summaryrefslogtreecommitdiff
path: root/src/cuchaz/enigma/gui
diff options
context:
space:
mode:
authorGravatar jeff2014-07-29 23:12:30 -0400
committerGravatar jeff2014-07-29 23:12:30 -0400
commit85b3ea9beb5934012280dc0efa475f334dd9a93a (patch)
treeabd878ee7f8c2929431b49475783e0bb2a02e281 /src/cuchaz/enigma/gui
parentadded start of menu bar (diff)
downloadenigma-fork-85b3ea9beb5934012280dc0efa475f334dd9a93a.tar.gz
enigma-fork-85b3ea9beb5934012280dc0efa475f334dd9a93a.tar.xz
enigma-fork-85b3ea9beb5934012280dc0efa475f334dd9a93a.zip
added gui/cli loading of jars/mappings
gui can save mappings too
Diffstat (limited to 'src/cuchaz/enigma/gui')
-rw-r--r--src/cuchaz/enigma/gui/Gui.java278
-rw-r--r--src/cuchaz/enigma/gui/GuiController.java147
2 files changed, 368 insertions, 57 deletions
diff --git a/src/cuchaz/enigma/gui/Gui.java b/src/cuchaz/enigma/gui/Gui.java
index 631089c..a86ff9b 100644
--- a/src/cuchaz/enigma/gui/Gui.java
+++ b/src/cuchaz/enigma/gui/Gui.java
@@ -20,6 +20,7 @@ import java.awt.event.ActionEvent;
20import java.awt.event.ActionListener; 20import java.awt.event.ActionListener;
21import java.awt.event.MouseAdapter; 21import java.awt.event.MouseAdapter;
22import java.awt.event.MouseEvent; 22import java.awt.event.MouseEvent;
23import java.io.IOException;
23import java.util.List; 24import java.util.List;
24import java.util.Vector; 25import java.util.Vector;
25 26
@@ -27,6 +28,7 @@ import javax.swing.BorderFactory;
27import javax.swing.BoxLayout; 28import javax.swing.BoxLayout;
28import javax.swing.JButton; 29import javax.swing.JButton;
29import javax.swing.JEditorPane; 30import javax.swing.JEditorPane;
31import javax.swing.JFileChooser;
30import javax.swing.JFrame; 32import javax.swing.JFrame;
31import javax.swing.JLabel; 33import javax.swing.JLabel;
32import javax.swing.JList; 34import javax.swing.JList;
@@ -39,6 +41,7 @@ import javax.swing.JSplitPane;
39import javax.swing.JTextField; 41import javax.swing.JTextField;
40import javax.swing.ListSelectionModel; 42import javax.swing.ListSelectionModel;
41import javax.swing.WindowConstants; 43import javax.swing.WindowConstants;
44import javax.swing.event.CaretEvent;
42import javax.swing.event.CaretListener; 45import javax.swing.event.CaretListener;
43import javax.swing.text.BadLocationException; 46import javax.swing.text.BadLocationException;
44 47
@@ -55,6 +58,8 @@ import cuchaz.enigma.mapping.MethodEntry;
55 58
56public class Gui 59public class Gui
57{ 60{
61 private GuiController m_controller;
62
58 // controls 63 // controls
59 private JFrame m_frame; 64 private JFrame m_frame;
60 private JList<ClassFile> m_obfClasses; 65 private JList<ClassFile> m_obfClasses;
@@ -65,16 +70,28 @@ public class Gui
65 private JLabel m_typeLabel; 70 private JLabel m_typeLabel;
66 private JTextField m_nameField; 71 private JTextField m_nameField;
67 private JButton m_renameButton; 72 private JButton m_renameButton;
73 private BoxHighlightPainter m_highlightPainter;
68 74
69 // listeners 75 // dynamic menu items
70 private ClassSelectionListener m_classSelectionListener; 76 private JMenuItem m_closeJarMenu;
71 private RenameListener m_renameListener; 77 private JMenuItem m_openMappingsMenu;
78 private JMenuItem m_saveMappingsMenu;
79 private JMenuItem m_saveMappingsAsMenu;
80 private JMenuItem m_closeMappingsMenu;
72 81
73 private BoxHighlightPainter m_highlightPainter; 82 // state
74 private EntryPair m_selectedEntryPair; 83 private EntryPair m_selectedEntryPair;
84 private JFileChooser m_jarFileChooser;
85 private JFileChooser m_mappingFileChooser;
75 86
76 public Gui( ) 87 public Gui( )
77 { 88 {
89 m_controller = new GuiController( this );
90
91 // init file choosers
92 m_jarFileChooser = new JFileChooser();
93 m_mappingFileChooser = new JFileChooser();
94
78 // init frame 95 // init frame
79 m_frame = new JFrame( Constants.Name ); 96 m_frame = new JFrame( Constants.Name );
80 final Container pane = m_frame.getContentPane(); 97 final Container pane = m_frame.getContentPane();
@@ -91,13 +108,10 @@ public class Gui
91 { 108 {
92 if( event.getClickCount() == 2 ) 109 if( event.getClickCount() == 2 )
93 { 110 {
94 if( m_classSelectionListener != null ) 111 ClassFile selected = m_obfClasses.getSelectedValue();
112 if( selected != null )
95 { 113 {
96 ClassFile selected = m_obfClasses.getSelectedValue(); 114 m_controller.deobfuscateClass( selected );
97 if( selected != null )
98 {
99 m_classSelectionListener.classSelected( selected );
100 }
101 } 115 }
102 } 116 }
103 } 117 }
@@ -130,9 +144,9 @@ public class Gui
130 @Override 144 @Override
131 public void actionPerformed( ActionEvent event ) 145 public void actionPerformed( ActionEvent event )
132 { 146 {
133 if( m_renameListener != null && m_selectedEntryPair != null ) 147 if( m_selectedEntryPair != null )
134 { 148 {
135 m_renameListener.rename( m_selectedEntryPair.obf, m_nameField.getText() ); 149 m_controller.rename( m_selectedEntryPair.obf, m_nameField.getText() );
136 } 150 }
137 } 151 }
138 } ); 152 } );
@@ -148,10 +162,27 @@ public class Gui
148 162
149 // init editor 163 // init editor
150 DefaultSyntaxKit.initKit(); 164 DefaultSyntaxKit.initKit();
165 m_highlightPainter = new BoxHighlightPainter();
151 m_editor = new JEditorPane(); 166 m_editor = new JEditorPane();
152 m_editor.setEditable( false ); 167 m_editor.setEditable( false );
153 JScrollPane sourceScroller = new JScrollPane( m_editor ); 168 JScrollPane sourceScroller = new JScrollPane( m_editor );
154 m_editor.setContentType( "text/java" ); 169 m_editor.setContentType( "text/java" );
170 m_editor.addCaretListener( new CaretListener( )
171 {
172 @Override
173 public void caretUpdate( CaretEvent event )
174 {
175 m_selectedEntryPair = m_controller.getEntryPair( event.getDot() );
176 if( m_selectedEntryPair != null )
177 {
178 showEntryPair( m_selectedEntryPair );
179 }
180 else
181 {
182 clearEntryPair();
183 }
184 }
185 } );
155 186
156 // layout controls 187 // layout controls
157 JSplitPane splitLeft = new JSplitPane( JSplitPane.VERTICAL_SPLIT, true, obfPanel, deobfPanel ); 188 JSplitPane splitLeft = new JSplitPane( JSplitPane.VERTICAL_SPLIT, true, obfPanel, deobfPanel );
@@ -164,21 +195,147 @@ public class Gui
164 195
165 // init menus 196 // init menus
166 JMenuBar menuBar = new JMenuBar(); 197 JMenuBar menuBar = new JMenuBar();
167 JMenu menu = new JMenu( "Help" ); 198 m_frame.setJMenuBar( menuBar );
168 menu.setMnemonic( 'h' ); 199 {
169 JMenuItem item = new JMenuItem( "About" ); 200 JMenu menu = new JMenu( "File" );
170 item.setMnemonic( 'a' ); 201 menuBar.add( menu );
171 item.addActionListener( new ActionListener( ) 202 {
203 JMenuItem item = new JMenuItem( "Open Jar..." );
204 menu.add( item );
205 item.addActionListener( new ActionListener( )
206 {
207 @Override
208 public void actionPerformed( ActionEvent event )
209 {
210 if( m_jarFileChooser.showOpenDialog( m_frame ) == JFileChooser.APPROVE_OPTION )
211 {
212 try
213 {
214 m_controller.openJar( m_jarFileChooser.getSelectedFile() );
215 }
216 catch( IOException ex )
217 {
218 throw new Error( ex );
219 }
220 }
221 }
222 } );
223 }
224 {
225 JMenuItem item = new JMenuItem( "Close Jar" );
226 menu.add( item );
227 item.addActionListener( new ActionListener( )
228 {
229 @Override
230 public void actionPerformed( ActionEvent event )
231 {
232 m_controller.closeJar();
233 }
234 } );
235 m_closeJarMenu = item;
236 }
237 menu.addSeparator();
238 {
239 JMenuItem item = new JMenuItem( "Open Mappings..." );
240 menu.add( item );
241 item.addActionListener( new ActionListener( )
242 {
243 @Override
244 public void actionPerformed( ActionEvent event )
245 {
246 if( m_mappingFileChooser.showOpenDialog( m_frame ) == JFileChooser.APPROVE_OPTION )
247 {
248 try
249 {
250 m_controller.openMappings( m_mappingFileChooser.getSelectedFile() );
251 m_saveMappingsMenu.setEnabled( true );
252 }
253 catch( IOException ex )
254 {
255 throw new Error( ex );
256 }
257 }
258 }
259 } );
260 m_openMappingsMenu = item;
261 }
262 {
263 JMenuItem item = new JMenuItem( "Save Mappings" );
264 menu.add( item );
265 item.addActionListener( new ActionListener( )
266 {
267 @Override
268 public void actionPerformed( ActionEvent event )
269 {
270 try
271 {
272 m_controller.saveMappings( m_mappingFileChooser.getSelectedFile() );
273 }
274 catch( IOException ex )
275 {
276 throw new Error( ex );
277 }
278 }
279 } );
280 m_saveMappingsMenu = item;
281 }
282 {
283 JMenuItem item = new JMenuItem( "Save Mappings As..." );
284 menu.add( item );
285 item.addActionListener( new ActionListener( )
286 {
287 @Override
288 public void actionPerformed( ActionEvent event )
172 { 289 {
173 @Override 290 if( m_mappingFileChooser.showSaveDialog( m_frame ) == JFileChooser.APPROVE_OPTION )
174 public void actionPerformed( ActionEvent event )
175 { 291 {
176 AboutDialog.show( m_frame ); 292 try
293 {
294 m_controller.saveMappings( m_mappingFileChooser.getSelectedFile() );
295 m_saveMappingsMenu.setEnabled( true );
296 }
297 catch( IOException ex )
298 {
299 throw new Error( ex );
300 }
177 } 301 }
178 } ); 302 }
303 } );
304 m_saveMappingsAsMenu = item;
305 }
306 {
307 JMenuItem item = new JMenuItem( "Close Mapppings" );
179 menu.add( item ); 308 menu.add( item );
309 item.addActionListener( new ActionListener( )
310 {
311 @Override
312 public void actionPerformed( ActionEvent event )
313 {
314 m_controller.closeMappings();
315 }
316 } );
317 m_closeMappingsMenu = item;
318 }
319 }
320 {
321 JMenu menu = new JMenu( "Help" );
180 menuBar.add( menu ); 322 menuBar.add( menu );
181 m_frame.setJMenuBar( menuBar ); 323 {
324 JMenuItem item = new JMenuItem( "About" );
325 menu.add( item );
326 item.addActionListener( new ActionListener( )
327 {
328 @Override
329 public void actionPerformed( ActionEvent event )
330 {
331 AboutDialog.show( m_frame );
332 }
333 } );
334 }
335 }
336
337 // init state
338 onCloseJar();
182 339
183 // show the frame 340 // show the frame
184 pane.doLayout(); 341 pane.doLayout();
@@ -186,22 +343,52 @@ public class Gui
186 m_frame.setMinimumSize( new Dimension( 640, 480 ) ); 343 m_frame.setMinimumSize( new Dimension( 640, 480 ) );
187 m_frame.setVisible( true ); 344 m_frame.setVisible( true );
188 m_frame.setDefaultCloseOperation( WindowConstants.EXIT_ON_CLOSE ); 345 m_frame.setDefaultCloseOperation( WindowConstants.EXIT_ON_CLOSE );
346 }
347
348 public GuiController getController( )
349 {
350 return m_controller;
351 }
352
353 public void onOpenJar( String jarName )
354 {
355 // update gui
356 m_frame.setTitle( Constants.Name + " - " + jarName );
357 setSource( null );
189 358
190 // init listeners 359 // update menu
191 m_classSelectionListener = null; 360 m_closeJarMenu.setEnabled( true );
192 m_renameListener = null; 361 m_openMappingsMenu.setEnabled( true );
193 362 m_saveMappingsMenu.setEnabled( false );
194 m_highlightPainter = new BoxHighlightPainter(); 363 m_saveMappingsAsMenu.setEnabled( true );
364 m_closeMappingsMenu.setEnabled( true );
195 } 365 }
196 366
197 public void setTitle( String title ) 367 public void onCloseJar( )
198 { 368 {
199 m_frame.setTitle( Constants.Name + " - " + title ); 369 // update gui
370 m_frame.setTitle( Constants.Name );
371 setObfClasses( null );
372 setSource( null );
373
374 // update menu
375 m_closeJarMenu.setEnabled( false );
376 m_openMappingsMenu.setEnabled( false );
377 m_saveMappingsMenu.setEnabled( false );
378 m_saveMappingsAsMenu.setEnabled( false );
379 m_closeMappingsMenu.setEnabled( false );
200 } 380 }
201 381
202 public void setObfClasses( List<ClassFile> classes ) 382 public void setObfClasses( List<ClassFile> classes )
203 { 383 {
204 m_obfClasses.setListData( new Vector<ClassFile>( classes ) ); 384 if( classes != null )
385 {
386 m_obfClasses.setListData( new Vector<ClassFile>( classes ) );
387 }
388 else
389 {
390 m_obfClasses.setListData( new Vector<ClassFile>() );
391 }
205 } 392 }
206 393
207 public void setSource( String source ) 394 public void setSource( String source )
@@ -212,9 +399,10 @@ public class Gui
212 public void setSource( String source, SourceIndex index ) 399 public void setSource( String source, SourceIndex index )
213 { 400 {
214 m_editor.setText( source ); 401 m_editor.setText( source );
402 setHighlightedTokens( null );
215 } 403 }
216 404
217 public void highlightTokens( Iterable<Token> tokens ) 405 public void setHighlightedTokens( Iterable<Token> tokens )
218 { 406 {
219 // remove any old highlighters 407 // remove any old highlighters
220 m_editor.getHighlighter().removeAllHighlights(); 408 m_editor.getHighlighter().removeAllHighlights();
@@ -240,28 +428,7 @@ public class Gui
240 redraw(); 428 redraw();
241 } 429 }
242 430
243 public void setClassSelectionListener( ClassSelectionListener val ) 431 private void clearEntryPair( )
244 {
245 m_classSelectionListener = val;
246 }
247
248 public void setRenameListener( RenameListener val )
249 {
250 m_renameListener = val;
251 }
252
253 public void setCaretListener( CaretListener listener )
254 {
255 // remove any old listeners
256 for( CaretListener oldListener : m_editor.getCaretListeners() )
257 {
258 m_editor.removeCaretListener( oldListener );
259 }
260
261 m_editor.addCaretListener( listener );
262 }
263
264 public void clearEntryPair( )
265 { 432 {
266 m_actionPanel.removeAll(); 433 m_actionPanel.removeAll();
267 JLabel label = new JLabel( "No identifier selected" ); 434 JLabel label = new JLabel( "No identifier selected" );
@@ -272,7 +439,7 @@ public class Gui
272 redraw(); 439 redraw();
273 } 440 }
274 441
275 public void showEntryPair( EntryPair pair ) 442 private void showEntryPair( EntryPair pair )
276 { 443 {
277 if( pair == null ) 444 if( pair == null )
278 { 445 {
@@ -280,9 +447,6 @@ public class Gui
280 return; 447 return;
281 } 448 }
282 449
283 // TEMP
284 System.out.println( "Pair:\n" + pair.obf + "\n" + pair.deobf );
285
286 m_selectedEntryPair = pair; 450 m_selectedEntryPair = pair;
287 451
288 // layout the action panel 452 // layout the action panel
diff --git a/src/cuchaz/enigma/gui/GuiController.java b/src/cuchaz/enigma/gui/GuiController.java
new file mode 100644
index 0000000..5df2d43
--- /dev/null
+++ b/src/cuchaz/enigma/gui/GuiController.java
@@ -0,0 +1,147 @@
1/*******************************************************************************
2 * Copyright (c) 2014 Jeff Martin.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the GNU Public License v3.0
5 * which accompanies this distribution, and is available at
6 * http://www.gnu.org/licenses/gpl.html
7 *
8 * Contributors:
9 * Jeff Martin - initial API and implementation
10 ******************************************************************************/
11package cuchaz.enigma.gui;
12
13import java.io.File;
14import java.io.FileInputStream;
15import java.io.FileOutputStream;
16import java.io.IOException;
17
18import cuchaz.enigma.ClassFile;
19import cuchaz.enigma.Deobfuscator;
20import cuchaz.enigma.analysis.Analyzer;
21import cuchaz.enigma.analysis.SourceIndex;
22import cuchaz.enigma.mapping.ClassEntry;
23import cuchaz.enigma.mapping.Entry;
24import cuchaz.enigma.mapping.EntryPair;
25import cuchaz.enigma.mapping.TranslationMappings;
26
27public class GuiController
28{
29 private Deobfuscator m_deobfuscator;
30 private Gui m_gui;
31 private SourceIndex m_index;
32 private ClassFile m_currentFile;
33
34 public GuiController( Gui gui )
35 {
36 m_gui = gui;
37 m_deobfuscator = null;
38 m_index = null;
39 m_currentFile = null;
40 }
41
42 public void openJar( File file )
43 throws IOException
44 {
45 m_deobfuscator = new Deobfuscator( file );
46 m_gui.onOpenJar( m_deobfuscator.getJarName() );
47 m_gui.setObfClasses( m_deobfuscator.getObfuscatedClasses() );
48 }
49
50 public void closeJar( )
51 {
52 m_deobfuscator = null;
53 m_gui.onCloseJar();
54 }
55
56 public void openMappings( File file )
57 throws IOException
58 {
59 FileInputStream in = new FileInputStream( file );
60 m_deobfuscator.setMappings( TranslationMappings.newFromStream( in ) );
61 in.close();
62 refreshOpenFiles();
63 }
64
65 public void saveMappings( File file )
66 throws IOException
67 {
68 FileOutputStream out = new FileOutputStream( file );
69 m_deobfuscator.getMappings().write( out );
70 out.close();
71 }
72
73 public void closeMappings( )
74 {
75 m_deobfuscator.setMappings( null );
76 refreshOpenFiles();
77 }
78
79 public void deobfuscateClass( ClassFile classFile )
80 {
81 m_currentFile = classFile;
82 deobfuscate( m_currentFile );
83 }
84
85 public EntryPair getEntryPair( int pos )
86 {
87 if( m_index == null )
88 {
89 return null;
90 }
91
92 Entry deobfEntry = m_index.getEntry( pos );
93 if( deobfEntry == null )
94 {
95 return null;
96 }
97 return new EntryPair( m_deobfuscator.obfuscate( deobfEntry ), deobfEntry );
98 }
99
100 public void rename( Entry obfsEntry, String newName )
101 {
102 m_deobfuscator.rename( obfsEntry, newName );
103
104 // did we rename the current file?
105 if( obfsEntry instanceof ClassEntry )
106 {
107 ClassEntry classEntry = (ClassEntry)obfsEntry;
108
109 // update the current file
110 if( classEntry.getName().equals( m_currentFile.getName() ) )
111 {
112 m_currentFile = new ClassFile( newName );
113 }
114 }
115
116 refreshOpenFiles();
117 }
118
119 private void refreshOpenFiles( )
120 {
121 if( m_currentFile != null )
122 {
123 deobfuscate( m_currentFile );
124 }
125 }
126
127 private void deobfuscate( final ClassFile classFile )
128 {
129 m_gui.setSource( "(deobfuscating...)" );
130
131 // run the deobfuscator in a separate thread so we don't block the GUI event queue
132 new Thread( )
133 {
134 @Override
135 public void run( )
136 {
137 // deobfuscate the bytecode
138 String source = m_deobfuscator.getSource( classFile );
139 m_gui.setSource( source );
140
141 // index the source file
142 m_index = Analyzer.analyze( classFile.getName(), source );
143 m_gui.setHighlightedTokens( m_index.tokens() );
144 }
145 }.start();
146 }
147}