未验证 提交 c66ffaa7 编写于 作者: S Skylot

feat(gui): show start page on jadx open

上级 5193c6a5
...@@ -135,6 +135,9 @@ public class JadxProject { ...@@ -135,6 +135,9 @@ public class JadxProject {
.map(TabStateViewAdapter::build) .map(TabStateViewAdapter::build)
.filter(Objects::nonNull) .filter(Objects::nonNull)
.collect(Collectors.toList()); .collect(Collectors.toList());
if (tabStateList.isEmpty()) {
return;
}
boolean dataChanged; boolean dataChanged;
dataChanged = data.setOpenTabs(tabStateList); dataChanged = data.setOpenTabs(tabStateList);
dataChanged |= data.setActiveTab(activeTab); dataChanged |= data.setActiveTab(activeTab);
......
...@@ -210,6 +210,11 @@ public class JadxSettings extends JadxCLIArgs { ...@@ -210,6 +210,11 @@ public class JadxSettings extends JadxCLIArgs {
partialSync(settings -> settings.recentProjects = recentProjects); partialSync(settings -> settings.recentProjects = recentProjects);
} }
public void removeRecentProject(Path projectPath) {
recentProjects.remove(projectPath);
partialSync(settings -> settings.recentProjects = recentProjects);
}
public void saveWindowPos(Window window) { public void saveWindowPos(Window window) {
WindowLocation pos = new WindowLocation(window.getClass().getSimpleName(), window.getBounds()); WindowLocation pos = new WindowLocation(window.getClass().getSimpleName(), window.getBounds());
windowPos.put(pos.getWindowId(), pos); windowPos.put(pos.getWindowId(), pos);
......
...@@ -14,6 +14,7 @@ import jadx.api.JavaNode; ...@@ -14,6 +14,7 @@ import jadx.api.JavaNode;
import jadx.core.dex.attributes.AFlag; import jadx.core.dex.attributes.AFlag;
import jadx.core.dex.info.AccessInfo; import jadx.core.dex.info.AccessInfo;
import jadx.core.dex.instructions.args.ArgType; import jadx.core.dex.instructions.args.ArgType;
import jadx.gui.utils.Icons;
import jadx.gui.utils.OverlayIcon; import jadx.gui.utils.OverlayIcon;
import jadx.gui.utils.UiUtils; import jadx.gui.utils.UiUtils;
...@@ -84,10 +85,10 @@ public class JMethod extends JNode { ...@@ -84,10 +85,10 @@ public class JMethod extends JNode {
OverlayIcon overIcon = new OverlayIcon(icon); OverlayIcon overIcon = new OverlayIcon(icon);
if (accessFlags.isFinal()) { if (accessFlags.isFinal()) {
overIcon.add(UiUtils.ICON_FINAL); overIcon.add(Icons.FINAL);
} }
if (accessFlags.isStatic()) { if (accessFlags.isStatic()) {
overIcon.add(UiUtils.ICON_STATIC); overIcon.add(Icons.STATIC);
} }
return overIcon; return overIcon;
......
...@@ -125,12 +125,14 @@ import jadx.gui.ui.panel.IssuesPanel; ...@@ -125,12 +125,14 @@ import jadx.gui.ui.panel.IssuesPanel;
import jadx.gui.ui.panel.JDebuggerPanel; import jadx.gui.ui.panel.JDebuggerPanel;
import jadx.gui.ui.panel.ProgressPanel; import jadx.gui.ui.panel.ProgressPanel;
import jadx.gui.ui.popupmenu.JPackagePopupMenu; import jadx.gui.ui.popupmenu.JPackagePopupMenu;
import jadx.gui.ui.treenodes.StartPageNode;
import jadx.gui.ui.treenodes.SummaryNode; import jadx.gui.ui.treenodes.SummaryNode;
import jadx.gui.update.JadxUpdate; import jadx.gui.update.JadxUpdate;
import jadx.gui.update.JadxUpdate.IUpdateCallback; import jadx.gui.update.JadxUpdate.IUpdateCallback;
import jadx.gui.update.data.Release; import jadx.gui.update.data.Release;
import jadx.gui.utils.CacheObject; import jadx.gui.utils.CacheObject;
import jadx.gui.utils.FontUtils; import jadx.gui.utils.FontUtils;
import jadx.gui.utils.Icons;
import jadx.gui.utils.LafManager; import jadx.gui.utils.LafManager;
import jadx.gui.utils.Link; import jadx.gui.utils.Link;
import jadx.gui.utils.NLS; import jadx.gui.utils.NLS;
...@@ -152,7 +154,6 @@ public class MainWindow extends JFrame { ...@@ -152,7 +154,6 @@ public class MainWindow extends JFrame {
private static final double WINDOW_RATIO = 1 - BORDER_RATIO * 2; private static final double WINDOW_RATIO = 1 - BORDER_RATIO * 2;
public static final double SPLIT_PANE_RESIZE_WEIGHT = 0.15; public static final double SPLIT_PANE_RESIZE_WEIGHT = 0.15;
private static final ImageIcon ICON_OPEN = UiUtils.openSvgIcon("ui/openDisk");
private static final ImageIcon ICON_ADD_FILES = UiUtils.openSvgIcon("ui/addFile"); private static final ImageIcon ICON_ADD_FILES = UiUtils.openSvgIcon("ui/addFile");
private static final ImageIcon ICON_SAVE_ALL = UiUtils.openSvgIcon("ui/menu-saveall"); private static final ImageIcon ICON_SAVE_ALL = UiUtils.openSvgIcon("ui/menu-saveall");
private static final ImageIcon ICON_RELOAD = UiUtils.openSvgIcon("ui/refresh"); private static final ImageIcon ICON_RELOAD = UiUtils.openSvgIcon("ui/refresh");
...@@ -249,7 +250,7 @@ public class MainWindow extends JFrame { ...@@ -249,7 +250,7 @@ public class MainWindow extends JFrame {
private void processCommandLineArgs() { private void processCommandLineArgs() {
if (settings.getFiles().isEmpty()) { if (settings.getFiles().isEmpty()) {
openFileOrProject(); tabbedPane.showNode(new StartPageNode());
} else { } else {
open(FileUtils.fileNamesToPaths(settings.getFiles()), this::handleSelectClassOption); open(FileUtils.fileNamesToPaths(settings.getFiles()), this::handleSelectClassOption);
} }
...@@ -286,12 +287,20 @@ public class MainWindow extends JFrame { ...@@ -286,12 +287,20 @@ public class MainWindow extends JFrame {
}); });
} }
public void openFileOrProject() { public void openFileDialog() {
showOpenDialog(FileDialog.OpenMode.OPEN);
}
public void openProjectDialog() {
showOpenDialog(FileDialog.OpenMode.OPEN_PROJECT);
}
private void showOpenDialog(FileDialog.OpenMode mode) {
saveAll(); saveAll();
if (!ensureProjectIsSaved()) { if (!ensureProjectIsSaved()) {
return; return;
} }
FileDialog fileDialog = new FileDialog(this, FileDialog.OpenMode.OPEN); FileDialog fileDialog = new FileDialog(this, mode);
List<Path> openPaths = fileDialog.show(); List<Path> openPaths = fileDialog.show();
if (!openPaths.isEmpty()) { if (!openPaths.isEmpty()) {
settings.setLastOpenFilePath(fileDialog.getCurrentDir()); settings.setLastOpenFilePath(fileDialog.getCurrentDir());
...@@ -313,6 +322,7 @@ public class MainWindow extends JFrame { ...@@ -313,6 +322,7 @@ public class MainWindow extends JFrame {
} }
private void newProject() { private void newProject() {
saveAll();
if (!ensureProjectIsSaved()) { if (!ensureProjectIsSaved()) {
return; return;
} }
...@@ -386,7 +396,11 @@ public class MainWindow extends JFrame { ...@@ -386,7 +396,11 @@ public class MainWindow extends JFrame {
s -> update()); s -> update());
} }
void open(List<Path> paths) { public void open(Path path) {
open(Collections.singletonList(path), EMPTY_RUNNABLE);
}
public void open(List<Path> paths) {
open(paths, EMPTY_RUNNABLE); open(paths, EMPTY_RUNNABLE);
} }
...@@ -825,14 +839,15 @@ public class MainWindow extends JFrame { ...@@ -825,14 +839,15 @@ public class MainWindow extends JFrame {
} }
private void initMenuAndToolbar() { private void initMenuAndToolbar() {
Action openAction = new AbstractAction(NLS.str("file.open_action"), ICON_OPEN) { ActionHandler openAction = new ActionHandler(this::openFileDialog);
@Override openAction.setNameAndDesc(NLS.str("file.open_action"));
public void actionPerformed(ActionEvent e) { openAction.setIcon(Icons.OPEN);
openFileOrProject(); openAction.setKeyBinding(getKeyStroke(KeyEvent.VK_O, UiUtils.ctrlButton()));
}
}; ActionHandler openProject = new ActionHandler(this::openProjectDialog);
openAction.putValue(Action.SHORT_DESCRIPTION, NLS.str("file.open_action")); openProject.setNameAndDesc(NLS.str("file.open_project"));
openAction.putValue(Action.ACCELERATOR_KEY, getKeyStroke(KeyEvent.VK_O, UiUtils.ctrlButton())); openProject.setIcon(Icons.OPEN_PROJECT);
openProject.setKeyBinding(getKeyStroke(KeyEvent.VK_O, InputEvent.SHIFT_DOWN_MASK | UiUtils.ctrlButton()));
Action addFilesAction = new AbstractAction(NLS.str("file.add_files_action"), ICON_ADD_FILES) { Action addFilesAction = new AbstractAction(NLS.str("file.add_files_action"), ICON_ADD_FILES) {
@Override @Override
...@@ -842,7 +857,7 @@ public class MainWindow extends JFrame { ...@@ -842,7 +857,7 @@ public class MainWindow extends JFrame {
}; };
addFilesAction.putValue(Action.SHORT_DESCRIPTION, NLS.str("file.add_files_action")); addFilesAction.putValue(Action.SHORT_DESCRIPTION, NLS.str("file.add_files_action"));
newProjectAction = new AbstractAction(NLS.str("file.new_project")) { newProjectAction = new AbstractAction(NLS.str("file.new_project"), Icons.NEW_PROJECT) {
@Override @Override
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
newProject(); newProject();
...@@ -1089,6 +1104,7 @@ public class MainWindow extends JFrame { ...@@ -1089,6 +1104,7 @@ public class MainWindow extends JFrame {
JMenu file = new JMenu(NLS.str("menu.file")); JMenu file = new JMenu(NLS.str("menu.file"));
file.setMnemonic(KeyEvent.VK_F); file.setMnemonic(KeyEvent.VK_F);
file.add(openAction); file.add(openAction);
file.add(openProject);
file.add(addFilesAction); file.add(addFilesAction);
file.addSeparator(); file.addSeparator();
file.add(newProjectAction); file.add(newProjectAction);
......
...@@ -9,7 +9,6 @@ import java.util.List; ...@@ -9,7 +9,6 @@ import java.util.List;
import java.util.Map; import java.util.Map;
import javax.swing.BorderFactory; import javax.swing.BorderFactory;
import javax.swing.ImageIcon;
import javax.swing.JButton; import javax.swing.JButton;
import javax.swing.JLabel; import javax.swing.JLabel;
import javax.swing.JMenuItem; import javax.swing.JMenuItem;
...@@ -21,15 +20,13 @@ import javax.swing.plaf.basic.BasicButtonUI; ...@@ -21,15 +20,13 @@ import javax.swing.plaf.basic.BasicButtonUI;
import jadx.gui.treemodel.JClass; import jadx.gui.treemodel.JClass;
import jadx.gui.treemodel.JNode; import jadx.gui.treemodel.JNode;
import jadx.gui.ui.panel.ContentPanel; import jadx.gui.ui.panel.ContentPanel;
import jadx.gui.utils.Icons;
import jadx.gui.utils.NLS; import jadx.gui.utils.NLS;
import jadx.gui.utils.UiUtils; import jadx.gui.utils.UiUtils;
public class TabComponent extends JPanel { public class TabComponent extends JPanel {
private static final long serialVersionUID = -8147035487543610321L; private static final long serialVersionUID = -8147035487543610321L;
private static final ImageIcon ICON_CLOSE = UiUtils.openSvgIcon("ui/closeHovered");
private static final ImageIcon ICON_CLOSE_INACTIVE = UiUtils.openSvgIcon("ui/close");
private final TabbedPane tabbedPane; private final TabbedPane tabbedPane;
private final ContentPanel contentPanel; private final ContentPanel contentPanel;
...@@ -71,8 +68,8 @@ public class TabComponent extends JPanel { ...@@ -71,8 +68,8 @@ public class TabComponent extends JPanel {
label.setIcon(node.getIcon()); label.setIcon(node.getIcon());
final JButton closeBtn = new JButton(); final JButton closeBtn = new JButton();
closeBtn.setIcon(ICON_CLOSE_INACTIVE); closeBtn.setIcon(Icons.CLOSE_INACTIVE);
closeBtn.setRolloverIcon(ICON_CLOSE); closeBtn.setRolloverIcon(Icons.CLOSE);
closeBtn.setRolloverEnabled(true); closeBtn.setRolloverEnabled(true);
closeBtn.setOpaque(false); closeBtn.setOpaque(false);
closeBtn.setUI(new BasicButtonUI()); closeBtn.setUI(new BasicButtonUI());
......
...@@ -29,6 +29,7 @@ public class FileDialog { ...@@ -29,6 +29,7 @@ public class FileDialog {
public enum OpenMode { public enum OpenMode {
OPEN, OPEN,
OPEN_PROJECT,
ADD, ADD,
SAVE_PROJECT, SAVE_PROJECT,
EXPORT, EXPORT,
...@@ -95,13 +96,19 @@ public class FileDialog { ...@@ -95,13 +96,19 @@ public class FileDialog {
private void initForMode(OpenMode mode) { private void initForMode(OpenMode mode) {
switch (mode) { switch (mode) {
case OPEN: case OPEN:
case OPEN_PROJECT:
case ADD: case ADD:
fileExtList = new ArrayList<>(Arrays.asList("apk", "dex", "jar", "class", "smali", "zip", "aar", "arsc")); if (mode == OpenMode.OPEN_PROJECT) {
if (mode == OpenMode.OPEN) { fileExtList = Collections.singletonList(JadxProject.PROJECT_EXTENSION);
fileExtList.addAll(Arrays.asList(JadxProject.PROJECT_EXTENSION, "aab"));
title = NLS.str("file.open_title"); title = NLS.str("file.open_title");
} else { } else {
title = NLS.str("file.add_files_action"); fileExtList = new ArrayList<>(Arrays.asList("apk", "dex", "jar", "class", "smali", "zip", "xapk", "aar", "arsc"));
if (mode == OpenMode.OPEN) {
fileExtList.addAll(Arrays.asList(JadxProject.PROJECT_EXTENSION, "aab"));
title = NLS.str("file.open_title");
} else {
title = NLS.str("file.add_files_action");
}
} }
selectionMode = JFileChooser.FILES_AND_DIRECTORIES; selectionMode = JFileChooser.FILES_AND_DIRECTORIES;
currentDir = mainWindow.getSettings().getLastOpenFilePath(); currentDir = mainWindow.getSettings().getLastOpenFilePath();
......
package jadx.gui.ui.panel;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Font;
import java.nio.file.Path;
import java.util.List;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.JButton;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.ScrollPaneConstants;
import javax.swing.border.Border;
import javax.swing.border.TitledBorder;
import jadx.gui.settings.JadxSettings;
import jadx.gui.ui.MainWindow;
import jadx.gui.ui.TabbedPane;
import jadx.gui.ui.treenodes.StartPageNode;
import jadx.gui.utils.Icons;
import jadx.gui.utils.NLS;
public class StartPagePanel extends ContentPanel {
public StartPagePanel(TabbedPane tabbedPane, StartPageNode node) {
super(tabbedPane, node);
MainWindow mainWindow = tabbedPane.getMainWindow();
Font baseFont = mainWindow.getSettings().getFont();
JButton openFile = new JButton(NLS.str("file.open_title"), Icons.OPEN);
openFile.addActionListener(ev -> mainWindow.openFileDialog());
JButton openProject = new JButton(NLS.str("file.open_project"), Icons.OPEN_PROJECT);
openProject.addActionListener(ev -> mainWindow.openProjectDialog());
JPanel start = new JPanel();
start.setBorder(sectionFrame(NLS.str("start_page.start"), baseFont));
start.setLayout(new BoxLayout(start, BoxLayout.LINE_AXIS));
start.add(openFile);
start.add(Box.createRigidArea(new Dimension(10, 0)));
start.add(openProject);
start.add(Box.createHorizontalGlue());
JPanel recentPanel = new JPanel();
JScrollPane scrollPane = new JScrollPane(recentPanel);
scrollPane.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
scrollPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
scrollPane.setPreferredSize(new Dimension(400, 200));
scrollPane.setBorder(BorderFactory.createEmptyBorder());
fillRecentPanel(recentPanel, scrollPane, mainWindow);
JPanel recent = new JPanel();
recent.setBorder(sectionFrame(NLS.str("start_page.recent"), baseFont));
recent.setLayout(new BoxLayout(recent, BoxLayout.PAGE_AXIS));
recent.add(scrollPane);
JPanel center = new JPanel();
center.setLayout(new BorderLayout(10, 10));
center.add(start, BorderLayout.PAGE_START);
center.add(recent, BorderLayout.CENTER);
center.setMaximumSize(new Dimension(700, 600));
center.setAlignmentX(CENTER_ALIGNMENT);
setLayout(new BoxLayout(this, BoxLayout.PAGE_AXIS));
setBorder(BorderFactory.createEmptyBorder(50, 50, 50, 50));
add(Box.createVerticalGlue());
add(center);
add(Box.createVerticalGlue());
}
private void fillRecentPanel(JPanel panel, JScrollPane scrollPane, MainWindow mainWindow) {
JadxSettings settings = mainWindow.getSettings();
List<Path> recentProjects = settings.getRecentProjects();
panel.removeAll();
panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
Font baseFont = settings.getFont();
Font font = baseFont.deriveFont(baseFont.getSize() - 1f);
for (Path path : recentProjects) {
JButton openBtn = new JButton(path.getFileName().toString());
openBtn.setToolTipText(path.toAbsolutePath().toString());
openBtn.setFont(font);
openBtn.setBorderPainted(false);
openBtn.addActionListener(ev -> mainWindow.open(path));
JButton removeBtn = new JButton();
removeBtn.setIcon(Icons.CLOSE_INACTIVE);
removeBtn.setRolloverIcon(Icons.CLOSE);
removeBtn.setRolloverEnabled(true);
removeBtn.setFocusable(false);
removeBtn.setBorder(null);
removeBtn.setBorderPainted(false);
removeBtn.setContentAreaFilled(false);
removeBtn.setOpaque(true);
removeBtn.addActionListener(e -> {
mainWindow.getSettings().removeRecentProject(path);
fillRecentPanel(panel, scrollPane, mainWindow);
panel.revalidate();
scrollPane.repaint();
});
JPanel linePanel = new JPanel();
linePanel.setLayout(new BoxLayout(linePanel, BoxLayout.LINE_AXIS));
linePanel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
linePanel.add(openBtn);
linePanel.add(Box.createHorizontalGlue());
linePanel.add(removeBtn);
panel.add(linePanel);
}
panel.add(Box.createVerticalGlue());
}
private static Border sectionFrame(String title, Font font) {
TitledBorder titledBorder = BorderFactory.createTitledBorder(title);
titledBorder.setTitleFont(font.deriveFont(Font.BOLD, font.getSize() + 1));
Border spacing = BorderFactory.createEmptyBorder(10, 10, 10, 10);
return BorderFactory.createCompoundBorder(titledBorder, spacing);
}
@Override
public void loadSettings() {
}
}
package jadx.gui.ui.treenodes;
import javax.swing.Icon;
import jadx.gui.treemodel.JClass;
import jadx.gui.treemodel.JNode;
import jadx.gui.ui.TabbedPane;
import jadx.gui.ui.panel.ContentPanel;
import jadx.gui.ui.panel.StartPagePanel;
import jadx.gui.utils.Icons;
import jadx.gui.utils.NLS;
public class StartPageNode extends JNode {
private static final long serialVersionUID = 8983134608645736174L;
@Override
public ContentPanel getContentPanel(TabbedPane tabbedPane) {
return new StartPagePanel(tabbedPane, this);
}
@Override
public String makeString() {
return NLS.str("start_page.title");
}
@Override
public Icon getIcon() {
return Icons.START_PAGE;
}
@Override
public JClass getJParent() {
return null;
}
}
package jadx.gui.utils;
import javax.swing.ImageIcon;
import static jadx.gui.utils.UiUtils.openSvgIcon;
public class Icons {
public static final ImageIcon OPEN = openSvgIcon("ui/openDisk");
public static final ImageIcon OPEN_PROJECT = openSvgIcon("ui/projectDirectory");
public static final ImageIcon NEW_PROJECT = openSvgIcon("ui/newFolder");
public static final ImageIcon CLOSE = openSvgIcon("ui/closeHovered");
public static final ImageIcon CLOSE_INACTIVE = openSvgIcon("ui/close");
public static final ImageIcon STATIC = openSvgIcon("nodes/staticMark");
public static final ImageIcon FINAL = openSvgIcon("nodes/finalMark");
public static final ImageIcon START_PAGE = openSvgIcon("nodes/newWindow");
}
...@@ -46,9 +46,6 @@ import jadx.gui.ui.codearea.AbstractCodeArea; ...@@ -46,9 +46,6 @@ import jadx.gui.ui.codearea.AbstractCodeArea;
public class UiUtils { public class UiUtils {
private static final Logger LOG = LoggerFactory.getLogger(UiUtils.class); private static final Logger LOG = LoggerFactory.getLogger(UiUtils.class);
public static final ImageIcon ICON_STATIC = openSvgIcon("nodes/staticMark");
public static final ImageIcon ICON_FINAL = openSvgIcon("nodes/finalMark");
/** /**
* The minimum about of memory in bytes we are trying to keep free, otherwise the application may * The minimum about of memory in bytes we are trying to keep free, otherwise the application may
* run out of heap * run out of heap
...@@ -190,10 +187,10 @@ public class UiUtils { ...@@ -190,10 +187,10 @@ public class UiUtils {
} }
OverlayIcon overIcon = new OverlayIcon(icon); OverlayIcon overIcon = new OverlayIcon(icon);
if (af.isFinal()) { if (af.isFinal()) {
overIcon.add(ICON_FINAL); overIcon.add(Icons.FINAL);
} }
if (af.isStatic()) { if (af.isStatic()) {
overIcon.add(ICON_STATIC); overIcon.add(Icons.STATIC);
} }
return overIcon; return overIcon;
} }
......
...@@ -11,6 +11,10 @@ public class ActionHandler extends AbstractAction { ...@@ -11,6 +11,10 @@ public class ActionHandler extends AbstractAction {
private final Consumer<ActionEvent> consumer; private final Consumer<ActionEvent> consumer;
public ActionHandler(Runnable action) {
this.consumer = ev -> action.run();
}
public ActionHandler(Consumer<ActionEvent> consumer) { public ActionHandler(Consumer<ActionEvent> consumer) {
this.consumer = consumer; this.consumer = consumer;
} }
......
...@@ -23,6 +23,7 @@ menu.update_label=Neue Version %s verfügbar! ...@@ -23,6 +23,7 @@ menu.update_label=Neue Version %s verfügbar!
file.open_action=Datei öffnen… file.open_action=Datei öffnen…
file.add_files_action=Dateien hinzufügen… file.add_files_action=Dateien hinzufügen…
file.open_title=Datei öffnen file.open_title=Datei öffnen
#file.open_project=Open project
file.new_project=Neues Projekt file.new_project=Neues Projekt
file.save_project=Projekt speichern file.save_project=Projekt speichern
file.save_project_as=Projekt speichern als… file.save_project_as=Projekt speichern als…
...@@ -35,6 +36,10 @@ file.export_gradle=Als Gradle-Projekt speichern ...@@ -35,6 +36,10 @@ file.export_gradle=Als Gradle-Projekt speichern
file.save_all_msg=Verzeichnis für das Speichern dekompilierter Ressourcen auswählen file.save_all_msg=Verzeichnis für das Speichern dekompilierter Ressourcen auswählen
file.exit=Beenden file.exit=Beenden
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=Quelltexte tree.sources_title=Quelltexte
tree.resources_title=Ressourcen tree.resources_title=Ressourcen
tree.loading=Laden… tree.loading=Laden…
......
...@@ -23,6 +23,7 @@ menu.update_label=New version %s available! ...@@ -23,6 +23,7 @@ menu.update_label=New version %s available!
file.open_action=Open files ... file.open_action=Open files ...
file.add_files_action=Add files file.add_files_action=Add files
file.open_title=Open file file.open_title=Open file
file.open_project=Open project
file.new_project=New project file.new_project=New project
file.save_project=Save project file.save_project=Save project
file.save_project_as=Save project as... file.save_project_as=Save project as...
...@@ -35,6 +36,10 @@ file.export_gradle=Save as gradle project ...@@ -35,6 +36,10 @@ file.export_gradle=Save as gradle project
file.save_all_msg=Select directory for save decompiled sources file.save_all_msg=Select directory for save decompiled sources
file.exit=Exit file.exit=Exit
start_page.title=Start page
start_page.start=Start
start_page.recent=Recent projects
tree.sources_title=Source code tree.sources_title=Source code
tree.resources_title=Resources tree.resources_title=Resources
tree.loading=Loading... tree.loading=Loading...
......
...@@ -23,6 +23,7 @@ menu.update_label=¡Nueva versión %s disponible! ...@@ -23,6 +23,7 @@ menu.update_label=¡Nueva versión %s disponible!
file.open_action=Abrir archivo... file.open_action=Abrir archivo...
#file.add_files_action=Add files ... #file.add_files_action=Add files ...
file.open_title=Abrir archivo file.open_title=Abrir archivo
#file.open_project=Open project
#file.new_project= #file.new_project=
#file.save_project= #file.save_project=
#file.save_project_as= #file.save_project_as=
...@@ -35,6 +36,10 @@ file.export_gradle=Guardar como proyecto Gradle ...@@ -35,6 +36,10 @@ file.export_gradle=Guardar como proyecto Gradle
file.save_all_msg=Seleccionar carpeta para guardar fuentes descompiladas file.save_all_msg=Seleccionar carpeta para guardar fuentes descompiladas
file.exit=Salir file.exit=Salir
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=Código fuente tree.sources_title=Código fuente
tree.resources_title=Recursos tree.resources_title=Recursos
tree.loading=Cargando... tree.loading=Cargando...
......
...@@ -23,6 +23,7 @@ menu.update_label=새 버전 %s 이(가) 존재합니다! ...@@ -23,6 +23,7 @@ menu.update_label=새 버전 %s 이(가) 존재합니다!
file.open_action=파일 열기 ... file.open_action=파일 열기 ...
file.add_files_action=파일 추가 file.add_files_action=파일 추가
file.open_title=파일 열기 file.open_title=파일 열기
#file.open_project=Open project
file.new_project=새 프로젝트 file.new_project=새 프로젝트
file.save_project=프로젝트 저장 file.save_project=프로젝트 저장
file.save_project_as=다른 이름으로 프로젝트 저장... file.save_project_as=다른 이름으로 프로젝트 저장...
...@@ -35,6 +36,10 @@ file.export_gradle=Gradle 프로젝트로 저장 ...@@ -35,6 +36,10 @@ file.export_gradle=Gradle 프로젝트로 저장
file.save_all_msg=디컴파일된 소스를 저장할 디렉토리 선택 file.save_all_msg=디컴파일된 소스를 저장할 디렉토리 선택
file.exit=나가기 file.exit=나가기
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=소스코드 tree.sources_title=소스코드
tree.resources_title=리소스 tree.resources_title=리소스
tree.loading=로딩중... tree.loading=로딩중...
......
...@@ -23,6 +23,7 @@ menu.update_label=Nova versão %s disponível! ...@@ -23,6 +23,7 @@ menu.update_label=Nova versão %s disponível!
file.open_action=Abrir arquivos... file.open_action=Abrir arquivos...
file.add_files_action=Adicionar arquivos file.add_files_action=Adicionar arquivos
file.open_title=Abrir arquivo file.open_title=Abrir arquivo
#file.open_project=Open project
file.new_project=Novo projeto file.new_project=Novo projeto
file.save_project=Salvar projeto file.save_project=Salvar projeto
file.save_project_as=Salvar projeto como... file.save_project_as=Salvar projeto como...
...@@ -35,6 +36,10 @@ file.export_gradle=Salvar como um projeto gradle ...@@ -35,6 +36,10 @@ file.export_gradle=Salvar como um projeto gradle
file.save_all_msg=Selecionar diretório para salvar arquivos descompilados file.save_all_msg=Selecionar diretório para salvar arquivos descompilados
file.exit=Sair file.exit=Sair
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=Código fonte tree.sources_title=Código fonte
tree.resources_title=Recursos tree.resources_title=Recursos
tree.loading=Carregando... tree.loading=Carregando...
......
...@@ -23,6 +23,7 @@ menu.update_label=发现新版本 %s! ...@@ -23,6 +23,7 @@ menu.update_label=发现新版本 %s!
file.open_action=打开文件... file.open_action=打开文件...
file.add_files_action=添加文件 file.add_files_action=添加文件
file.open_title=打开文件 file.open_title=打开文件
#file.open_project=Open project
file.new_project=新建项目 file.new_project=新建项目
file.save_project=保存项目 file.save_project=保存项目
file.save_project_as=另存项目为... file.save_project_as=另存项目为...
...@@ -35,6 +36,10 @@ file.export_gradle=另存为 Gradle 项目 ...@@ -35,6 +36,10 @@ file.export_gradle=另存为 Gradle 项目
file.save_all_msg=请选择保存反编译资源的目录 file.save_all_msg=请选择保存反编译资源的目录
file.exit=退出 file.exit=退出
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=源代码 tree.sources_title=源代码
tree.resources_title=资源文件 tree.resources_title=资源文件
tree.loading=加载中... tree.loading=加载中...
......
...@@ -23,6 +23,7 @@ menu.update_label=新版本 %s 可供下載! ...@@ -23,6 +23,7 @@ menu.update_label=新版本 %s 可供下載!
file.open_action=開啟檔案... file.open_action=開啟檔案...
file.add_files_action=新增檔案 file.add_files_action=新增檔案
file.open_title=開啟檔案 file.open_title=開啟檔案
#file.open_project=Open project
file.new_project=新建專案 file.new_project=新建專案
file.save_project=儲存專案 file.save_project=儲存專案
file.save_project_as=另存專案... file.save_project_as=另存專案...
...@@ -35,6 +36,10 @@ file.export_gradle=另存為 gradle 專案 ...@@ -35,6 +36,10 @@ file.export_gradle=另存為 gradle 專案
file.save_all_msg=選擇儲存反編譯原始碼的路徑 file.save_all_msg=選擇儲存反編譯原始碼的路徑
file.exit=離開 file.exit=離開
#start_page.title=Start page
#start_page.start=Start
#start_page.recent=Recent projects
tree.sources_title=原始碼 tree.sources_title=原始碼
tree.resources_title=資源 tree.resources_title=資源
tree.loading=載入中... tree.loading=載入中...
......
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M2 2H13V4V5H11V4H4V11H5V13H2V12V11V4V2Z" fill="#6E6E6E"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M14 6H6V14H14V6ZM12 8H8V12H12V8Z" fill="#6E6E6E"/>
</svg>
<!-- Copyright 2000-2021 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. -->
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16">
<g fill="none" fill-rule="evenodd">
<path fill="#6E6E6E" d="M9,13 L2,13 L2,5 L2,3 L6.60006714,3 L7.75640322,5 L14,5 L14,8 L11,8 L11,10 L9,10 L9,13 Z"/>
<rect width="2" height="6" x="12" y="9" fill="#6E6E6E"/>
<rect width="6" height="2" x="10" y="11" fill="#6E6E6E"/>
</g>
</svg>
<!-- Copyright 2000-2021 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. -->
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16">
<g fill="none" fill-rule="evenodd">
<path fill="#6E6E6E" d="M10,15 L10,10 L15,10 L15,15 L10,15 Z M11,14 L13,14 L13,13 L11,13 L11,14 Z"/>
<path fill="#6E6E6E" d="M14,9 L9,9 L9,13 L2,13 L2,5 L2,3 L6.60006714,3 L7.75640322,5 L14,5 L14,9 Z"/>
</g>
</svg>
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册