diff --git a/Ghidra/Features/Base/certification.manifest b/Ghidra/Features/Base/certification.manifest index 11ab2393b2..d35661f6a9 100644 --- a/Ghidra/Features/Base/certification.manifest +++ b/Ghidra/Features/Base/certification.manifest @@ -16,6 +16,7 @@ data/ElfFunctionsThatDoNotReturn||GHIDRA||||END| data/ExtensionPoint.manifest||GHIDRA||||END| data/MachOFunctionsThatDoNotReturn||GHIDRA||||END| data/PEFunctionsThatDoNotReturn||GHIDRA||||END| +data/base.file.extensions.icons.theme.properties||GHIDRA||||END| data/base.icons.theme.properties||GHIDRA||||END| data/base.listing.theme.properties||GHIDRA||||END| data/base.programgraph.theme.properties||GHIDRA||||END| @@ -80,7 +81,6 @@ data/symbols/win64/mfc80u.exports||GHIDRA||||END| data/symbols/win64/mfc90.exports||GHIDRA||||END| data/symbols/win64/mfc90u.exports||GHIDRA||||END| data/symbols/win64/msvcrt.hints||GHIDRA||||END| -data/typeinfo/base.file.extensions.icons.theme.properties||GHIDRA||||END| data/typeinfo/generic/generic_clib.gdt||GHIDRA||||END| data/typeinfo/generic/generic_clib_64.gdt||GHIDRA||||END| data/typeinfo/mac_10.9/mac_osx.gdt||GHIDRA||||END| diff --git a/Ghidra/Features/Base/data/typeinfo/base.file.extensions.icons.theme.properties b/Ghidra/Features/Base/data/base.file.extensions.icons.theme.properties similarity index 100% rename from Ghidra/Features/Base/data/typeinfo/base.file.extensions.icons.theme.properties rename to Ghidra/Features/Base/data/base.file.extensions.icons.theme.properties diff --git a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeFontTable.java b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeFontTable.java index 0b36688696..cad35de85e 100644 --- a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeFontTable.java +++ b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeFontTable.java @@ -108,10 +108,7 @@ public class ThemeFontTable extends JPanel implements ActionContextProvider { @Override public ActionContext getActionContext(MouseEvent e) { - if (e == null) { - return null; - } - if (e.getSource() == table) { + if (e != null && e.getSource() == table) { FontValue currentValue = filterTable.getSelectedRowObject(); if (currentValue == null) { return null; diff --git a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeIconTable.java b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeIconTable.java index 0514c902b7..15ff8f6e02 100644 --- a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeIconTable.java +++ b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeIconTable.java @@ -104,7 +104,7 @@ public class ThemeIconTable extends JPanel implements ActionContextProvider { @Override public ActionContext getActionContext(MouseEvent e) { - if (e.getSource() == table) { + if (e != null && e.getSource() == table) { IconValue currentValue = filterTable.getSelectedRowObject(); if (currentValue == null) { return null; diff --git a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeUtils.java b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeUtils.java index 0b3dcef9d9..e90f530530 100644 --- a/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeUtils.java +++ b/Ghidra/Framework/Docking/src/main/java/docking/theme/gui/ThemeUtils.java @@ -215,6 +215,9 @@ public class ThemeUtils { private static boolean saveCurrentValues(ThemeManager themeManager, String themeName) { GTheme activeTheme = themeManager.getActiveTheme(); File file = getSaveFile(themeName); + if (!file.exists()) { + Msg.info(ThemeUtils.class, "Saving theme to " + file); + } GTheme newTheme = new GTheme(file, themeName, activeTheme.getLookAndFeelType(), activeTheme.useDarkDefaults()); diff --git a/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeFileLoader.java b/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeFileLoader.java index 0489086416..88eb1d3603 100644 --- a/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeFileLoader.java +++ b/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeFileLoader.java @@ -44,7 +44,6 @@ public class ThemeFileLoader { Application.findFilesByExtensionInApplication(".theme.properties"); for (ResourceFile resourceFile : themeDefaultFiles) { - Msg.debug(this, "found theme file: " + resourceFile.getAbsolutePath()); try { ThemePropertyFileReader reader = new ThemePropertyFileReader(resourceFile); defaults.load(reader.getDefaultValues()); diff --git a/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeValue.java b/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeValue.java index 5d45bcd1dc..674e6d33f5 100644 --- a/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeValue.java +++ b/Ghidra/Framework/Generic/src/main/java/generic/theme/ThemeValue.java @@ -93,7 +93,7 @@ public abstract class ThemeValue implements Comparable> { // loop resolving indirect references while (referred != null) { if (referred.value != null) { - return referred.value; + return referred.get(values); } visitedKeys.add(referred.id); if (visitedKeys.contains(referred.referenceId)) { diff --git a/Ghidra/Framework/Generic/src/test/java/generic/theme/IconValueTest.java b/Ghidra/Framework/Generic/src/test/java/generic/theme/IconValueTest.java index 807365905a..8e9dac00c9 100644 --- a/Ghidra/Framework/Generic/src/test/java/generic/theme/IconValueTest.java +++ b/Ghidra/Framework/Generic/src/test/java/generic/theme/IconValueTest.java @@ -123,6 +123,30 @@ public class IconValueTest { @Test public void testParseWithOverlays() throws ParseException { + IconValue value = IconValue.parse("icon.foo", "EMPTY_ICON{Plus2.png}"); + values.addIcon(value); + value = IconValue.parse("icon.test", + "images/core.png[size(25,25)]{icon.foo[move(4,4)]}"); + + assertEquals("icon.test", value.getId()); + Icon icon = value.get(values); + + assertTrue(icon instanceof MultiIcon); + MultiIcon multiIcon = (MultiIcon) icon; + Icon[] icons = multiIcon.getIcons(); + assertEquals(2, icons.length); + assertEquals(25, icons[0].getIconWidth()); + assertEquals(25, icons[0].getIconWidth()); + assertEquals(16, icons[1].getIconWidth()); + assertEquals(16, icons[1].getIconWidth()); + assertTrue(icons[1] instanceof TranslateIcon); + TranslateIcon tIcon = (TranslateIcon) icons[1]; + Icon baseIcon = tIcon.getBaseIcon(); + assertTrue(baseIcon instanceof MultiIcon); + } + + @Test + public void testParseWithModifiedOverlay() throws ParseException { IconValue value = IconValue.parse("icon.test", "images/core.png[size(25,25)]{images/flag.png[size(8,8)][move(4,4)]}"); assertEquals("icon.test", value.getId());