Skip to content

Commit 0ffa329

Browse files
(v2) Scene editor: tile scale tool.
1 parent bed389c commit 0ffa329

File tree

3 files changed

+290
-4
lines changed

3 files changed

+290
-4
lines changed

source/v2/phasereditor/phasereditor.scene.ui/src/phasereditor/scene/ui/editor/interactive/TilePositionElement.java

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -198,11 +198,11 @@ public void mouseMove(MouseEvent e) {
198198

199199
for (var model : getModels()) {
200200

201-
var initialXY = (float[]) model.get("initial-local-xy");
201+
var initialLocalXY = (float[]) model.get("initial-local-xy");
202202
var localXY = getRenderer().sceneToLocal(model, e.x, e.y);
203203

204-
var dx = localXY[0] - initialXY[0];
205-
var dy = localXY[1] - initialXY[1];
204+
var dx = localXY[0] - initialLocalXY[0];
205+
var dy = localXY[1] - initialLocalXY[1];
206206

207207
var initialTilePositionX = (float) model.get("initial-tilePositionX");
208208
var initialTilePositionY = (float) model.get("initial-tilePositionY");
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,275 @@
1+
// The MIT License (MIT)
2+
//
3+
// Copyright (c) 2015, 2018 Arian Fornaris
4+
//
5+
// Permission is hereby granted, free of charge, to any person obtaining a
6+
// copy of this software and associated documentation files (the
7+
// "Software"), to deal in the Software without restriction, including
8+
// without limitation the rights to use, copy, modify, merge, publish,
9+
// distribute, sublicense, and/or sell copies of the Software, and to permit
10+
// persons to whom the Software is furnished to do so, subject to the
11+
// following conditions: The above copyright notice and this permission
12+
// notice shall be included in all copies or substantial portions of the
13+
// Software.
14+
//
15+
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
16+
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17+
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
18+
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
19+
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
20+
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
21+
// USE OR OTHER DEALINGS IN THE SOFTWARE.
22+
package phasereditor.scene.ui.editor.interactive;
23+
24+
import java.util.List;
25+
26+
import org.eclipse.swt.SWT;
27+
import org.eclipse.swt.events.MouseEvent;
28+
import org.eclipse.swt.graphics.Color;
29+
import org.eclipse.swt.graphics.GC;
30+
import org.eclipse.swt.graphics.Transform;
31+
import org.eclipse.wb.swt.SWTResourceManager;
32+
33+
import phasereditor.scene.core.ObjectModel;
34+
import phasereditor.scene.core.TextureComponent;
35+
import phasereditor.scene.core.TileSpriteComponent;
36+
import phasereditor.scene.ui.editor.SceneEditor;
37+
import phasereditor.scene.ui.editor.undo.SingleObjectSnapshotOperation;
38+
import phasereditor.ui.PhaserEditorUI;
39+
40+
/**
41+
* @author arian
42+
*
43+
*/
44+
@SuppressWarnings("boxing")
45+
public class TileScaleElement extends RenderInteractiveElement {
46+
47+
private static final int BOX = 14;
48+
private int _globalX;
49+
private int _globalY;
50+
private boolean _dragging;
51+
private int _initialGlobalY;
52+
private int _initialGlobalX;
53+
private boolean _changeX;
54+
private boolean _changeY;
55+
private boolean _hightlights;
56+
57+
public TileScaleElement(SceneEditor editor, List<ObjectModel> models, boolean changeX, boolean changeY) {
58+
super(editor, models);
59+
60+
_changeX = changeX;
61+
_changeY = changeY;
62+
}
63+
64+
@Override
65+
public void render(GC gc) {
66+
var renderer = getRenderer();
67+
68+
var centerGlobalX = 0;
69+
var centerGlobalY = 0;
70+
var globalX = 0;
71+
var globalY = 0;
72+
var globalAngle = 0f;
73+
74+
for (var model : getModels()) {
75+
var frame = TextureComponent.get_frame(model);
76+
var textureWidth = frame.getFrameData().srcSize.x;
77+
var textureHeight = frame.getFrameData().srcSize.y;
78+
79+
var modelX = 0;
80+
var modelY = 0;
81+
82+
var globalXY = renderer.localToScene(model, modelX, modelY);
83+
84+
centerGlobalX += globalXY[0];
85+
centerGlobalY += globalXY[1];
86+
87+
globalAngle += renderer.globalAngle(model);
88+
89+
if (_changeX && _changeY) {
90+
91+
globalX = centerGlobalX;
92+
globalY = centerGlobalY;
93+
94+
} else if (_changeX) {
95+
96+
97+
var tileScale = TileSpriteComponent.get_tileScaleX(model);
98+
var len = textureWidth * tileScale;
99+
100+
var xy = renderer.localToScene(model, modelX + len, modelY);
101+
102+
globalX += (int) xy[0];
103+
globalY += (int) xy[1];
104+
105+
} else {
106+
107+
var tileScale = TileSpriteComponent.get_tileScaleY(model);
108+
var len = textureHeight * tileScale;
109+
110+
var xy = renderer.localToScene(model, modelX, modelY + len);
111+
112+
globalX += (int) xy[0];
113+
globalY += (int) xy[1];
114+
115+
}
116+
117+
}
118+
119+
var size = getModels().size();
120+
121+
globalX = globalX / size;
122+
globalY = globalY / size;
123+
124+
centerGlobalX = centerGlobalX / size;
125+
centerGlobalY = centerGlobalY / size;
126+
127+
globalAngle = globalAngle / size;
128+
129+
if (_changeX && _changeY) {
130+
fillRect(gc, globalX, _globalY, globalAngle, BOX,
131+
SWTResourceManager.getColor(_hightlights ? SWT.COLOR_WHITE : SWT.COLOR_YELLOW));
132+
} else {
133+
gc.setBackground(SWTResourceManager.getColor(SWT.COLOR_BLACK));
134+
gc.setForeground(SWTResourceManager.getColor(SWT.COLOR_BLACK));
135+
136+
var color = SWTResourceManager
137+
.getColor(_hightlights ? SWT.COLOR_WHITE : (_changeX ? SWT.COLOR_RED : SWT.COLOR_GREEN));
138+
139+
gc.setBackground(color);
140+
gc.setForeground(color);
141+
142+
gc.drawLine(centerGlobalX, centerGlobalY, globalX, globalY);
143+
144+
fillRect(gc, globalX, globalY, globalAngle + (_changeY ? 90 : 0), BOX, color);
145+
}
146+
147+
_globalX = globalX;
148+
_globalY = globalY;
149+
150+
}
151+
152+
private static void fillRect(GC gc, int globalX, int globalY, float globalAngle, int size, Color color) {
153+
var tx = new Transform(gc.getDevice());
154+
155+
tx.translate(globalX, globalY);
156+
tx.rotate(globalAngle);
157+
gc.setTransform(tx);
158+
159+
gc.setBackground(color);
160+
gc.setForeground(SWTResourceManager.getColor(SWT.COLOR_BLACK));
161+
162+
gc.fillRectangle(-size / 2, -size / 2, size, size);
163+
gc.drawRectangle(-size / 2, -size / 2, size, size);
164+
165+
gc.setTransform(null);
166+
167+
tx.dispose();
168+
}
169+
170+
@Override
171+
public boolean contains(int sceneX, int sceneY) {
172+
173+
if (_dragging) {
174+
return true;
175+
}
176+
177+
var contains = PhaserEditorUI.distance(sceneX, sceneY, _globalX, _globalY) <= BOX;
178+
179+
_hightlights = contains;
180+
181+
return contains;
182+
}
183+
184+
@Override
185+
public void mouseMove(MouseEvent e) {
186+
if (_dragging && contains(e.x, e.y)) {
187+
188+
for (var model : getModels()) {
189+
var frame = TextureComponent.get_frame(model);
190+
var textureWidth = frame.getFrameData().srcSize.x;
191+
var textureHeight = frame.getFrameData().srcSize.y;
192+
193+
var initialLocalXY = (float[]) model.get("initial-local-xy");
194+
var localXY = getRenderer().sceneToLocal(model, e.x, e.y);
195+
196+
var dx = localXY[0] - initialLocalXY[0];
197+
var dy = localXY[1] - initialLocalXY[1];
198+
199+
var initialTileScaleX = (float) model.get("initial-tileScaleX");
200+
var initialTileScaleY = (float) model.get("initial-tileScaleY");
201+
202+
var tileScaleX = initialTileScaleX + dx / textureWidth;
203+
var tileScaleY = initialTileScaleY + dy / textureHeight;
204+
205+
if (_changeX) {
206+
TileSpriteComponent.set_tileScaleX(model, tileScaleX);
207+
}
208+
209+
if (_changeY) {
210+
TileSpriteComponent.set_tileScaleY(model, tileScaleY);
211+
}
212+
213+
model.setDirty(true);
214+
215+
getEditor().updatePropertyPagesContentWithSelection();
216+
}
217+
}
218+
}
219+
220+
@Override
221+
public void mouseDown(MouseEvent e) {
222+
if (contains(e.x, e.y)) {
223+
224+
_dragging = true;
225+
226+
_initialGlobalX = _globalX;
227+
_initialGlobalY = _globalY;
228+
229+
for (var model : getModels()) {
230+
model.put("initial-tileScaleX", TileSpriteComponent.get_tileScaleX(model));
231+
model.put("initial-tileScaleY", TileSpriteComponent.get_tileScaleY(model));
232+
233+
var xy = getRenderer().sceneToLocal(model, _initialGlobalX, _initialGlobalY);
234+
model.put("initial-local-xy", xy);
235+
236+
}
237+
}
238+
}
239+
240+
@Override
241+
public void mouseUp(MouseEvent e) {
242+
if (_dragging) {
243+
244+
var editor = getEditor();
245+
246+
getModels().forEach(model -> {
247+
248+
model.put("final-tileScaleX", TileSpriteComponent.get_tilePositionX(model));
249+
model.put("final-tileScaleY", TileSpriteComponent.get_tilePositionY(model));
250+
251+
TileSpriteComponent.set_tilePositionX(model, (float) model.get("initial-tileScaleX"));
252+
TileSpriteComponent.set_tilePositionY(model, (float) model.get("initial-tileScaleY"));
253+
254+
});
255+
256+
var before = SingleObjectSnapshotOperation.takeSnapshot(getModels());
257+
258+
getModels().forEach(model -> {
259+
260+
TileSpriteComponent.set_tilePositionX(model, (float) model.get("final-tileScaleX"));
261+
TileSpriteComponent.set_tilePositionY(model, (float) model.get("final-tileScaleY"));
262+
263+
});
264+
265+
var after = SingleObjectSnapshotOperation.takeSnapshot(getModels());
266+
267+
editor.executeOperation(new SingleObjectSnapshotOperation(before, after, "Set tile position.", true));
268+
269+
editor.setDirty(true);
270+
271+
}
272+
_dragging = false;
273+
}
274+
275+
}

source/v2/phasereditor/phasereditor.scene.ui/src/phasereditor/scene/ui/editor/properties/TileSpriteSection.java

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
import phasereditor.scene.core.TileSpriteComponent;
3636
import phasereditor.scene.core.TileSpriteModel;
3737
import phasereditor.scene.ui.editor.interactive.TilePositionElement;
38+
import phasereditor.scene.ui.editor.interactive.TileScaleElement;
3839
import phasereditor.scene.ui.editor.undo.SingleObjectSnapshotOperation;
3940
import phasereditor.ui.EditorSharedImages;
4041
import phasereditor.ui.properties.FormPropertyPage;
@@ -113,7 +114,17 @@ public void run() {
113114
{
114115
var manager = new ToolBarManager();
115116
manager.add(new Action("Tile Scale", EditorSharedImages.getImageDescriptor(IMG_EDIT_OBJ_PROPERTY)) {
116-
//
117+
@Override
118+
public void run() {
119+
120+
getEditor().getScene().setInteractiveElements(
121+
122+
new TileScaleElement(getEditor(), getModels(), true, false),
123+
new TileScaleElement(getEditor(), getModels(), false, true),
124+
new TileScaleElement(getEditor(), getModels(), true, true)
125+
126+
);
127+
}
117128
});
118129
manager.createControl(comp);
119130
}

0 commit comments

Comments
 (0)