X-Git-Url: https://gerrit.simantics.org/r/gitweb?p=simantics%2Fplatform.git;a=blobdiff_plain;f=bundles%2Forg.simantics.diagram%2Fsrc%2Forg%2Fsimantics%2Fdiagram%2Fui%2FSWTPopupMenuParticipant.java;h=c489373b6a5b0391ea2e64b7f6ec8b22fd78731c;hp=770632143dedffbe0567534c43103f78392b82e1;hb=ec70c03d4ce3f68b71de5eeadce3d008620c5521;hpb=969bd23cab98a79ca9101af33334000879fb60c5 diff --git a/bundles/org.simantics.diagram/src/org/simantics/diagram/ui/SWTPopupMenuParticipant.java b/bundles/org.simantics.diagram/src/org/simantics/diagram/ui/SWTPopupMenuParticipant.java index 770632143..c489373b6 100644 --- a/bundles/org.simantics.diagram/src/org/simantics/diagram/ui/SWTPopupMenuParticipant.java +++ b/bundles/org.simantics.diagram/src/org/simantics/diagram/ui/SWTPopupMenuParticipant.java @@ -1,241 +1,236 @@ -/******************************************************************************* - * Copyright (c) 2007, 2010 Association for Decentralized Information Management - * in Industry THTH ry. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Eclipse Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/epl-v10.html - * - * Contributors: - * VTT Technical Research Centre of Finland - initial API and implementation - *******************************************************************************/ -package org.simantics.diagram.ui; - -import java.awt.geom.Point2D; - -import org.eclipse.jface.action.GroupMarker; -import org.eclipse.jface.action.IMenuListener2; -import org.eclipse.jface.action.IMenuManager; -import org.eclipse.jface.action.MenuManager; -import org.eclipse.swt.SWT; -import org.eclipse.swt.events.MenuAdapter; -import org.eclipse.swt.events.MenuEvent; -import org.eclipse.swt.events.MenuListener; -import org.eclipse.swt.graphics.Point; -import org.eclipse.swt.widgets.Control; -import org.eclipse.swt.widgets.Display; -import org.eclipse.swt.widgets.Event; -import org.eclipse.swt.widgets.Listener; -import org.eclipse.swt.widgets.Menu; -import org.eclipse.swt.widgets.Widget; -import org.eclipse.ui.IWorkbenchActionConstants; -import org.eclipse.ui.IWorkbenchPartSite; -import org.simantics.g2d.canvas.ICanvasContext; -import org.simantics.g2d.canvas.impl.AbstractCanvasParticipant; -import org.simantics.g2d.canvas.impl.DependencyReflection.Dependency; -import org.simantics.g2d.diagram.DiagramHints; -import org.simantics.g2d.participant.TransformUtil; -import org.simantics.scenegraph.g2d.events.EventHandlerReflection.EventHandler; -import org.simantics.scenegraph.g2d.events.command.CommandEvent; -import org.simantics.scenegraph.g2d.events.command.ShowPopup; -import org.simantics.utils.datastructures.hints.HintListenerAdapter; -import org.simantics.utils.datastructures.hints.IHintContext.Key; -import org.simantics.utils.datastructures.hints.IHintListener; -import org.simantics.utils.datastructures.hints.IHintObservable; - -/** - * A participant that initializes an SWT pop-up menu and registers it with the - * Eclipse workbench if a workbench site is provided. The client can specify the - * ID of the menu to create which allows the user to control contributions via - * Eclipse's declarative command mechanisms. - * - * @author Tuukka Lehtonen - */ -public class SWTPopupMenuParticipant extends AbstractCanvasParticipant { - - @Dependency - WorkbenchSelectionProvider wbsp; - @Dependency - TransformUtil trUtil; - - IWorkbenchPartSite site; - Control control; - Display display; - MenuManager menuManager; - String menuId; - - IHintListener popupListener = new HintListenerAdapter() { - @Override - public void hintChanged(IHintObservable sender, Key key, Object oldValue, Object newValue) { - if (key == DiagramHints.SHOW_POPUP_MENU) { - if (newValue != null) { - Control c = control; - if (display.isDisposed() || c == null || c.isDisposed()) - return; - - showPopup((Point2D) newValue); - } - } - } - }; - - IMenuListener2 menuManagerListener = new IMenuListener2() { - @Override - public void menuAboutToShow(IMenuManager manager) { - manager.add(new GroupMarker(IWorkbenchActionConstants.WB_START)); -// manager.add(new GroupMarker(IWorkbenchActionConstants.NEW_EXT)); -// manager.add(new GroupMarker(IWorkbenchActionConstants.IMPORT_EXT)); -// manager.add(new Separator(IWorkbenchActionConstants.MB_ADDITIONS)); -// manager.add(new GroupMarker(IWorkbenchActionConstants.WB_END)); - } - @Override - public void menuAboutToHide(IMenuManager manager) { - } - }; - - MenuListener menuListener = new MenuAdapter() { - @Override - public void menuShown(MenuEvent e) { - SWTPopupMenuParticipant.this.menuShown(e); - } - @Override - public void menuHidden(MenuEvent e) { - SWTPopupMenuParticipant.this.menuHidden(e); - } - }; - - protected void menuShown(MenuEvent e) { - asyncExec(new Runnable() { - @Override - public void run() { - final long time = System.currentTimeMillis(); - //System.out.println("popup shown: " + time); - setHint(DiagramHints.POPUP_MENU_SHOWN, time); - removeHint(DiagramHints.POPUP_MENU_HIDDEN); - - } - }); - } - - protected void menuHidden(MenuEvent e) { - asyncExec(new Runnable() { - @Override - public void run() { - final long time = System.currentTimeMillis(); - //System.out.println("popup closed: " + time); - removeHint(DiagramHints.POPUP_MENU_SHOWN); - setHint(DiagramHints.POPUP_MENU_HIDDEN, time); - } - }); - } - - /** - * NOTE: this constructor must currently be invoked from the SWT display - * thread. - * - * @param site - * @param control - * @param menuId - * @deprecated use {@link #SWTPopupMenuParticipant(IWorkbenchPartSite, Control, Display, String)} instead - */ - public SWTPopupMenuParticipant(IWorkbenchPartSite site, Control control, String menuId) { - this(site, control, control.getDisplay(), menuId); - } - - public SWTPopupMenuParticipant(IWorkbenchPartSite site, Control control, Display display, String menuId) { - super(); - this.site = site; - this.control = control; - this.display = display; - this.menuId = menuId; - control.addListener(SWT.Dispose, new Listener() { - - @Override - public void handleEvent(Event event) { - runDispose(); - } - - }); - } - - protected void runDispose() { - SWTPopupMenuParticipant.this.control = null; - if(menuManager != null) { - menuManager.removeAll(); - menuManager.dispose(); - menuManager = null; - } - } - - @Override - public void addedToContext(ICanvasContext ctx) { - super.addedToContext(ctx); - - display.asyncExec(new Runnable() { - @Override - public void run() { - createControl(); - } - }); - - getHintStack().addKeyHintListener(DiagramHints.SHOW_POPUP_MENU, popupListener); - } - - protected void createControl() { - if (control == null || control.isDisposed()) - return; - menuManager = createPopupMenu(); - if (menuManager != null) { - Menu menu = menuManager.createContextMenu(control); - menu.addMenuListener(menuListener); - control.setMenu(menu); - if (site != null) { - site.registerContextMenu(menuManager.getId(), menuManager, wbsp); - } - } - } - - @Override - public void removedFromContext(ICanvasContext ctx) { - getHintStack().removeKeyHintListener(DiagramHints.SHOW_POPUP_MENU, popupListener); - super.removedFromContext(ctx); - } - - protected MenuManager createPopupMenu() { - final MenuManager mm = new MenuManager("Canvas Popup", menuId); - mm.setRemoveAllWhenShown(true); - mm.addMenuListener(menuManagerListener); - return mm; - } - - @EventHandler(priority = 0) - public boolean handleCommands(CommandEvent e) { - if (e.command instanceof ShowPopup) { - showPopup(((ShowPopup) e.command).getControlPosition()); - return true; - } - return false; - } - - /** - * @param newValue - * @thread canvas-thread (AWT) - */ - protected void showPopup(Point2D newValue) { - final Point2D cp = (Point2D) newValue; - setHint(DiagramHints.POPUP_MENU_CONTROL_POSITION, cp); - setHint(DiagramHints.POPUP_MENU_CANVAS_POSITION, trUtil.controlToCanvas(cp, null)); - display.asyncExec(new Runnable() { - @Override - public void run() { - if (control == null || control.isDisposed()) - return; - - Point p = control.toDisplay((int) cp.getX(), (int) cp.getY()); - menuManager.getMenu().setLocation(p); - menuManager.getMenu().setVisible(true); - } - }); - } - -} +/******************************************************************************* + * Copyright (c) 2007, 2010 Association for Decentralized Information Management + * in Industry THTH ry. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * VTT Technical Research Centre of Finland - initial API and implementation + *******************************************************************************/ +package org.simantics.diagram.ui; + +import java.awt.geom.Point2D; + +import org.eclipse.jface.action.GroupMarker; +import org.eclipse.jface.action.IMenuListener2; +import org.eclipse.jface.action.IMenuManager; +import org.eclipse.jface.action.MenuManager; +import org.eclipse.swt.SWT; +import org.eclipse.swt.events.MenuAdapter; +import org.eclipse.swt.events.MenuEvent; +import org.eclipse.swt.events.MenuListener; +import org.eclipse.swt.graphics.Point; +import org.eclipse.swt.widgets.Control; +import org.eclipse.swt.widgets.Display; +import org.eclipse.swt.widgets.Event; +import org.eclipse.swt.widgets.Listener; +import org.eclipse.swt.widgets.Menu; +import org.eclipse.ui.IWorkbenchActionConstants; +import org.eclipse.ui.IWorkbenchPartSite; +import org.simantics.g2d.canvas.ICanvasContext; +import org.simantics.g2d.canvas.impl.AbstractCanvasParticipant; +import org.simantics.g2d.canvas.impl.DependencyReflection.Dependency; +import org.simantics.g2d.diagram.DiagramHints; +import org.simantics.g2d.participant.TransformUtil; +import org.simantics.scenegraph.g2d.events.EventHandlerReflection.EventHandler; +import org.simantics.scenegraph.g2d.events.command.CommandEvent; +import org.simantics.scenegraph.g2d.events.command.ShowPopup; +import org.simantics.utils.datastructures.hints.HintListenerAdapter; +import org.simantics.utils.datastructures.hints.IHintContext.Key; +import org.simantics.utils.datastructures.hints.IHintListener; +import org.simantics.utils.datastructures.hints.IHintObservable; +import org.simantics.utils.ui.SWTDPIUtil; + +/** + * A participant that initializes an SWT pop-up menu and registers it with the + * Eclipse workbench if a workbench site is provided. The client can specify the + * ID of the menu to create which allows the user to control contributions via + * Eclipse's declarative command mechanisms. + * + * @author Tuukka Lehtonen + */ +public class SWTPopupMenuParticipant extends AbstractCanvasParticipant { + + @Dependency + WorkbenchSelectionProvider wbsp; + @Dependency + TransformUtil trUtil; + + IWorkbenchPartSite site; + Control control; + Display display; + MenuManager menuManager; + String menuId; + + IHintListener popupListener = new HintListenerAdapter() { + @Override + public void hintChanged(IHintObservable sender, Key key, Object oldValue, Object newValue) { + if (key == DiagramHints.SHOW_POPUP_MENU) { + if (newValue != null) { + Control c = control; + if (display.isDisposed() || c == null || c.isDisposed()) + return; + + showPopup((Point2D) newValue); + } + } + } + }; + + IMenuListener2 menuManagerListener = new IMenuListener2() { + @Override + public void menuAboutToShow(IMenuManager manager) { + manager.add(new GroupMarker(IWorkbenchActionConstants.WB_START)); +// manager.add(new GroupMarker(IWorkbenchActionConstants.NEW_EXT)); +// manager.add(new GroupMarker(IWorkbenchActionConstants.IMPORT_EXT)); +// manager.add(new Separator(IWorkbenchActionConstants.MB_ADDITIONS)); +// manager.add(new GroupMarker(IWorkbenchActionConstants.WB_END)); + } + @Override + public void menuAboutToHide(IMenuManager manager) { + } + }; + + MenuListener menuListener = new MenuAdapter() { + @Override + public void menuShown(MenuEvent e) { + SWTPopupMenuParticipant.this.menuShown(e); + } + @Override + public void menuHidden(MenuEvent e) { + SWTPopupMenuParticipant.this.menuHidden(e); + } + }; + + protected void menuShown(MenuEvent e) { + asyncExec(new Runnable() { + @Override + public void run() { + final long time = System.currentTimeMillis(); + //System.out.println("popup shown: " + time); + setHint(DiagramHints.POPUP_MENU_SHOWN, time); + removeHint(DiagramHints.POPUP_MENU_HIDDEN); + + } + }); + } + + protected void menuHidden(MenuEvent e) { + asyncExec(new Runnable() { + @Override + public void run() { + final long time = System.currentTimeMillis(); + //System.out.println("popup closed: " + time); + removeHint(DiagramHints.POPUP_MENU_SHOWN); + setHint(DiagramHints.POPUP_MENU_HIDDEN, time); + } + }); + } + + /** + * NOTE: this constructor must currently be invoked from the SWT display + * thread. + * + * @param site + * @param control + * @param menuId + * @deprecated use {@link #SWTPopupMenuParticipant(IWorkbenchPartSite, Control, Display, String)} instead + */ + public SWTPopupMenuParticipant(IWorkbenchPartSite site, Control control, String menuId) { + this(site, control, control.getDisplay(), menuId); + } + + public SWTPopupMenuParticipant(IWorkbenchPartSite site, Control control, Display display, String menuId) { + super(); + this.site = site; + this.control = control; + this.display = display; + this.menuId = menuId; + control.addListener(SWT.Dispose, new Listener() { + + @Override + public void handleEvent(Event event) { + runDispose(); + } + + }); + } + + protected void runDispose() { + SWTPopupMenuParticipant.this.control = null; + if(menuManager != null) { + menuManager.removeAll(); + menuManager.dispose(); + menuManager = null; + } + } + + @Override + public void addedToContext(ICanvasContext ctx) { + super.addedToContext(ctx); + + display.asyncExec(new Runnable() { + @Override + public void run() { + createControl(); + } + }); + + getHintStack().addKeyHintListener(DiagramHints.SHOW_POPUP_MENU, popupListener); + } + + protected void createControl() { + if (control == null || control.isDisposed()) + return; + menuManager = createPopupMenu(); + if (menuManager != null) { + Menu menu = menuManager.createContextMenu(control); + menu.addMenuListener(menuListener); + control.setMenu(menu); + if (site != null) { + site.registerContextMenu(menuManager.getId(), menuManager, wbsp); + } + } + } + + @Override + public void removedFromContext(ICanvasContext ctx) { + getHintStack().removeKeyHintListener(DiagramHints.SHOW_POPUP_MENU, popupListener); + super.removedFromContext(ctx); + } + + protected MenuManager createPopupMenu() { + final MenuManager mm = new MenuManager("Canvas Popup", menuId); + mm.setRemoveAllWhenShown(true); + mm.addMenuListener(menuManagerListener); + return mm; + } + + @EventHandler(priority = 0) + public boolean handleCommands(CommandEvent e) { + if (e.command instanceof ShowPopup) { + showPopup(((ShowPopup) e.command).getControlPosition()); + return true; + } + return false; + } + + /** + * @param newValue + * @thread canvas-thread (AWT) + */ + protected void showPopup(Point2D cp) { + setHint(DiagramHints.POPUP_MENU_CONTROL_POSITION, cp); + setHint(DiagramHints.POPUP_MENU_CANVAS_POSITION, trUtil.controlToCanvas(cp, null)); + display.asyncExec(() -> { + if (control == null || control.isDisposed()) + return; + Point p = control.toDisplay( SWTDPIUtil.downscaleSwtToInteger(cp) ); + menuManager.getMenu().setLocation(p); + menuManager.getMenu().setVisible(true); + }); + } + +}