mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-05-25 03:06:14 +08:00
Merge remote-tracking branch 'origin/GP-2841-dragonmacher-program-name-tooltips--SQUASHED'
This commit is contained in:
+17
-22
@@ -35,7 +35,7 @@ import ghidra.util.layout.HorizontalLayout;
|
||||
import resources.Icons;
|
||||
|
||||
/**
|
||||
* Panel to show a "tab" for an object. ChangeListeners are notified when a tab is selected.
|
||||
* Panel to show a "tab" for an object. ChangeListeners are notified when a tab is selected.
|
||||
*/
|
||||
public class MultiTabPanel extends JPanel {
|
||||
private static final String FONT_TABS_ID = "font.plugin.tabs";
|
||||
@@ -49,17 +49,13 @@ public class MultiTabPanel extends JPanel {
|
||||
private final static Icon HIGHLIGHT_CLOSE_ICON = new GIcon("icon.plugin.programmanager.close.highlight");
|
||||
private final static Icon LIST_ICON = new GIcon("icon.plugin.programmanager.list");
|
||||
private final static Icon TRANSIENT_ICON = new GIcon("icon.plugin.programmanager.transient");
|
||||
//@formatter:on
|
||||
|
||||
private final static Color TEXT_SELECTION_COLOR =
|
||||
new GColor("color.fg.listing.tabs.text.selected");
|
||||
private final static Color TEXT_NON_SELECTION_COLOR =
|
||||
new GColor("color.fg.listing.tabs.text.unselected");
|
||||
private final static Color TEXT_SELECTION_COLOR = new GColor("color.fg.listing.tabs.text.selected");
|
||||
private final static Color TEXT_NON_SELECTION_COLOR = new GColor("color.fg.listing.tabs.text.unselected");
|
||||
private final static Color BG_SELECTION_COLOR = SELECTED_TAB_COLOR;
|
||||
private final static Color BG_NON_SELECTION_COLOR =
|
||||
new GColor("color.bg.listing.tabs.unselected");
|
||||
private static final Color BG_COLOR_MORE_TABS_HOVER =
|
||||
new GColor("color.bg.listing.tabs.more.tabs.hover");
|
||||
private final static Color BG_NON_SELECTION_COLOR = new GColor("color.bg.listing.tabs.unselected");
|
||||
private static final Color BG_COLOR_MORE_TABS_HOVER = new GColor("color.bg.listing.tabs.more.tabs.hover");
|
||||
//@formatter:on
|
||||
|
||||
private static final String DEFAULT_HIDDEN_COUNT_STR = "99";
|
||||
|
||||
@@ -85,7 +81,6 @@ public class MultiTabPanel extends JPanel {
|
||||
private boolean ignoreFocus;
|
||||
|
||||
MultiTabPanel(MultiTabPlugin multiTabPlugin) {
|
||||
super();
|
||||
this.multiTabPlugin = multiTabPlugin;
|
||||
setLayout(new HorizontalLayout(0));
|
||||
|
||||
@@ -145,7 +140,7 @@ public class MultiTabPanel extends JPanel {
|
||||
}
|
||||
|
||||
/**
|
||||
* Refresh label displayed in the tab for the given object.
|
||||
* Refresh label displayed in the tab for the given object.
|
||||
* @param program object associated with a tab
|
||||
*/
|
||||
void refresh(Program program) {
|
||||
@@ -555,8 +550,8 @@ public class MultiTabPanel extends JPanel {
|
||||
newVisibleTabList.add(panel);
|
||||
}
|
||||
|
||||
// check for the boundary condition where all elements would fit in the display if we
|
||||
// don't show the label indicating tabs are hidden. The boundary case is when there
|
||||
// check for the boundary condition where all elements would fit in the display if we
|
||||
// don't show the label indicating tabs are hidden. The boundary case is when there
|
||||
// is only one hidden element that could potentially be put into the view
|
||||
if (allTabsList.size() - newVisibleTabList.size() == 1) {
|
||||
TabPanel lastPanel = allTabsList.get(allTabsList.size() - 1);
|
||||
@@ -599,7 +594,7 @@ public class MultiTabPanel extends JPanel {
|
||||
usedWidth += panel.getPreferredSize().width;
|
||||
}
|
||||
|
||||
// remove items from the end of the visible list until we have room for the current tab
|
||||
// remove items from the end of the visible list until we have room for the current tab
|
||||
for (int i = newVisibleTabList.size() - 1; i >= 0; i--) {
|
||||
TabPanel lastPanel = newVisibleTabList.remove(i);
|
||||
int width = lastPanel.getPreferredSize().width;
|
||||
@@ -790,7 +785,7 @@ public class MultiTabPanel extends JPanel {
|
||||
list.addFocusListener(new FocusAdapter() {
|
||||
@Override
|
||||
public void focusLost(FocusEvent focusEvent) {
|
||||
// close the window when the user focuses another component
|
||||
// close the window when the user focuses another component
|
||||
if (focusEvent.getOppositeComponent() != filterField) {
|
||||
hideListWindowDueToFocusChange();
|
||||
}
|
||||
@@ -912,7 +907,7 @@ public class MultiTabPanel extends JPanel {
|
||||
|
||||
//==================================================================================================
|
||||
// Inner Classes
|
||||
//==================================================================================================
|
||||
//==================================================================================================
|
||||
|
||||
private class TabPanel extends JPanel {
|
||||
private Color defaultBgColor;
|
||||
@@ -963,7 +958,7 @@ public class MultiTabPanel extends JPanel {
|
||||
}
|
||||
}
|
||||
|
||||
// a panel that paints below it's bounds in order to connect the panel and the border
|
||||
// a panel that paints below it's bounds in order to connect the panel and the border
|
||||
// below it visually
|
||||
private class SelectedPanel extends TabPanel {
|
||||
private SelectedPanel(Color backgroundColor, Program program, JLabel nameLabel,
|
||||
@@ -1005,8 +1000,8 @@ public class MultiTabPanel extends JPanel {
|
||||
}
|
||||
}
|
||||
|
||||
// This class doesn't paint the bottom border in order to make the object appear to be
|
||||
// connected to the component below. This class also paints its side borders below its
|
||||
// This class doesn't paint the bottom border in order to make the object appear to be
|
||||
// connected to the component below. This class also paints its side borders below its
|
||||
// bounds for the same reason.
|
||||
class BottomlessBevelBorder extends BevelBorder {
|
||||
public BottomlessBevelBorder() {
|
||||
@@ -1014,7 +1009,7 @@ public class MultiTabPanel extends JPanel {
|
||||
}
|
||||
|
||||
@Override
|
||||
// overridden to reduce the space below, since there is no component
|
||||
// overridden to reduce the space below, since there is no component
|
||||
public Insets getBorderInsets(Component c) {
|
||||
Insets borderInsets = super.getBorderInsets(c);
|
||||
borderInsets.bottom = 0;
|
||||
@@ -1079,7 +1074,7 @@ public class MultiTabPanel extends JPanel {
|
||||
g.setColor(getHighlightOuterColor(c));
|
||||
g.drawLine(0, h - 1, w - 1, h - 1);
|
||||
|
||||
// bottom inner
|
||||
// bottom inner
|
||||
g.setColor(getShadowInnerColor(c));
|
||||
|
||||
g.translate(-x, -y);
|
||||
|
||||
+33
-12
@@ -58,7 +58,7 @@ public class MultiTabPlugin extends Plugin implements DomainObjectListener {
|
||||
// Unusual Code Alert!: We can't initialize these in the fields above because calling
|
||||
// DockingUtils calls into Swing code. Further, we don't want Swing code being accessed
|
||||
// when the Plugin classes are loaded, as they get loaded in the headless environment.
|
||||
//
|
||||
//
|
||||
private final KeyStroke NEXT_TAB_KEYSTROKE =
|
||||
KeyStroke.getKeyStroke(KeyEvent.VK_F9, DockingUtils.CONTROL_KEY_MODIFIER_MASK);
|
||||
private final KeyStroke PREVIOUS_TAB_KEYSTROKE =
|
||||
@@ -96,14 +96,14 @@ public class MultiTabPlugin extends Plugin implements DomainObjectListener {
|
||||
goToProgramAction.setMenuBarData(
|
||||
new MenuData(new String[] { ToolConstants.MENU_NAVIGATION, "Go To Program..." }, null,
|
||||
ToolConstants.MENU_NAVIGATION_GROUP_WINDOWS, MenuData.NO_MNEMONIC, firstGroup));
|
||||
goToProgramAction.setKeyBindingData(
|
||||
new KeyBindingData(KeyEvent.VK_F7, InputEvent.CTRL_DOWN_MASK));
|
||||
goToProgramAction
|
||||
.setKeyBindingData(new KeyBindingData(KeyEvent.VK_F7, InputEvent.CTRL_DOWN_MASK));
|
||||
|
||||
goToProgramAction.setEnabled(false);
|
||||
goToProgramAction.setDescription(
|
||||
"Shows the program selection dialog with the current program selected");
|
||||
goToProgramAction.setHelpLocation(
|
||||
new HelpLocation("ProgramManagerPlugin", "Go_To_Program"));
|
||||
goToProgramAction
|
||||
.setHelpLocation(new HelpLocation("ProgramManagerPlugin", "Go_To_Program"));
|
||||
|
||||
goToNextProgramAction = new DockingAction("Go To Next Program", getName()) {
|
||||
@Override
|
||||
@@ -133,7 +133,7 @@ public class MultiTabPlugin extends Plugin implements DomainObjectListener {
|
||||
goToPreviousProgramAction.setHelpLocation(
|
||||
new HelpLocation("ProgramManagerPlugin", "Go_To_Next_And_Previous_Program"));
|
||||
|
||||
// this timer is to give the user time to select successive programs before activating one
|
||||
// this timer is to give the user time to select successive programs before activating one
|
||||
selectHighlightedProgramTimer = new Timer(750, e -> selectHighlightedProgram());
|
||||
selectHighlightedProgramTimer.setRepeats(false);
|
||||
|
||||
@@ -146,11 +146,11 @@ public class MultiTabPlugin extends Plugin implements DomainObjectListener {
|
||||
goToLastActiveProgramAction.setMenuBarData(new MenuData(
|
||||
new String[] { ToolConstants.MENU_NAVIGATION, "Go To Last Active Program" }, null,
|
||||
ToolConstants.MENU_NAVIGATION_GROUP_WINDOWS, MenuData.NO_MNEMONIC, secondGroup));
|
||||
goToLastActiveProgramAction.setKeyBindingData(
|
||||
new KeyBindingData(KeyEvent.VK_F6, InputEvent.CTRL_DOWN_MASK));
|
||||
goToLastActiveProgramAction
|
||||
.setKeyBindingData(new KeyBindingData(KeyEvent.VK_F6, InputEvent.CTRL_DOWN_MASK));
|
||||
goToLastActiveProgramAction.setEnabled(false);
|
||||
goToLastActiveProgramAction.setDescription(
|
||||
"Activates the last program used before the current program");
|
||||
goToLastActiveProgramAction
|
||||
.setDescription("Activates the last program used before the current program");
|
||||
goToLastActiveProgramAction.setHelpLocation(
|
||||
new HelpLocation("ProgramManagerPlugin", "Go_To_Last_Active_Program"));
|
||||
|
||||
@@ -192,10 +192,31 @@ public class MultiTabPlugin extends Plugin implements DomainObjectListener {
|
||||
String getStringUsedInList(Program program) {
|
||||
DomainFile df = program.getDomainFile();
|
||||
String changeIndicator = program.isChanged() ? "*" : "";
|
||||
String pathString = getShortPath(df);
|
||||
if (!df.isInWritableProject()) {
|
||||
return df.toString() + " [Read-Only]" + changeIndicator;
|
||||
return pathString + " [Read-Only]" + changeIndicator;
|
||||
}
|
||||
return df.toString() + changeIndicator;
|
||||
return pathString + changeIndicator;
|
||||
}
|
||||
|
||||
private String getShortPath(DomainFile df) {
|
||||
String pathString = df.toString();
|
||||
int length = pathString.length();
|
||||
if (length < 100) {
|
||||
return pathString;
|
||||
}
|
||||
|
||||
String[] pathParts = pathString.split("/");
|
||||
if (pathParts.length == 2) { // at least 2 for project name and filename
|
||||
return pathString;
|
||||
}
|
||||
|
||||
String projectName = df.getProjectLocator().getName();
|
||||
int parentFolderIndex = pathParts.length - 2;
|
||||
String parentName = pathParts[parentFolderIndex];
|
||||
String filename = df.getName();
|
||||
pathString = projectName + ":/.../" + parentName + "/" + filename;
|
||||
return pathString;
|
||||
}
|
||||
|
||||
String getToolTip(Program program) {
|
||||
|
||||
Reference in New Issue
Block a user