Lines 14-28
Link Here
|
14 |
import org.eclipse.core.runtime.IStatus; |
14 |
import org.eclipse.core.runtime.IStatus; |
15 |
import org.eclipse.core.runtime.Status; |
15 |
import org.eclipse.core.runtime.Status; |
16 |
import org.eclipse.core.runtime.jobs.Job; |
16 |
import org.eclipse.core.runtime.jobs.Job; |
17 |
import org.eclipse.jface.util.Geometry; |
|
|
18 |
import org.eclipse.swt.SWT; |
17 |
import org.eclipse.swt.SWT; |
19 |
import org.eclipse.swt.events.PaintEvent; |
|
|
20 |
import org.eclipse.swt.events.PaintListener; |
21 |
import org.eclipse.swt.graphics.Color; |
18 |
import org.eclipse.swt.graphics.Color; |
22 |
import org.eclipse.swt.graphics.GC; |
|
|
23 |
import org.eclipse.swt.graphics.Rectangle; |
19 |
import org.eclipse.swt.graphics.Rectangle; |
|
|
20 |
import org.eclipse.swt.graphics.Region; |
24 |
import org.eclipse.swt.widgets.Canvas; |
21 |
import org.eclipse.swt.widgets.Canvas; |
25 |
import org.eclipse.swt.widgets.Composite; |
22 |
import org.eclipse.swt.widgets.Control; |
|
|
23 |
import org.eclipse.swt.widgets.Display; |
24 |
import org.eclipse.swt.widgets.Shell; |
26 |
|
25 |
|
27 |
/** |
26 |
/** |
28 |
* This job creates an animated rectangle that moves from a source rectangle to |
27 |
* This job creates an animated rectangle that moves from a source rectangle to |
Lines 32-37
Link Here
|
32 |
* @since 3.0 |
31 |
* @since 3.0 |
33 |
*/ |
32 |
*/ |
34 |
public class RectangleAnimation extends Job { |
33 |
public class RectangleAnimation extends Job { |
|
|
34 |
private static final int LINE_WIDTH = 2; |
35 |
private Rectangle start; |
35 |
private Rectangle start; |
36 |
private int elapsed; |
36 |
private int elapsed; |
37 |
private int duration; |
37 |
private int duration; |
Lines 39-44
Link Here
|
39 |
private Rectangle end; |
39 |
private Rectangle end; |
40 |
private Rectangle last; |
40 |
private Rectangle last; |
41 |
private boolean done = false; |
41 |
private boolean done = false; |
|
|
42 |
private Shell theShell; |
43 |
private Display display; |
44 |
private Region shellRegion; |
45 |
private boolean first = true; |
42 |
|
46 |
|
43 |
/** |
47 |
/** |
44 |
* Canvas used to draw the animation, or null if the animation should be skipped. |
48 |
* Canvas used to draw the animation, or null if the animation should be skipped. |
Lines 60-111
Link Here
|
60 |
private Runnable paintJob = new Runnable() { //$NON-NLS-1$ |
64 |
private Runnable paintJob = new Runnable() { //$NON-NLS-1$ |
61 |
|
65 |
|
62 |
public void run() { |
66 |
public void run() { |
63 |
if (canvas == null || canvas.isDisposed()) { |
67 |
|
|
|
68 |
// Measure the start as the time of the first syncExec |
69 |
if (startTime == 0) { |
70 |
startTime = System.currentTimeMillis(); |
71 |
} |
72 |
|
73 |
if (theShell == null || theShell.isDisposed()) { |
64 |
done = true; |
74 |
done = true; |
65 |
return; |
75 |
return; |
66 |
} |
76 |
} |
67 |
|
77 |
|
68 |
canvas.redraw(); |
78 |
long currentTime = System.currentTimeMillis(); |
|
|
79 |
|
80 |
double amount = (double)(currentTime - startTime) / (double)duration; |
81 |
|
82 |
if (amount > 1.0) { |
83 |
amount = 1.0; |
84 |
done = true; |
85 |
} |
86 |
|
87 |
Rectangle toPaint = interpolate(start, end, amount); |
88 |
|
89 |
theShell.setBounds(toPaint); |
90 |
if (shellRegion != null) { |
91 |
shellRegion.dispose(); |
92 |
shellRegion = new Region(display); |
93 |
} |
94 |
|
95 |
Rectangle rect = theShell.getClientArea(); |
96 |
shellRegion.add(rect); |
97 |
rect.x += LINE_WIDTH; |
98 |
rect.y += LINE_WIDTH; |
99 |
rect.width -= 2 * LINE_WIDTH; |
100 |
rect.height -= 2 * LINE_WIDTH; |
101 |
|
102 |
shellRegion.subtract(rect); |
103 |
|
104 |
theShell.setRegion(shellRegion); |
105 |
|
106 |
if (first) { |
107 |
// Make sure that opening the shell doesn't steal focus |
108 |
Control focusControl = display.getFocusControl(); |
109 |
theShell.open(); |
110 |
if (focusControl != null) { |
111 |
focusControl.setFocus(); |
112 |
} |
113 |
} |
114 |
|
115 |
first = false; |
69 |
} |
116 |
} |
70 |
|
117 |
|
71 |
}; |
118 |
}; |
72 |
|
119 |
|
73 |
private void draw(GC gc) { |
120 |
public RectangleAnimation(Shell parentShell, Rectangle start, Rectangle end) { |
74 |
if (startTime == 0) { |
121 |
this(parentShell, start, end, 400); |
75 |
return; |
|
|
76 |
} |
77 |
|
78 |
if (canvas == null || canvas.isDisposed()) { |
79 |
done = true; |
80 |
return; |
81 |
} |
82 |
|
83 |
long currentTime = System.currentTimeMillis(); |
84 |
|
85 |
double amount = (double)(currentTime - startTime) / (double)duration; |
86 |
|
87 |
if (amount > 1.0) { |
88 |
amount = 1.0; |
89 |
done = true; |
90 |
} |
91 |
|
92 |
Rectangle toPaint = interpolate(start, end, amount); |
93 |
|
94 |
gc.setLineWidth(2); |
95 |
Color color = canvas.getDisplay().getSystemColor(SWT.COLOR_WHITE); |
96 |
gc.setForeground(color); |
97 |
|
98 |
gc.setXORMode(true); |
99 |
if (last != null) { |
100 |
if (last.equals(toPaint)) { |
101 |
return; |
102 |
} |
103 |
gc.drawRectangle(Geometry.toControl(canvas, last)); |
104 |
} |
105 |
gc.drawRectangle(Geometry.toControl(canvas, toPaint)); |
106 |
last = toPaint; |
107 |
} |
122 |
} |
108 |
|
|
|
109 |
|
123 |
|
110 |
/** |
124 |
/** |
111 |
* Creates an animation that will morph the start rectangle to the end rectangle in the |
125 |
* Creates an animation that will morph the start rectangle to the end rectangle in the |
Lines 122-152
Link Here
|
122 |
* @param end final rectangle (display coordinates) |
136 |
* @param end final rectangle (display coordinates) |
123 |
* @param duration number of milliseconds over which the animation will run |
137 |
* @param duration number of milliseconds over which the animation will run |
124 |
*/ |
138 |
*/ |
125 |
public RectangleAnimation(Composite whereToDraw, Rectangle start, Rectangle end, int duration) { |
139 |
public RectangleAnimation(Shell parentShell, Rectangle start, Rectangle end, int duration) { |
126 |
super(WorkbenchMessages.getString("RectangleAnimation.Animating_Rectangle")); //$NON-NLS-1$ |
140 |
super(WorkbenchMessages.getString("RectangleAnimation.Animating_Rectangle")); //$NON-NLS-1$ |
127 |
this.duration = duration; |
141 |
this.duration = duration; |
128 |
this.start = start; |
142 |
this.start = start; |
129 |
this.end = end; |
143 |
this.end = end; |
130 |
|
144 |
|
|
|
145 |
display = parentShell.getDisplay(); |
146 |
|
131 |
setSystem(true); |
147 |
setSystem(true); |
132 |
|
148 |
|
133 |
// Determine if we're on a platform where animations look ugly. |
149 |
// Determine if we're on a platform where animations look ugly. |
134 |
// If so, we indicate this by setting canvas=null, in which case this job does nothing. |
150 |
// If so, we indicate this by setting canvas=null, in which case this job does nothing. |
135 |
String platform = SWT.getPlatform(); |
151 |
// String platform = SWT.getPlatform(); |
136 |
if (!"win32".equals(platform)) { //$NON-NLS-1$ |
152 |
// if (!"win32".equals(platform)) { //$NON-NLS-1$ |
137 |
return; |
153 |
// return; |
138 |
} |
154 |
// } |
139 |
|
155 |
|
140 |
this.canvas = new Canvas(whereToDraw, SWT.NO_BACKGROUND); |
156 |
theShell = new Shell(parentShell, SWT.NO_TRIM | SWT.NO_FOCUS); |
141 |
canvas.setBounds(whereToDraw.getClientArea()); |
157 |
Color color = display.getSystemColor(SWT.COLOR_BLACK); |
|
|
158 |
theShell.setBackground(color); |
142 |
|
159 |
|
143 |
canvas.addPaintListener(new PaintListener() { |
160 |
theShell.setBounds(start); |
144 |
public void paintControl(PaintEvent event) { |
|
|
145 |
draw(event.gc); |
146 |
} |
147 |
}); |
148 |
|
161 |
|
149 |
canvas.moveAbove(null); |
162 |
shellRegion = new Region(display); |
150 |
} |
163 |
} |
151 |
|
164 |
|
152 |
/* (non-Javadoc) |
165 |
/* (non-Javadoc) |
Lines 155-178
Link Here
|
155 |
protected IStatus run(IProgressMonitor monitor) { |
168 |
protected IStatus run(IProgressMonitor monitor) { |
156 |
|
169 |
|
157 |
// We use canvas = null to indicate that the animation should be skipped on this platform. |
170 |
// We use canvas = null to indicate that the animation should be skipped on this platform. |
158 |
if (canvas == null) { |
171 |
if (theShell == null) { |
159 |
return Status.OK_STATUS; |
172 |
return Status.OK_STATUS; |
160 |
} |
173 |
} |
161 |
|
174 |
|
162 |
startTime = System.currentTimeMillis(); |
175 |
startTime = 0;//System.currentTimeMillis(); |
163 |
|
176 |
|
164 |
while (!done) { |
177 |
while (!done) { |
165 |
if (!canvas.isDisposed()) { |
178 |
if (!theShell.isDisposed()) { |
166 |
canvas.getDisplay().syncExec(paintJob); |
179 |
display.syncExec(paintJob); |
|
|
180 |
// Don't pin the CPU |
181 |
Thread.yield(); |
167 |
} |
182 |
} |
168 |
} |
183 |
} |
169 |
|
184 |
|
170 |
if (!canvas.isDisposed()) { |
185 |
if (!theShell.isDisposed()) { |
171 |
canvas.getDisplay().syncExec(new Runnable() { |
186 |
theShell.getDisplay().syncExec(new Runnable() { |
172 |
public void run() { |
187 |
public void run() { |
173 |
canvas.dispose(); |
188 |
theShell.dispose(); |
174 |
} |
189 |
} |
175 |
}); |
190 |
}); |
|
|
191 |
} |
192 |
|
193 |
if (!shellRegion.isDisposed()) { |
194 |
shellRegion.dispose(); |
176 |
} |
195 |
} |
177 |
|
196 |
|
178 |
return Status.OK_STATUS; |
197 |
return Status.OK_STATUS; |