author | ca |
Sat, 25 May 1996 15:54:02 +0200 | |
changeset 354 | 909581778d57 |
parent 333 | 785f0e48fdb8 |
child 357 | 9b43dacb35d1 |
permissions | -rw-r--r-- |
318 | 1 |
" |
2 |
COPYRIGHT (c) 1996 by Claus Gittinger |
|
3 |
All Rights Reserved |
|
4 |
||
5 |
This software is furnished under a license and may be used |
|
6 |
only in accordance with the terms of that license and with the |
|
7 |
inclusion of the above copyright notice. This software may not |
|
8 |
be provided or otherwise made available to, or used by, any |
|
9 |
other person. No title to or ownership of the software is |
|
10 |
hereby transferred. |
|
11 |
" |
|
12 |
||
13 |
||
14 |
||
15 |
||
16 |
||
17 |
LineSegment subclass:#Arrow |
|
18 |
instanceVariableNames:'arrowHeadPosition arrowHeadLength arrowHeadAngle' |
|
19 |
classVariableNames:'DefaultLength DefaultAngle' |
|
20 |
poolDictionaries:'' |
|
21 |
category:'Graphics-Geometry' |
|
22 |
! |
|
23 |
||
24 |
!Arrow class methodsFor:'documentation'! |
|
25 |
||
26 |
copyright |
|
27 |
" |
|
28 |
COPYRIGHT (c) 1996 by Claus Gittinger |
|
29 |
All Rights Reserved |
|
30 |
||
31 |
This software is furnished under a license and may be used |
|
32 |
only in accordance with the terms of that license and with the |
|
33 |
inclusion of the above copyright notice. This software may not |
|
34 |
be provided or otherwise made available to, or used by, any |
|
35 |
other person. No title to or ownership of the software is |
|
36 |
hereby transferred. |
|
37 |
" |
|
38 |
||
39 |
||
40 |
||
41 |
||
42 |
! |
|
43 |
||
44 |
documentation |
|
45 |
" |
|
46 |
Arrows are just what the name says - a directed LineSegment, which |
|
47 |
draws itself with an arrowHead. The position of the arrowhead can |
|
48 |
be set to be anywhere along the lineSegement (default is at the end). |
|
49 |
||
323 | 50 |
Arrows can be drawn stroked or filled - when filled, only the arrowHead |
51 |
is filled. |
|
52 |
||
318 | 53 |
[author:] |
54 |
Claus Gittinger |
|
55 |
||
56 |
[see also:] |
|
320 | 57 |
Rectangle Polygon EllipticalArc Circle Spline Curve Point |
331 | 58 |
LineSegment ArrowedSpline |
318 | 59 |
GraphicsContext |
331 | 60 |
StrokingWrapper FillingWrapper |
318 | 61 |
" |
62 |
! |
|
63 |
||
64 |
examples |
|
65 |
" |
|
66 |
low level use: |
|
67 |
[exBegin] |
|
68 |
|v a| |
|
69 |
||
70 |
v := (View extent:100@100) openAndWait. |
|
71 |
||
72 |
a := Arrow from:10@10 to:90@90. |
|
73 |
||
74 |
v paint:Color red. |
|
75 |
a displayStrokedOn:v. |
|
76 |
||
77 |
a start:90@10 end:10@90. |
|
78 |
v paint:Color blue. |
|
79 |
a displayStrokedOn:v. |
|
80 |
[exEnd] |
|
81 |
||
325 | 82 |
as component (automatic redraw): |
83 |
[exBegin] |
|
84 |
|v a| |
|
85 |
||
86 |
v := View extent:100@100. |
|
87 |
||
88 |
a := Arrow from:50@50 to:10@10. |
|
89 |
v addComponent:(StrokingWrapper on:a). |
|
90 |
||
91 |
a := Arrow from:50@50 to:90@10. |
|
92 |
v addComponent:(StrokingWrapper on:a). |
|
93 |
||
94 |
a := Arrow from:50@50 to:10@90. |
|
95 |
v addComponent:(StrokingWrapper on:a). |
|
96 |
||
97 |
a := Arrow from:50@50 to:90@90. |
|
98 |
v addComponent:(StrokingWrapper on:a). |
|
99 |
||
100 |
v open |
|
101 |
[exEnd] |
|
102 |
||
103 |
as component filled vs. stroked: |
|
323 | 104 |
[exBegin] |
105 |
|v a| |
|
106 |
||
107 |
v := View extent:100@100. |
|
108 |
||
109 |
a := Arrow from:10@10 to:90@10. |
|
110 |
v addComponent:(StrokingWrapper on:a). |
|
111 |
||
112 |
a := Arrow from:90@20 to:10@20. |
|
113 |
v addComponent:(StrokingWrapper on:a). |
|
114 |
||
115 |
a := Arrow from:10@50 to:90@50. |
|
116 |
v addComponent:(FillingWrapper on:a). |
|
117 |
||
118 |
a := Arrow from:90@60 to:10@60. |
|
119 |
v addComponent:(FillingWrapper on:a). |
|
120 |
||
121 |
v open |
|
122 |
[exEnd] |
|
123 |
||
324 | 124 |
as component (varying lineStyles): |
318 | 125 |
[exBegin] |
126 |
|v a| |
|
127 |
||
128 |
v := View extent:100@100. |
|
129 |
||
130 |
a := Arrow from:10@10 to:90@90. |
|
131 |
v addComponent:(StrokingWrapper on:a). |
|
132 |
||
133 |
a := Arrow from:10@10 to:90@10. |
|
134 |
a arrowHeadPosition:0.5. |
|
135 |
v addComponent:(StrokingWrapper on:a). |
|
136 |
||
137 |
a := Arrow from:90@10 to:10@90. |
|
138 |
v addComponent:((StrokingWrapper on:a) foregroundColor:(Color red)). |
|
139 |
||
140 |
a := Arrow from:10@50 to:90@50. |
|
141 |
a arrowHeadLength:20; arrowHeadAngle:130. |
|
142 |
||
143 |
v addComponent:((StrokingWrapper on:a) |
|
144 |
lineWidth:5; |
|
145 |
foregroundColor:(Color red)). |
|
146 |
||
147 |
a := Arrow from:50@90 to:50@10. |
|
148 |
a arrowHeadLength:10; arrowHeadAngle:170. |
|
149 |
||
150 |
v addComponent:((StrokingWrapper on:a) |
|
151 |
lineWidth:2; |
|
152 |
lineStyle:#dashed; |
|
153 |
foregroundColor:(Color red); |
|
154 |
backgroundColor:(Color yellow)). |
|
155 |
||
156 |
v open. |
|
157 |
[exEnd] |
|
321 | 158 |
varying the position: |
159 |
[exBegin] |
|
160 |
|v a| |
|
161 |
||
323 | 162 |
v := View extent:200@100. |
321 | 163 |
|
323 | 164 |
a := Arrow from:10@10 to:90@10. |
321 | 165 |
a arrowHeadPosition:0. |
166 |
v addComponent:(StrokingWrapper on:a). |
|
167 |
||
168 |
a := Arrow from:10@30 to:90@30. |
|
169 |
a arrowHeadPosition:(1/3). |
|
170 |
v addComponent:(StrokingWrapper on:a). |
|
171 |
||
172 |
a := Arrow from:10@40 to:90@40. |
|
173 |
a arrowHeadPosition:0.5. |
|
174 |
v addComponent:(StrokingWrapper on:a). |
|
175 |
||
176 |
a := Arrow from:10@50 to:90@50. |
|
177 |
a arrowHeadPosition:(2/3). |
|
178 |
v addComponent:(StrokingWrapper on:a). |
|
179 |
||
323 | 180 |
a := Arrow from:10@70 to:90@70. |
181 |
v addComponent:(StrokingWrapper on:a). |
|
182 |
||
183 |
||
184 |
a := Arrow from:100@10 to:150@90. |
|
185 |
a arrowHeadPosition:(1/3). |
|
326 | 186 |
v addComponent:(FillingWrapper on:a). |
323 | 187 |
|
188 |
a := Arrow from:110@10 to:160@90. |
|
189 |
a arrowHeadPosition:(2/3). |
|
326 | 190 |
v addComponent:(FillingWrapper on:a). |
323 | 191 |
|
192 |
a := Arrow from:120@10 to:170@90. |
|
326 | 193 |
v addComponent:(FillingWrapper on:a). |
321 | 194 |
|
195 |
v open. |
|
196 |
[exEnd] |
|
318 | 197 |
" |
198 |
! ! |
|
199 |
||
200 |
!Arrow class methodsFor:'initialization'! |
|
201 |
||
202 |
initialize |
|
203 |
DefaultAngle := 150. |
|
204 |
DefaultLength := 8 |
|
205 |
||
206 |
" |
|
207 |
Arrow initialize |
|
208 |
" |
|
209 |
! ! |
|
210 |
||
321 | 211 |
!Arrow class methodsFor:'accessing defaults'! |
212 |
||
213 |
defaultAngle |
|
214 |
^ DefaultAngle |
|
215 |
! |
|
216 |
||
217 |
defaultLength |
|
218 |
^ DefaultLength |
|
219 |
! ! |
|
220 |
||
318 | 221 |
!Arrow methodsFor:'accessing'! |
222 |
||
223 |
arrowHeadAngle |
|
224 |
"return the arrowHeads angle, in degrees. |
|
225 |
The default is 150 degrees" |
|
226 |
||
227 |
arrowHeadAngle isNil ifTrue:[^ DefaultAngle]. |
|
228 |
^ arrowHeadAngle |
|
229 |
||
230 |
"Modified: 12.5.1996 / 22:48:29 / cg" |
|
231 |
"Created: 12.5.1996 / 22:56:36 / cg" |
|
232 |
! |
|
233 |
||
234 |
arrowHeadAngle:angleInDegrees |
|
235 |
"set the arrowHeads angle, in degrees. |
|
236 |
The default is 150 degrees" |
|
237 |
||
238 |
arrowHeadAngle := angleInDegrees |
|
239 |
||
240 |
"Modified: 12.5.1996 / 22:48:29 / cg" |
|
241 |
"Created: 12.5.1996 / 22:57:47 / cg" |
|
242 |
! |
|
243 |
||
244 |
arrowHeadLength |
|
245 |
"return the arrowHeads length, in pixels. |
|
246 |
The default is 8 pixels" |
|
247 |
||
248 |
arrowHeadPosition isNil ifTrue:[^ DefaultLength]. |
|
249 |
^ arrowHeadLength |
|
250 |
||
251 |
"Created: 12.5.1996 / 22:47:32 / cg" |
|
252 |
"Modified: 12.5.1996 / 22:57:27 / cg" |
|
253 |
! |
|
254 |
||
255 |
arrowHeadLength:pixels |
|
256 |
"set the arrowHeads length, in pixels. |
|
257 |
The default is 8 pixels" |
|
258 |
||
259 |
arrowHeadLength := pixels |
|
260 |
||
261 |
"Created: 12.5.1996 / 22:47:48 / cg" |
|
262 |
"Modified: 12.5.1996 / 23:01:20 / cg" |
|
263 |
! |
|
264 |
||
265 |
arrowHeadPosition |
|
266 |
"return the arrowHeads position, as a fraction of the overall length; |
|
267 |
0 is at the beginning, 1 is at the end, 0.5 is in the center." |
|
268 |
||
269 |
arrowHeadPosition isNil ifTrue:[^ 1]. |
|
270 |
^ arrowHeadPosition |
|
271 |
||
272 |
"Created: 12.5.1996 / 22:46:21 / cg" |
|
273 |
"Modified: 12.5.1996 / 22:57:55 / cg" |
|
274 |
! |
|
275 |
||
276 |
arrowHeadPosition:aFractionOfTheLinesLength |
|
277 |
"set the arrowHeads position, as a fraction of the overall length; |
|
278 |
0 is at the beginning, 1 is at the end, 0.5 is in the center." |
|
279 |
||
280 |
arrowHeadPosition := aFractionOfTheLinesLength |
|
281 |
||
282 |
"Created: 12.5.1996 / 22:46:54 / cg" |
|
283 |
"Modified: 12.5.1996 / 23:01:09 / cg" |
|
284 |
! ! |
|
285 |
||
286 |
!Arrow methodsFor:'displaying'! |
|
287 |
||
354 | 288 |
arrowPoints |
289 |
"return the arrowPoints in a collection" |
|
318 | 290 |
|
333 | 291 |
|arrowHeadPoint len pos angle point grad x1 y1 x2 y2 |
292 |
savedLineStyle atn p1 p2 deriv dX dY| |
|
318 | 293 |
|
294 |
arrowHeadPosition isNil ifTrue:[ |
|
321 | 295 |
pos := 1 |
318 | 296 |
] ifFalse:[ |
321 | 297 |
pos := arrowHeadPosition max:0.0001. |
318 | 298 |
]. |
299 |
||
321 | 300 |
arrowHeadPoint := startPoint + ((endPoint - startPoint) * pos). |
301 |
||
318 | 302 |
len := arrowHeadLength. |
303 |
len isNil ifTrue:[ |
|
304 |
len := DefaultLength |
|
305 |
]. |
|
306 |
||
307 |
angle := arrowHeadAngle. |
|
308 |
angle isNil ifTrue:[ |
|
309 |
angle := DefaultAngle |
|
310 |
]. |
|
311 |
angle := angle degreesToRadians. |
|
312 |
||
333 | 313 |
deriv := arrowHeadPoint - startPoint. |
314 |
dX := deriv x. |
|
315 |
dY := deriv y. |
|
316 |
||
317 |
dX = 0 ifTrue: [ |
|
318 |
grad := 99999999.9 |
|
319 |
] ifFalse: [ |
|
320 |
grad := dY / dX |
|
321 |
]. |
|
322
38c88d4b3976
avoid calling arcTan too often
Claus Gittinger <cg@exept.de>
parents:
321
diff
changeset
|
322 |
|
38c88d4b3976
avoid calling arcTan too often
Claus Gittinger <cg@exept.de>
parents:
321
diff
changeset
|
323 |
atn := grad arcTan. |
333 | 324 |
x1 := len * (angle - atn) cos. |
325 |
y1 := len * (angle - atn) sin. |
|
318 | 326 |
|
333 | 327 |
x2 := len * (angle + atn) cos. |
328 |
y2 := len * (angle + atn) sin. |
|
318 | 329 |
|
333 | 330 |
dX = 0 ifTrue:[ |
331 |
dY > 0 ifTrue:[ |
|
332 |
p1 := (dX + x1) @ (dY - y1). |
|
333 |
p2 := (dX + x2) @ (dY + y2). |
|
334 |
] ifFalse:[ |
|
335 |
p1 := (dX - x1) @ (dY + y1). |
|
336 |
p2 := (dX - x2) @ (dY - y2). |
|
337 |
] |
|
338 |
] ifFalse:[ |
|
339 |
dX > 0 ifTrue:[ |
|
340 |
p1 := (dX + x1) @ (dY - y1). |
|
341 |
p2 := (dX + x2) @ (dY + y2). |
|
342 |
] ifFalse:[ |
|
343 |
p1 := (dX - x1) @ (dY + y1). |
|
344 |
p2 := (dX - x2) @ (dY - y2). |
|
345 |
] |
|
346 |
]. |
|
318 | 347 |
|
333 | 348 |
p1 := startPoint + p1. |
349 |
p2 := startPoint + p2. |
|
323 | 350 |
|
354 | 351 |
^ Array with:p1 with:arrowHeadPoint with:p2. |
352 |
||
353 |
"Created: 12.5.1996 / 23:54:35 / cg" |
|
354 |
"Modified: 13.5.1996 / 20:55:51 / cg" |
|
355 |
! |
|
356 |
||
357 |
displayArrowOn:aGC filled:filled |
|
358 |
"display the receivers arrow in the graphicsContext, aGC" |
|
359 |
||
360 |
|arrowHeadPoint savedLineStyle p1 p2 points| |
|
361 |
||
362 |
super displayStrokedOn:aGC. |
|
363 |
||
364 |
savedLineStyle := aGC lineStyle. |
|
365 |
aGC lineStyle:#solid. |
|
366 |
||
367 |
points := self arrowPoints. |
|
368 |
||
369 |
p1 := points at:1. |
|
370 |
arrowHeadPoint := points at:2. |
|
371 |
p2 := points at:3. |
|
372 |
||
323 | 373 |
filled ifFalse:[ |
374 |
aGC displayLineFrom:arrowHeadPoint to:p1. |
|
375 |
aGC displayLineFrom:arrowHeadPoint to:p2. |
|
376 |
] ifTrue:[ |
|
377 |
aGC fillPolygon:(Array with:p1 with:arrowHeadPoint with:p2). |
|
378 |
]. |
|
318 | 379 |
|
380 |
aGC lineStyle:savedLineStyle. |
|
381 |
||
382 |
" |
|
383 |
|v| |
|
384 |
||
385 |
v := View new openAndWait. |
|
386 |
||
387 |
(Arrow from:10@10 to:50@50) displayStrokedOn:v |
|
388 |
" |
|
389 |
||
323 | 390 |
"Created: 12.5.1996 / 23:54:35 / cg" |
333 | 391 |
"Modified: 13.5.1996 / 20:55:51 / cg" |
323 | 392 |
! |
393 |
||
394 |
displayFilledOn:aGC |
|
395 |
"display the receiver in the graphicsContext, aGC" |
|
396 |
||
397 |
super displayStrokedOn:aGC. |
|
398 |
self displayArrowOn:aGC filled:true |
|
399 |
||
400 |
"Modified: 12.5.1996 / 23:54:52 / cg" |
|
401 |
"Created: 12.5.1996 / 23:58:42 / cg" |
|
402 |
! |
|
403 |
||
404 |
displayStrokedOn:aGC |
|
405 |
"display the receiver in the graphicsContext, aGC" |
|
406 |
||
407 |
super displayStrokedOn:aGC. |
|
408 |
self displayArrowOn:aGC filled:false |
|
409 |
||
410 |
"Modified: 12.5.1996 / 23:54:52 / cg" |
|
318 | 411 |
! ! |
412 |
||
413 |
!Arrow class methodsFor:'documentation'! |
|
414 |
||
415 |
version |
|
354 | 416 |
^ '$Header: /cvs/stx/stx/libbasic2/Arrow.st,v 1.11 1996-05-25 13:54:02 ca Exp $' |
318 | 417 |
! ! |
418 |
Arrow initialize! |