I´ve created a TreeView with a ContentProvider and custom tree elements.
I also have a ISelectionChangedListener added to the TreeView.
I want to add an MouseListener, do detect if an element of the tree is right-clicked and show a popup menu.
If the white area around the tree is clicked, i don´t want to display the popup menu.
The menu is added via Extensions in the plugin.xml.
How can I now evaluate if a tree element is right-clicked, so I can show the popup menu (maybe with visibleWhen in the plugin.xml) ?
I also want to clear the selection, if the right-click is detected in the white area of the TreeView.
Ok, i did not realized that i can still use tree.getItem(...).
So here is my full MouseListener:
treeOPCUA.addMouseListener(new MouseListener()
{
#Override
public void mouseUp(MouseEvent e)
{
if(e.button == 3 && rightMouseClicked == true)
rightMouseClicked = false;
}
#Override
public void mouseDown(MouseEvent e)
{
if(e.button == 3 && rightMouseClicked == false)
rightMouseClicked = true;
if(treeOPCUA.getItem(new Point(e.x, e.y)) == null)
viewer.setSelection(null);
}
#Override
public void mouseDoubleClick(MouseEvent e)
{
viewer.setExpandedState(e.getSource(), true);
}
});
With the boolean variable "rightMouseClicked" I detect in my ISelectionChangedListener if the right mouse is clicked:
if(event.getSelection() instanceof IStructuredSelection && !rightMouseClicked)
I hope this answer helps anyone.
Related
When space is limited, the tabs get shown in a scroll pane, and two small arrow buttons appear. I would like to use the mouse wheel to operate these buttons.
There is a nice solution in Use mouse to scroll through tabs in JTabbedPane, but it actually selects the tabs. I only want to scroll them, without changing the selection.
How do I get these bottons or related actions?
(I am using the Nimbus LaF, if that is important.)
just found it!
The drag-and-drop code in DnDTabbedPane at https://java-swing-tips.blogspot.co.at/2008/04/drag-and-drop-tabs-in-jtabbedpane.html has this very nice method:
private void clickArrowButton(String actionKey) {
ActionMap map = getActionMap();
if (map != null) {
Action action = map.get(actionKey);
if (action != null && action.isEnabled()) {
action.actionPerformed(new ActionEvent(
this, ActionEvent.ACTION_PERFORMED, null, 0, 0));
}
}
}
and so I just need to say:
addMouseWheelListener(new MouseWheelListener() {
#Override
public void mouseWheelMoved(MouseWheelEvent e) {
if (e.getWheelRotation() > 0) {
clickArrowButton("scrollTabsBackwardAction");
} else {
clickArrowButton("scrollTabsForwardAction");
}
}
});
I need to find out whether the cursor is inside my tree (tree extends org.eclipse.ui.EditorPart) or somewhere else in the Eclipse workbench.
So I have tried this code:
tree.addMouseMoveListener(new MouseMoveListener() {
#Override
public void mouseMove(MouseEvent e) {
boolean mouseIsInEditor = tree.getClientArea().contains(new Point(e.x, e.y));
if (mouseIsInEditor) {
System.out.println("IS IN EDITOR");
} else {
System.out.println("NOT IN EDITOR");
}
}
});
}
But it won't even run the code as long as the mouse is outside of my tree, so mouseIsInEditor will always be true.
Add a MouseTrackListener listener to your tree:
tree.addMouseTrackListener(listener);
This has mouseEnter method called when the mouse enters your control, mouseExit called when the mouse leaves the control and mouseHover when the mouse hovers over some part of the control.
WorldWind LayerTree uses checkboxes for default configuration. Is there any way to change checkboxes to radio-buttons?
Screenshot
I could not find any solution for replacing check boxes with radio-buttons. So, I decided to try another approach and it works for me. I catch the property change event of LayerTree and reset the selected nodes other than the newly selected one.
LayerTree layerTree = new LayerTree();
layerTree.addPropertyChangeListener(new PropertyChangeListener(){
#Override
public void propertyChange(PropertyChangeEvent evt) {
for (Iterator<TreeNode> treeNode = layerTree.getModel().getRoot().getChildren().iterator(); treeNode.hasNext(); ) {
LayerTreeNode layerTreeNode = LayerTreeNode.class.cast(treeNode.next());
if(evt.getSource() instanceof LayerTreeNode && evt.getSource() != layerTreeNode)
layerTreeNode.setSelected(false);
}
}
});
here is my problem:
I have a jList and a popup menu. When I right click the jList, the popup menu shows. The problem is that the jList item which the mouse is pointing at won't select.
And I want it to do that. When I point my cursor at an item in the list and press the right button, I want two things to happen. Select the item on which I clicked and show the popup menu.
I tried this:
jLists.addMouseListener(new MouseAdapter() {
#Override
public void mousePressed(MouseEvent e) {
jList.setSelectedIndex(jList.locationToIndex(e.getPoint()));
}
});
jList.setComponentPopupMenu(jPopupMenu);
But it only shows the popup menu.
If I delete this line:
jList.setComponentPopupMenu(jPopupMenu);
then the right-click select works (but the popup menu doesn't show).
So, what do you think is the best way to make these two functions (both) work ?
Thanks and sorry for my english.
Don't do setComponentPopupMenu. In the MouseAdapter do the following:
public void mousePressed(MouseEvent e) {check(e);}
public void mouseReleased(MouseEvent e) {check(e);}
public void check(MouseEvent e) {
if (e.isPopupTrigger()) { //if the event shows the menu
jList.setSelectedIndex(jList.locationToIndex(e.getPoint())); //select the item
jPopupMenu.show(jList, e.getX(), e.getY()); //and show the menu
}
}
This should work.
EDIT: The code now checks both press and release events, because some platforms show popups when mouse presses and some other on release. See the Swing tutorial for more info.
If you want to continue to use setComponentPopupMenu (which is nice because it handles mouse and keyboard invocations of the popup in a cross platform way), you could override JPopupMenu.show(Component, int, int) to select the appropriate row.
JPopupMenu jPopupMenu = new JPopupMenu() {
#Override
public void show(Component invoker, int x, int y) {
int row = jList.locationToIndex(new Point(x, y));
if (row != -1) {
jList.setSelectedIndex(row);
}
super.show(invoker, x, y);
}
};
jList.setComponentPopupMenu(jPopupMenu);
Note that when your popup is invoked via the keyboard (and you don't also override getPopupLocation on your target component), the x, y location you get in JPopupMenu.show will be the midpoint of your component. If there's already a selection in this case you probably don't want to change the selection.
The solution I came up with to solve the keyboard vs. mouse invocation problem was to set a client property on the component in an override of getPopupLocation and then check it when showing the popup. The argument to getPopupLocation will be null when invoked via the keyboard. Here's the core code (perhaps implemented in a utility class available to your component and its popup menu).
private static final String POPUP_TRIGGERED_BY_MOUSE_EVENT = "popupTriggeredByMouseEvent"; // NOI18N
public static Point getPopupLocation(JComponent invoker, MouseEvent event)
{
boolean popupTriggeredByMouseEvent = event != null;
invoker.putClientProperty(POPUP_TRIGGERED_BY_MOUSE_EVENT, Boolean.valueOf(popupTriggeredByMouseEvent));
if (popupTriggeredByMouseEvent)
{
return event.getPoint();
}
return invoker.getMousePosition();
}
public static boolean isPopupTriggeredByMouseEvent(JComponent invoker)
{
return Boolean.TRUE.equals(invoker.getClientProperty(POPUP_TRIGGERED_BY_MOUSE_EVENT));
}
Then override getPopupLocation in your component:
#Override
public Point getPopupLocation(MouseEvent event)
{
return PopupMenuUtils.getPopupLocation(this, event);
}
and call isPopupTriggeredByMouseEvent in an override of JPopupMenu.show to determine whether or not to select the row at the popup location (or whatever action may make sense for the underlying component):
JPopupMenu jPopupMenu = new JPopupMenu() {
#Override
public void show(Component invoker, int x, int y) {
int row = jList.locationToIndex(new Point(x, y));
if (row != -1 && PopupMenuUtils.isPopupTriggeredByMouseEvent((JComponent) invoker)) {
jList.setSelectedIndex(row);
}
super.show(invoker, x, y);
}
};
Hiho,
currently I have a working popup menu which appears when I click on a treeview item.
But I want to show different popups for different tree view entries. I don't get a idea how to do so...
Here is my code for creating the menu:
MenuManager menuMgr = new MenuManager("#PopupMenu");
menuMgr.setRemoveAllWhenShown(true);
menuMgr.addMenuListener(new IMenuListener() {
#Override
public void menuAboutToShow(IMenuManager manager) {
Action action = new Action() {
public void run() {
// So something
}
};
action.setText("Set as working file");
manager.add(action);
}
});
Menu menu = menuMgr.createContextMenu(getTree());
getTree().setMenu(menu);
You should propably use a MouseListener on the tree:
final Tree tree = new Tree(parent, ...);
tree.addMouseListener(new MouseAdapter() {
#override
public void mouseDown(MouseEvent me) {
if(tree.getSelection() instanceof MySpecificTreeNode) {
// create menu...
}
}
});
Two ideas. For both you need to listen to selections on the TreeView, because that's the only way to determine which Menu (or special content) you want to show.
Then you could either set the correct menu to the the tree right after you know which one to use or contribute the needed items to the existing menu (that's how it's done in the eclipse framework).