Select components from context menu even when they are under other components

This commit is contained in:
bancika
2012-02-12 14:36:18 +00:00
parent 616b09b4b2
commit ebf06841a0
12 changed files with 181 additions and 100 deletions
@@ -0,0 +1,68 @@
package org.diylc.common;
import java.awt.Point;
public interface IMouseProcessor {
/**
* Notifies the presenter that mouse is clicked.
*
* Note: point coordinates are display based, i.e. scaled for zoom factor.
*
* @param point
* @param ctrlDown
* @param shiftDown
* @param altDown
* @param clickCount
*/
void mouseClicked(Point point, boolean ctrlDown, boolean shiftDown, boolean altDown,
int clickCount);
/**
* Notifies the presenter that mouse is moved.
*
* Note: point coordinates are display based, i.e. scaled for zoom factor.
*
* @param point
* @param ctrlDown
* @param shiftDown
* @param altDown
*/
void mouseMoved(Point point, boolean ctrlDown, boolean shiftDown, boolean altDown);
/**
* Notification that drag has been started from the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
* @param dragAction
*/
void dragStarted(Point point, int dragAction);
/**
* Checks if it's possible to drop over the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
* @return
*/
boolean dragOver(Point point);
/**
* Changes the current drag action during the dragging.
*
* @param dragAction
*/
void dragActionChanged(int dragAction);
/**
* Notification that drag has been ended in the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
*/
void dragEnded(Point point);
}
@@ -4,7 +4,6 @@ import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.dnd.DnDConstants;
import java.awt.geom.Point2D;
import java.util.List;
import java.util.Map;
@@ -29,7 +28,7 @@ import org.diylc.core.Theme;
* @see IMessageListener
* @see EventType
*/
public interface IPlugInPort {
public interface IPlugInPort extends ISelectionProcessor, IMouseProcessor {
public static final String ANTI_ALIASING_KEY = "antiAliasing";
public static final String HI_QUALITY_RENDER_KEY = "hiQualityRender";
@@ -45,7 +44,7 @@ public interface IPlugInPort {
public static final String OUTLINE_KEY = "outline";
public static final String THEME_KEY = "theme";
public static final String RECENT_COMPONENTS_KEY = "recentComponents";
public static final int DND_TOGGLE_STICKY = 0x1;
public static final int DND_TOGGLE_SNAP = 0x40000000;
@@ -163,89 +162,6 @@ public interface IPlugInPort {
*/
void setZoomLevel(double zoomLevel);
/**
* Notifies the presenter that mouse is clicked.
*
* Note: point coordinates are display based, i.e. scaled for zoom factor.
*
* @param point
* @param ctrlDown
* @param shiftDown
* @param altDown
* @param clickCount
*/
void mouseClicked(Point point, boolean ctrlDown, boolean shiftDown, boolean altDown,
int clickCount);
/**
* Notifies the presenter that mouse is moved.
*
* Note: point coordinates are display based, i.e. scaled for zoom factor.
*
* @param point
* @param ctrlDown
* @param shiftDown
* @param altDown
*/
void mouseMoved(Point point, boolean ctrlDown, boolean shiftDown, boolean altDown);
/**
* Returns the current {@link ComponentTransferable}.
*
* @return
*/
List<IDIYComponent<?>> getSelectedComponents();
/**
* Updates the selection with the specified list of component. Also, updates
* control point map with all components that are stuck to the newly
* selected components.
*
* @param newSelection
*/
void updateSelection(List<IDIYComponent<?>> newSelection);
/**
* Selects all components in the project.
*/
void selectAll();
/**
* Notification that drag has been started from the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
* @param dragAction
*/
void dragStarted(Point point, int dragAction);
/**
* Checks if it's possible to drop over the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
* @return
*/
boolean dragOver(Point point);
/**
* Changes the current drag action during the dragging.
*
* @param dragAction
*/
void dragActionChanged(int dragAction);
/**
* Notification that drag has been ended in the specified point.
*
* Note: point coordinates are scaled for zoom factor.
*
* @param point
*/
void dragEnded(Point point);
/**
* Returns current version number.
*
@@ -0,0 +1,39 @@
package org.diylc.common;
import java.awt.Point;
import java.util.List;
import org.diylc.core.IDIYComponent;
public interface ISelectionProcessor {
/**
* Returns the current {@link ComponentTransferable}.
*
* @return
*/
List<IDIYComponent<?>> getSelectedComponents();
/**
* Updates the selection with the specified list of component. Also, updates
* control point map with all components that are stuck to the newly
* selected components.
*
* @param newSelection
*/
void updateSelection(List<IDIYComponent<?>> newSelection);
/**
* Finds all components at the specified location, sorted by z-index from
* top to bottom.
*
* @param point
* @return
*/
List<IDIYComponent<?>> findComponentsAt(Point point);
/**
* Selects all components in the project.
*/
void selectAll();
}
@@ -31,7 +31,7 @@ public enum IconLoader {
"donate.png"), Bug("bug.png"), IconLarge("icon_large.png"), IconMedium(
"icon_medium.png"), IconSmall("icon_small.png"), DocumentEdit("document_edit.png"), EditComponent(
"edit_component.png"), Size("size.png"), Front("front.png"), Back("back.png"), Pens(
"pens.png"), Sort("sort.png");
"pens.png"), Sort("sort.png"), ElementsSelection("elements_selection.png");
protected String name;
Binary file not shown.

After

Width:  |  Height:  |  Size: 771 B

@@ -362,7 +362,7 @@ public class DrawingManager {
for (int i = 0; i < project.getComponents().size(); i++) {
Area area = componentAreaMap.get(project.getComponents().get(i));
if (area != null && area.contains(point)) {
components.add(project.getComponents().get(i));
components.add(0, project.getComponents().get(i));
}
}
return components;
@@ -341,7 +341,7 @@ public class Presenter implements IPlugInPort {
*
* @return
*/
private List<IDIYComponent<?>> findComponentsAt(Point point) {
public List<IDIYComponent<?>> findComponentsAtScaled(Point point) {
List<IDIYComponent<?>> components = drawingManager.findComponentsAt(point, currentProject);
Iterator<IDIYComponent<?>> iterator = components.iterator();
while (iterator.hasNext()) {
@@ -352,6 +352,13 @@ public class Presenter implements IPlugInPort {
return components;
}
@Override
public List<IDIYComponent<?>> findComponentsAt(Point point) {
Point scaledPoint = scalePoint(point);
List<IDIYComponent<?>> components = findComponentsAtScaled(scaledPoint);
return components;
}
@Override
public void mouseClicked(Point point, boolean ctrlDown, boolean shiftDown, boolean altDown,
int clickCount) {
@@ -455,14 +462,14 @@ public class Presenter implements IPlugInPort {
} else {
List<IDIYComponent<?>> newSelection = new ArrayList<IDIYComponent<?>>(
selectedComponents);
List<IDIYComponent<?>> components = findComponentsAt(scaledPoint);
List<IDIYComponent<?>> components = findComponentsAtScaled(scaledPoint);
// If there's nothing under mouse cursor deselect all.
if (components.isEmpty()) {
if (!ctrlDown) {
newSelection.clear();
}
} else {
IDIYComponent<?> component = components.get(components.size() - 1);
IDIYComponent<?> component = components.get(0);
// If ctrl is pressed just toggle the component under mouse
// cursor.
if (ctrlDown) {
@@ -584,7 +591,8 @@ public class Presenter implements IPlugInPort {
@Override
public void selectAll() {
LOG.info("selectAll()");
List<IDIYComponent<?>> newSelection = new ArrayList<IDIYComponent<?>>(currentProject.getComponents());
List<IDIYComponent<?>> newSelection = new ArrayList<IDIYComponent<?>>(currentProject
.getComponents());
newSelection.removeAll(getLockedComponents());
updateSelection(newSelection);
// messageDispatcher.dispatchMessage(EventType.SELECTION_CHANGED,
@@ -604,7 +612,9 @@ public class Presenter implements IPlugInPort {
LOG.debug(String.format("dragStarted(%s, %s)", point, dragAction));
if (instantiationManager.getComponentTypeSlot() != null) {
LOG.debug("Cannot start drag because a new component is being created.");
mouseClicked(point, dragAction == DnDConstants.ACTION_COPY, dragAction == DnDConstants.ACTION_LINK, dragAction == DnDConstants.ACTION_MOVE, 1);
mouseClicked(point, dragAction == DnDConstants.ACTION_COPY,
dragAction == DnDConstants.ACTION_LINK, dragAction == DnDConstants.ACTION_MOVE,
1);
return;
}
this.dragInProgress = true;
@@ -612,7 +622,7 @@ public class Presenter implements IPlugInPort {
preDragProject = cloner.deepClone(currentProject);
Point scaledPoint = scalePoint(point);
this.previousDragPoint = scaledPoint;
List<IDIYComponent<?>> components = findComponentsAt(scaledPoint);
List<IDIYComponent<?>> components = findComponentsAtScaled(scaledPoint);
if (!this.controlPointMap.isEmpty()) {
// If we're dragging control points reset selection.
updateSelection(new ArrayList<IDIYComponent<?>>(this.controlPointMap.keySet()));
@@ -631,7 +641,7 @@ public class Presenter implements IPlugInPort {
messageDispatcher.dispatchMessage(EventType.REPAINT);
} else {
// Take the last component, i.e. the top order component.
IDIYComponent<?> component = components.get(components.size() - 1);
IDIYComponent<?> component = components.get(0);
// If the component under the cursor is not already selected, make
// it into the only selected component.
if (!selectedComponents.contains(component)) {
@@ -665,7 +675,7 @@ public class Presenter implements IPlugInPort {
}
}
}
@Override
public void dragActionChanged(int dragAction) {
LOG.debug("dragActionChanged(" + dragAction + ")");
@@ -746,7 +756,7 @@ public class Presenter implements IPlugInPort {
LOG.trace("Component count didn't change, done with expanding.");
}
}
private boolean isSnapToGrid() {
boolean snapToGrid = ConfigurationManager.getInstance().readBoolean(
IPlugInPort.SNAP_TO_GRID_KEY, true);
@@ -31,7 +31,7 @@ public enum IconLoader {
"donate.png"), Bug("bug.png"), IconLarge("icon_large.png"), IconMedium(
"icon_medium.png"), IconSmall("icon_small.png"), DocumentEdit("document_edit.png"), EditComponent(
"edit_component.png"), Size("size.png"), Front("front.png"), Back("back.png"), Pens(
"pens.png"), Sort("sort.png");
"pens.png"), Sort("sort.png"), ElementsSelection("elements_selection.png");
protected String name;
Binary file not shown.

After

Width:  |  Height:  |  Size: 771 B

@@ -1,17 +1,24 @@
package org.diylc.swing.plugins.canvas;
import java.awt.Dimension;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.Toolkit;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.ClipboardOwner;
import java.awt.datatransfer.Transferable;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseWheelEvent;
import java.awt.event.MouseWheelListener;
import java.util.ArrayList;
import java.util.EnumSet;
import java.util.List;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JPopupMenu;
import javax.swing.SwingConstants;
@@ -22,8 +29,10 @@ import org.diylc.common.BadPositionException;
import org.diylc.common.EventType;
import org.diylc.common.IPlugIn;
import org.diylc.common.IPlugInPort;
import org.diylc.core.IDIYComponent;
import org.diylc.core.measures.Size;
import org.diylc.core.measures.SizeUnit;
import org.diylc.images.IconLoader;
import org.diylc.presenter.Presenter;
import org.diylc.swing.ActionFactory;
import org.diylc.swing.ISwingUI;
@@ -39,6 +48,7 @@ public class CanvasPlugin implements IPlugIn, ClipboardOwner {
private RulerScrollPane scrollPane;
private CanvasPanel canvasPanel;
private JPopupMenu popupMenu;
private JMenu selectionMenu;
private ActionFactory.CutAction cutAction;
private ActionFactory.CopyAction copyAction;
@@ -99,7 +109,7 @@ public class CanvasPlugin implements IPlugIn, ClipboardOwner {
getSendToBackAction().setEnabled(enabled);
getBringToFrontAction().setEnabled(enabled);
getPopupMenu().show(canvasPanel, e.getX(), e.getY());
showPopupAt(e.getX(), e.getY());
}
}
});
@@ -163,9 +173,16 @@ public class CanvasPlugin implements IPlugIn, ClipboardOwner {
return scrollPane;
}
private void showPopupAt(int x, int y) {
updateSelectionMenu(x, y);
getPopupMenu().show(canvasPanel, x, y);
}
public JPopupMenu getPopupMenu() {
if (popupMenu == null) {
popupMenu = new JPopupMenu();
popupMenu.add(getSelectionMenu());
popupMenu.addSeparator();
popupMenu.add(getCutAction());
popupMenu.add(getCopyAction());
popupMenu.add(getPasteAction());
@@ -182,6 +199,33 @@ public class CanvasPlugin implements IPlugIn, ClipboardOwner {
return popupMenu;
}
public JMenu getSelectionMenu() {
if (selectionMenu == null) {
selectionMenu = new JMenu("Select");
selectionMenu.setIcon(IconLoader.ElementsSelection.getIcon());
}
return selectionMenu;
}
private void updateSelectionMenu(int x, int y) {
getSelectionMenu().removeAll();
for (IDIYComponent<?> component : plugInPort.findComponentsAt(new Point(x, y))) {
JMenuItem item = new JMenuItem(component.getName());
final IDIYComponent<?> finalComponent = component;
item.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
List<IDIYComponent<?>> newSelection = new ArrayList<IDIYComponent<?>>();
newSelection.add(finalComponent);
plugInPort.updateSelection(newSelection);
plugInPort.refresh();
}
});
getSelectionMenu().add(item);
}
}
public ActionFactory.CutAction getCutAction() {
if (cutAction == null) {
cutAction = ActionFactory.getInstance().createCutAction(plugInPort, clipboard, this);
@@ -417,7 +417,11 @@
</versionNumber>
<releaseDate>2012-02-01 20:00:00.000 CET</releaseDate>
<name></name>
<changes>
<changes>
<com.diyfever.gui.update.Change>
<changeType>NEW_FEATURE</changeType>
<description>Select components from context menu even when they are under other components</description>
</com.diyfever.gui.update.Change>
<com.diyfever.gui.update.Change>
<changeType>NEW_FEATURE</changeType>
<description>Ctrl+Shift toggles "Snap to Grid" option</description>