1 /* 2 * Copyright (c) 2012, 2014, Oracle and/or its affiliates. 3 * All rights reserved. Use is subject to license terms. 4 * 5 * This file is available and licensed under the following license: 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * - Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * - Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in 15 * the documentation and/or other materials provided with the distribution. 16 * - Neither the name of Oracle Corporation nor the names of its 17 * contributors may be used to endorse or promote products derived 18 * from this software without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 23 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 24 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 25 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 26 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 27 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 28 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 30 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31 */ 32 package com.oracle.javafx.scenebuilder.kit.editor.drag.target; 33 34 import com.oracle.javafx.scenebuilder.kit.editor.EditorController; 35 import com.oracle.javafx.scenebuilder.kit.editor.drag.source.AbstractDragSource; 36 import com.oracle.javafx.scenebuilder.kit.editor.job.Job; 37 import com.oracle.javafx.scenebuilder.kit.editor.job.BatchJob; 38 import com.oracle.javafx.scenebuilder.kit.editor.job.InsertAsAccessoryJob; 39 import com.oracle.javafx.scenebuilder.kit.editor.job.atomic.ModifyObjectJob; 40 import com.oracle.javafx.scenebuilder.kit.editor.job.atomic.RemoveObjectJob; 41 import com.oracle.javafx.scenebuilder.kit.fxom.FXOMInstance; 42 import com.oracle.javafx.scenebuilder.kit.fxom.FXOMObject; 43 import com.oracle.javafx.scenebuilder.kit.metadata.property.value.EnumerationPropertyMetadata; 44 import com.oracle.javafx.scenebuilder.kit.metadata.util.DesignHierarchyMask; 45 import com.oracle.javafx.scenebuilder.kit.metadata.util.DesignHierarchyMask.Accessory; 46 import com.oracle.javafx.scenebuilder.kit.metadata.util.InspectorPath; 47 import com.oracle.javafx.scenebuilder.kit.metadata.util.PropertyName; 48 import java.util.Objects; 49 import javafx.geometry.Pos; 50 import javafx.scene.layout.BorderPane; 51 52 /** 53 * 54 */ 55 public class AccessoryDropTarget extends AbstractDropTarget { 56 57 private final FXOMInstance targetContainer; 58 private final Accessory accessory; 59 60 public AccessoryDropTarget(FXOMInstance targetContainer, Accessory accessory) { 61 assert targetContainer != null; 62 this.targetContainer = targetContainer; 63 this.accessory = accessory; 64 } 65 66 public Accessory getAccessory() { 67 return accessory; 68 } 69 70 71 /* 72 * AbstractDropTarget 73 */ 74 @Override 75 public FXOMObject getTargetObject() { 76 return targetContainer; 77 } 78 79 @Override 80 public boolean acceptDragSource(AbstractDragSource dragSource) { 81 assert dragSource != null; 82 83 final boolean result; 84 if (dragSource.getDraggedObjects().size() != 1) { 85 result = false; 86 } else { 87 final DesignHierarchyMask m = new DesignHierarchyMask(targetContainer); 88 final FXOMObject draggedObject = dragSource.getDraggedObjects().get(0); 89 result = m.isAcceptingAccessory(accessory, draggedObject) 90 && m.getAccessory(accessory) == null; 91 } 92 93 return result; 94 } 95 96 @Override 97 public Job makeDropJob(AbstractDragSource dragSource, EditorController editorController) { 98 assert acceptDragSource(dragSource); 99 assert editorController != null; 100 101 final boolean shouldRefreshSceneGraph = true; 102 final BatchJob result = new BatchJob(editorController, 103 shouldRefreshSceneGraph, dragSource.makeDropJobDescription()); 104 105 final FXOMObject draggedObject = dragSource.getDraggedObjects().get(0); 106 final FXOMObject currentParent = draggedObject.getParentObject(); 107 108 // Two steps : 109 // - remove drag source object from its current parent (if any) 110 // - set the drag source object as accessory of the drop target 111 112 if (currentParent != null) { 113 result.addSubJob(new RemoveObjectJob(draggedObject, editorController)); 114 } 115 final Job j = new InsertAsAccessoryJob(draggedObject, 116 targetContainer, accessory, editorController); 117 result.addSubJob(j); 118 119 if ((targetContainer.getSceneGraphObject() instanceof BorderPane) 120 && (draggedObject instanceof FXOMInstance)) { 121 122 // We add a job which sets BorderPane.alignment=CENTER on draggedObject 123 final FXOMInstance draggedInstance 124 = (FXOMInstance) draggedObject; 125 final PropertyName alignmentName 126 = new PropertyName("alignment", BorderPane.class); //NOI18N 127 final EnumerationPropertyMetadata alignmentMeta 128 = new EnumerationPropertyMetadata(alignmentName, Pos.class, 129 "UNUSED", true /* readWrite */, InspectorPath.UNUSED); //NOI18N 130 final Job alignmentJob 131 = new ModifyObjectJob(draggedInstance, alignmentMeta, 132 Pos.CENTER.toString(), editorController); 133 result.addSubJob(alignmentJob); 134 } 135 136 assert result.isExecutable(); 137 138 return result; 139 } 140 141 @Override 142 public boolean isSelectRequiredAfterDrop() { 143 return true; 144 } 145 146 /* 147 * Objects 148 */ 149 @Override 150 public int hashCode() { 151 int hash = 3; 152 hash = 97 * hash + Objects.hashCode(this.targetContainer); 153 hash = 97 * hash + (this.accessory != null ? this.accessory.hashCode() : 0); 154 return hash; 155 } 156 157 @Override 158 public boolean equals(Object obj) { 159 if (obj == null) { 160 return false; 161 } 162 if (getClass() != obj.getClass()) { 163 return false; 164 } 165 final AccessoryDropTarget other = (AccessoryDropTarget) obj; 166 if (!Objects.equals(this.targetContainer, other.targetContainer)) { 167 return false; 168 } 169 if (this.accessory != other.accessory) { 170 return false; 171 } 172 return true; 173 } 174 175 @Override 176 public String toString() { 177 return "AccessoryDropTarget{" + "targetContainer=" + targetContainer + ", accessory=" + accessory + '}'; //NOI18N 178 } 179 180 181 }