// ============================================================================ // // Copyright (C) 2006-2012 Talend Inc. - www.talend.com // // This source code is available under agreement available at // %InstallDIR%\features\org.talend.rcp.branding.%PRODUCTNAME%\%PRODUCTNAME%license.txt // // You should have received a copy of the agreement // along with this program; if not, write to Talend SA // 9 rue Pages 92150 Suresnes, France // // ============================================================================ package org.talend.designer.core.ui.editor.cmd; import java.util.ArrayList; import java.util.List; import org.eclipse.draw2d.geometry.Dimension; import org.eclipse.draw2d.geometry.Point; import org.eclipse.gef.EditPart; import org.eclipse.gef.GraphicalViewer; import org.eclipse.gef.commands.Command; import org.eclipse.jface.viewers.StructuredSelection; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.ui.PlatformUI; import org.talend.designer.core.i18n.Messages; import org.talend.designer.core.model.components.EParameterName; import org.talend.designer.core.ui.AbstractMultiPageTalendEditor; import org.talend.designer.core.ui.editor.TalendEditor; import org.talend.designer.core.ui.editor.notes.Note; import org.talend.designer.core.ui.editor.notes.NoteEditPart; import org.talend.designer.core.ui.editor.process.Process; import org.talend.designer.core.ui.editor.process.ProcessPart; /** * Command used to paste all the components. * * $Id: NodesPasteCommand.java 4549 2007-07-13 05:18:48Z nrousseau $ * */ public class NotesPasteCommand extends Command { private boolean isMultiple; private Process process; private List<EditPart> oldSelection; private List<Note> noteList; private Point firstNodeLocation; private List<NoteEditPart> noteParts; private boolean multipleCommand; public NotesPasteCommand(List<NoteEditPart> noteParts, Process process, Point cursorLocation, boolean isMultiple, Point point) { this.process = process; this.isMultiple = isMultiple; this.firstNodeLocation = point; orderNoteParts(noteParts); setLabel(Messages.getString("NotesPasteCommand.label")); //$NON-NLS-1$ setCursorLocation(cursorLocation); } Point cursorLocation = null; /** * Getter for cursorLocation. * * @return the cursorLocation */ public Point getCursorLocation() { return this.cursorLocation; } /** * Sets the cursorLocation. * * @param cursorLocation the cursorLocation to set */ public void setCursorLocation(Point cursorLocation) { this.cursorLocation = cursorLocation; } /* * (non-Javadoc) * * @see org.eclipse.gef.commands.Command#canExecute() */ @Override public boolean canExecute() { return !process.isReadOnly(); } private void orderNoteParts(List<NoteEditPart> noteParts) { this.noteParts = new ArrayList<NoteEditPart>(); Point curLocation; NoteEditPart toAdd = null; List<NoteEditPart> restToOrder = new ArrayList<NoteEditPart>(); restToOrder.addAll(noteParts); for (NoteEditPart copiedNodePart : noteParts) { curLocation = null; for (NoteEditPart partToOrder : restToOrder) { Note copiedNote = (Note) partToOrder.getModel(); if (curLocation == null) { curLocation = copiedNote.getLocation(); toAdd = partToOrder; } else { if (curLocation.y >= copiedNote.getLocation().y) { if (curLocation.x >= copiedNote.getLocation().x) { curLocation = copiedNote.getLocation(); toAdd = partToOrder; } } } } if (toAdd != null) { this.noteParts.add(toAdd); restToOrder.remove(toAdd); } } } /** * * Will return a empty location for a component from a given point. * * @param location * @return */ private Point findLocationForNote(final Point location, final Dimension size, int index, int firstIndex) { Point newLocation = findLocationForNoteInProcess(location, size); newLocation = findLocationForNoteInContainerList(newLocation, size, index, firstIndex); return newLocation; } @SuppressWarnings("unchecked") private Point findLocationForNoteInProcess(final Point location, Dimension size) { Rectangle copiedRect = new Rectangle(location.x, location.y, size.width, size.height); Point newLocation = new Point(location); for (Note node : process.getNotes()) { Rectangle currentRect = new Rectangle(node.getLocation().x, node.getLocation().y, node.getSize().width, node .getSize().height); if (currentRect.intersects(copiedRect)) { newLocation.x += TalendEditor.GRID_SIZE; newLocation.y += TalendEditor.GRID_SIZE; return findLocationForNoteInProcess(newLocation, size); } } return newLocation; } private Point findLocationForNoteInContainerList(final Point location, Dimension size, int index, int firstIndex) { Rectangle copiedRect = new Rectangle(location.x, location.y, size.width, size.height); Point newLocation = new Point(location); if (!isMultiple) { for (Note node : noteList) { Rectangle currentRect = new Rectangle(node.getLocation().x, node.getLocation().y, node.getSize().width, node .getSize().height); if (currentRect.intersects(copiedRect)) { newLocation = computeTheDistance(index, firstIndex, newLocation); // return findLocationForNoteInContainerList(newLocation, size, index, firstIndex); } } } else { if (getCursorLocation() == null) { return newLocation; } newLocation = computeTheDistance(index, firstIndex, newLocation); } return newLocation; } private Point computeTheDistance(int index, int firstIndex, Point location) { Point currentNodeLocation = null; if (!isMultiple) { firstNodeLocation = ((Note) noteParts.get(firstIndex).getModel()).getLocation(); } currentNodeLocation = ((Note) noteParts.get(index).getModel()).getLocation(); int distanceX = firstNodeLocation.x - currentNodeLocation.x; int distanceY = firstNodeLocation.y - currentNodeLocation.y; location.x = location.x - distanceX; location.y = location.y - distanceY; return location; } @SuppressWarnings("unchecked") private void createNoteList() { int firstIndex = 0; int index = 0; noteList = new ArrayList<Note>(); // create the notes for (NoteEditPart copiedNodePart : noteParts) { Note copiedNote = (Note) copiedNodePart.getModel(); Note pastedNote = new Note(); pastedNote.setOpaque(copiedNote.isOpaque()); pastedNote.setText(copiedNote.getText()); pastedNote.setSize(copiedNote.getSize()); // see bug 0005571: Copy/Paste of Note doesn't keep Format EParameterName[] params = new EParameterName[] { EParameterName.NOTE_FONT, EParameterName.FONT_SIZE, EParameterName.FONT_BOLD, EParameterName.FONT_ITALIC, EParameterName.NOTE_LINECOLOR, EParameterName.NOTE_COLOR, EParameterName.NOTETXT_COLOR, EParameterName.NOTETXT_LEFT, EParameterName.NOTETXT_RIGHT, EParameterName.NOTETXT_CENTER, EParameterName.NOTELABEL_CENTER, EParameterName.NOTETXT_TOP, EParameterName.NOTETXT_BOTTOM }; for (EParameterName param : params) { Object value = copiedNote.getElementParameter(param.getName()).getValue(); pastedNote.getElementParameter(param.getName()).setValue(value); } pastedNote.setOpaque(copiedNote.isOpaque()); pastedNote.setProcess(process); Point location = null; if (getCursorLocation() == null) { location = copiedNote.getLocation(); } else { location = getCursorLocation(); index = noteParts.indexOf(copiedNodePart); } if (process.isGridEnabled()) { // replace the component to set it on the grid if it's enabled int tempVar = location.x / TalendEditor.GRID_SIZE; location.x = tempVar * TalendEditor.GRID_SIZE; tempVar = location.y / TalendEditor.GRID_SIZE; location.y = tempVar * TalendEditor.GRID_SIZE; } pastedNote.setLocation(findLocationForNote(location, copiedNote.getSize(), index, firstIndex)); noteList.add(pastedNote); } } @SuppressWarnings("unchecked") @Override public void execute() { // create the note list to paste createNoteList(); AbstractMultiPageTalendEditor multiPageTalendEditor = (AbstractMultiPageTalendEditor) PlatformUI.getWorkbench() .getActiveWorkbenchWindow().getActivePage().getActiveEditor(); GraphicalViewer viewer = multiPageTalendEditor.getTalendEditor().getViewer(); // save old selection if (!multipleCommand) { oldSelection = new ArrayList<EditPart>(); for (EditPart editPart : (List<EditPart>) viewer.getSelectedEditParts()) { oldSelection.add(editPart); } // remove the old selection viewer.deselectAll(); } // creates the different notes for (Note note : noteList) { process.addNote(note); } // set the new note as the current selection if (!multipleCommand) { EditPart processPart = (EditPart) viewer.getRootEditPart().getChildren().get(0); if (processPart instanceof ProcessPart) { // can only be ProcessPart but still test List<EditPart> sel = new ArrayList<EditPart>(); for (EditPart editPart : (List<EditPart>) processPart.getChildren()) { if (editPart instanceof NoteEditPart) { Note currentNode = (Note) editPart.getModel(); if (noteList.contains(currentNode)) { sel.add(editPart); } } } StructuredSelection s = new StructuredSelection(sel); viewer.setSelection(s); } } process.checkStartNodes(); process.checkProcess(); } @SuppressWarnings("unchecked") @Override public void undo() { // remove the current selection AbstractMultiPageTalendEditor multiPageTalendEditor = (AbstractMultiPageTalendEditor) PlatformUI.getWorkbench() .getActiveWorkbenchWindow().getActivePage().getActiveEditor(); GraphicalViewer viewer = multiPageTalendEditor.getTalendEditor().getViewer(); if (!multipleCommand) { viewer.deselectAll(); } for (Note note : noteList) { process.removeNote(note); } // set the old selection active if (!multipleCommand) { StructuredSelection s = new StructuredSelection(oldSelection); viewer.setSelection(s); } process.checkStartNodes(); process.checkProcess(); } /** * Getter for multipleCommand. * * @return the multipleCommand */ public boolean isMultipleCommand() { return multipleCommand; } /** * Sets the multipleCommand. * * @param multipleCommand the multipleCommand to set */ public void setMultipleCommand(boolean multipleCommand) { this.multipleCommand = multipleCommand; } /** * Getter for noteList. * * @return the noteList */ public List<Note> getNoteList() { return noteList; } }