47 |
47 |
48 (aside from that, you will not see any difference from the outside) |
48 (aside from that, you will not see any difference from the outside) |
49 |
49 |
50 Instance variables: |
50 Instance variables: |
51 |
51 |
52 left <Number> the left coordinate (i.e origin x) |
52 left <Number> the left coordinate (i.e origin x) |
53 top <Number> the top coordinate (i.e origin y) |
53 top <Number> the top coordinate (i.e origin y) |
54 width <Number> the width of the rectangle |
54 width <Number> the width of the rectangle |
55 height <Number> the height of the rectangle |
55 height <Number> the height of the rectangle |
56 |
56 |
57 I am not certain, if implementing Rectangle different was a good idea - |
57 I am not certain, if implementing Rectangle different was a good idea - |
58 subclasses may expect things to be different ... |
58 subclasses may expect things to be different ... |
59 Therefore, this may change. |
59 Therefore, this may change. |
60 |
60 |
61 [author:] |
61 [author:] |
62 Claus Gittinger |
62 Claus Gittinger |
63 |
63 |
64 [see also:] |
64 [see also:] |
65 Point Polygon Circle EllipticalArc Spline |
65 Point Polygon Circle EllipticalArc Spline |
66 LayoutOrigin LayoutFrame AlignmentOrigin Layout |
66 LayoutOrigin LayoutFrame AlignmentOrigin Layout |
67 View GraphicsContext StrokingWrapper FillingWrapper |
67 View GraphicsContext StrokingWrapper FillingWrapper |
68 " |
68 " |
69 ! ! |
69 ! ! |
70 |
70 |
71 !Rectangle class methodsFor:'instance creation'! |
71 !Rectangle class methodsFor:'instance creation'! |
72 |
72 |
73 center:centerPoint extent:extentPoint |
73 center:centerPoint extent:extentPoint |
74 "return an instance of me whose center is centerPoint and width |
74 "return an instance of me whose center is centerPoint and width |
75 by height is extentPoint." |
75 by height is extentPoint." |
76 |
76 |
77 ^ self |
77 ^ self |
78 origin:centerPoint - (extentPoint//2) |
78 origin:centerPoint - (extentPoint//2) |
79 extent:extentPoint |
79 extent:extentPoint |
80 ! |
80 ! |
81 |
81 |
82 decodeFromLiteralArray:anArray |
82 decodeFromLiteralArray:anArray |
83 "create & return a new instance from information encoded in anArray. |
83 "create & return a new instance from information encoded in anArray. |
84 Redefined for faster creation." |
84 Redefined for faster creation." |
146 REGISTER OBJ newRect; |
146 REGISTER OBJ newRect; |
147 OBJ t; |
147 OBJ t; |
148 int spc; |
148 int spc; |
149 |
149 |
150 if (__CanDoQuickNew(OHDR_SIZE + 4*sizeof(OBJ))) { /* OBJECT ALLOCATION */ |
150 if (__CanDoQuickNew(OHDR_SIZE + 4*sizeof(OBJ))) { /* OBJECT ALLOCATION */ |
151 if (self == Rectangle) { |
151 if (self == Rectangle) { |
152 /* |
152 /* |
153 * short cut - rectangles are created so often ... |
153 * short cut - rectangles are created so often ... |
154 */ |
154 */ |
155 __qCheckedAlignedNew(newRect, OHDR_SIZE + 4*sizeof(OBJ)); |
155 __qCheckedNew(newRect, OHDR_SIZE + 4*sizeof(OBJ)); |
156 |
156 |
157 __InstPtr(newRect)->o_class = Rectangle; |
157 __InstPtr(newRect)->o_class = Rectangle; |
158 __qSTORE(newRect, Rectangle); |
158 __qSTORE(newRect, Rectangle); |
159 |
159 |
160 __InstPtr(newRect)->i_instvars[0] = left; |
160 __InstPtr(newRect)->i_instvars[0] = left; |
161 __InstPtr(newRect)->i_instvars[1] = top; |
161 __InstPtr(newRect)->i_instvars[1] = top; |
162 __InstPtr(newRect)->i_instvars[2] = w; |
162 __InstPtr(newRect)->i_instvars[2] = w; |
163 __InstPtr(newRect)->i_instvars[3] = h; |
163 __InstPtr(newRect)->i_instvars[3] = h; |
164 |
164 |
165 if (! (__bothSmallInteger(left, top) && |
165 if (! (__bothSmallInteger(left, top) && |
166 __bothSmallInteger(w, h))) { |
166 __bothSmallInteger(w, h))) { |
167 spc = __qSpace(newRect); |
167 spc = __qSpace(newRect); |
168 __STORE_SPC(newRect, left, spc); |
168 __STORE_SPC(newRect, left, spc); |
169 __STORE_SPC(newRect, top, spc); |
169 __STORE_SPC(newRect, top, spc); |
170 __STORE_SPC(newRect, w, spc); |
170 __STORE_SPC(newRect, w, spc); |
171 __STORE_SPC(newRect, h, spc); |
171 __STORE_SPC(newRect, h, spc); |
172 } |
172 } |
173 |
173 |
174 RETURN ( newRect ); |
174 RETURN ( newRect ); |
175 } |
175 } |
176 } |
176 } |
177 %}. |
177 %}. |
178 ^ (self basicNew) left:left top:top width:w height:h |
178 ^ (self basicNew) left:left top:top width:w height:h |
179 ! |
179 ! |
180 |
180 |
210 REGISTER OBJ newRect; |
210 REGISTER OBJ newRect; |
211 OBJ t; |
211 OBJ t; |
212 int spc; |
212 int spc; |
213 |
213 |
214 if (__CanDoQuickNew(OHDR_SIZE + 4*sizeof(OBJ))) { /* OBJECT ALLOCATION */ |
214 if (__CanDoQuickNew(OHDR_SIZE + 4*sizeof(OBJ))) { /* OBJECT ALLOCATION */ |
215 /* |
215 /* |
216 * short cut - rectangles are created so often ... |
216 * short cut - rectangles are created so often ... |
217 */ |
217 */ |
218 if (self == Rectangle) { |
218 if (self == Rectangle) { |
219 if (__isPoint(origin) && __isPoint(extent)) { |
219 if (__isPoint(origin) && __isPoint(extent)) { |
220 __qCheckedAlignedNew(newRect, OHDR_SIZE + 4*sizeof(OBJ)); |
220 __qCheckedNew(newRect, OHDR_SIZE + 4*sizeof(OBJ)); |
221 __InstPtr(newRect)->o_class = Rectangle; |
221 __InstPtr(newRect)->o_class = Rectangle; |
222 __qSTORE(newRect, Rectangle); |
222 __qSTORE(newRect, Rectangle); |
223 spc = __qSpace(newRect); |
223 spc = __qSpace(newRect); |
224 |
224 |
225 t = __PointInstPtr(origin)->p_x; |
225 t = __PointInstPtr(origin)->p_x; |
226 __InstPtr(newRect)->i_instvars[0] = t; |
226 __InstPtr(newRect)->i_instvars[0] = t; |
227 __STORE_SPC(newRect, t, spc); |
227 __STORE_SPC(newRect, t, spc); |
228 |
228 |
229 t = __PointInstPtr(origin)->p_y; |
229 t = __PointInstPtr(origin)->p_y; |
230 __InstPtr(newRect)->i_instvars[1] = t; |
230 __InstPtr(newRect)->i_instvars[1] = t; |
231 __STORE_SPC(newRect, t, spc); |
231 __STORE_SPC(newRect, t, spc); |
232 |
232 |
233 t = __PointInstPtr(extent)->p_x; |
233 t = __PointInstPtr(extent)->p_x; |
234 __InstPtr(newRect)->i_instvars[2] = t; |
234 __InstPtr(newRect)->i_instvars[2] = t; |
235 __STORE_SPC(newRect, t, spc); |
235 __STORE_SPC(newRect, t, spc); |
236 |
236 |
237 t = __PointInstPtr(extent)->p_y; |
237 t = __PointInstPtr(extent)->p_y; |
238 __InstPtr(newRect)->i_instvars[3] = t; |
238 __InstPtr(newRect)->i_instvars[3] = t; |
239 __STORE_SPC(newRect, t, spc); |
239 __STORE_SPC(newRect, t, spc); |
240 RETURN ( newRect ); |
240 RETURN ( newRect ); |
241 } |
241 } |
242 } |
242 } |
243 } |
243 } |
244 %}. |
244 %}. |
245 ^ (self basicNew) origin:origin extent:extent |
245 ^ (self basicNew) origin:origin extent:extent |
246 ! |
246 ! |
247 |
247 |
391 corner |
391 corner |
392 "return the corner" |
392 "return the corner" |
393 |
393 |
394 %{ /* NOCONTEXT */ |
394 %{ /* NOCONTEXT */ |
395 if (self == @global(Rectangle)) { |
395 if (self == @global(Rectangle)) { |
396 OBJ _tleft = __INST(left); |
396 OBJ _tleft = __INST(left); |
397 OBJ _ttop = __INST(top); |
397 OBJ _ttop = __INST(top); |
398 OBJ _twidth = __INST(width); |
398 OBJ _twidth = __INST(width); |
399 OBJ _theight = __INST(height); |
399 OBJ _theight = __INST(height); |
400 |
400 |
401 if (__bothSmallInteger(_tleft, _ttop) |
401 if (__bothSmallInteger(_tleft, _ttop) |
402 && __bothSmallInteger(_twidth, _theight)) { |
402 && __bothSmallInteger(_twidth, _theight)) { |
403 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
403 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
404 OBJ newPoint; |
404 OBJ newPoint; |
405 int spc; |
405 int spc; |
406 int cX = __intVal(_tleft) + __intVal(_twidth); |
406 int cX = __intVal(_tleft) + __intVal(_twidth); |
407 int cY = __intVal(_ttop) + __intVal(_theight); |
407 int cY = __intVal(_ttop) + __intVal(_theight); |
408 |
408 |
409 if (__ISVALIDINTEGER(cX) && __ISVALIDINTEGER(cY)) { |
409 if (__ISVALIDINTEGER(cX) && __ISVALIDINTEGER(cY)) { |
410 __qCheckedAlignedNew(newPoint, sizeof(struct __Point)); |
410 __qCheckedNew(newPoint, sizeof(struct __Point)); |
411 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
411 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
412 __PointInstPtr(newPoint)->p_x = __MKSMALLINT(cX); |
412 __PointInstPtr(newPoint)->p_x = __MKSMALLINT(cX); |
413 __PointInstPtr(newPoint)->p_y = __MKSMALLINT(cY); |
413 __PointInstPtr(newPoint)->p_y = __MKSMALLINT(cY); |
414 RETURN ( newPoint ); |
414 RETURN ( newPoint ); |
415 } |
415 } |
416 } |
416 } |
417 } |
417 } |
418 } |
418 } |
419 %}. |
419 %}. |
420 ^ (left + width) @ (top + height) |
420 ^ (left + width) @ (top + height) |
421 ! |
421 ! |
422 |
422 |
431 "return the extent" |
431 "return the extent" |
432 |
432 |
433 %{ /* NOCONTEXT */ |
433 %{ /* NOCONTEXT */ |
434 |
434 |
435 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
435 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
436 if (self == @global(Rectangle)) { |
436 if (self == @global(Rectangle)) { |
437 OBJ newPoint; |
437 OBJ newPoint; |
438 int spc; |
438 int spc; |
439 OBJ newX = __INST(width); |
439 OBJ newX = __INST(width); |
440 OBJ newY = __INST(height); |
440 OBJ newY = __INST(height); |
441 |
441 |
442 __qCheckedAlignedNew(newPoint, sizeof(struct __Point)); |
442 __qCheckedNew(newPoint, sizeof(struct __Point)); |
443 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
443 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
444 __PointInstPtr(newPoint)->p_x = newX; |
444 __PointInstPtr(newPoint)->p_x = newX; |
445 __PointInstPtr(newPoint)->p_y = newY; |
445 __PointInstPtr(newPoint)->p_y = newY; |
446 if (! __bothSmallInteger(newX, newY)) { |
446 if (! __bothSmallInteger(newX, newY)) { |
447 spc = __qSpace(newPoint); |
447 spc = __qSpace(newPoint); |
448 __STORE_SPC(newPoint, newX, spc); |
448 __STORE_SPC(newPoint, newX, spc); |
449 __STORE_SPC(newPoint, newY, spc); |
449 __STORE_SPC(newPoint, newY, spc); |
450 } |
450 } |
451 RETURN ( newPoint ); |
451 RETURN ( newPoint ); |
452 } |
452 } |
453 } |
453 } |
454 %}. |
454 %}. |
455 ^ Point x:width y:height |
455 ^ Point x:width y:height |
456 ! |
456 ! |
457 |
457 |
553 |
553 |
554 /* |
554 /* |
555 * claus: I am no longer certain, if this primitive is worth the effort |
555 * claus: I am no longer certain, if this primitive is worth the effort |
556 */ |
556 */ |
557 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
557 if (__CanDoQuickNew(sizeof(struct __Point))) { /* OBJECT ALLOCATION */ |
558 if (self == @global(Rectangle)) { |
558 if (self == @global(Rectangle)) { |
559 OBJ newPoint; |
559 OBJ newPoint; |
560 int spc; |
560 int spc; |
561 OBJ newX = __INST(left); |
561 OBJ newX = __INST(left); |
562 OBJ newY = __INST(top); |
562 OBJ newY = __INST(top); |
563 |
563 |
564 __qCheckedAlignedNew(newPoint, sizeof(struct __Point)); |
564 __qCheckedNew(newPoint, sizeof(struct __Point)); |
565 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
565 __InstPtr(newPoint)->o_class = self; __qSTORE(newPoint, self); |
566 __PointInstPtr(newPoint)->p_x = newX; |
566 __PointInstPtr(newPoint)->p_x = newX; |
567 __PointInstPtr(newPoint)->p_y = newY; |
567 __PointInstPtr(newPoint)->p_y = newY; |
568 if (! __bothSmallInteger(newX, newY)) { |
568 if (! __bothSmallInteger(newX, newY)) { |
569 spc = __qSpace(newPoint); |
569 spc = __qSpace(newPoint); |
570 __STORE_SPC(newPoint, newX, spc); |
570 __STORE_SPC(newPoint, newX, spc); |
571 __STORE_SPC(newPoint, newY, spc); |
571 __STORE_SPC(newPoint, newY, spc); |
572 } |
572 } |
573 RETURN ( newPoint ); |
573 RETURN ( newPoint ); |
574 } |
574 } |
575 } |
575 } |
576 %}. |
576 %}. |
577 ^ Point x:left y:top |
577 ^ Point x:left y:top |
578 ! |
578 ! |
579 |
579 |
849 b := (self bottom). |
849 b := (self bottom). |
850 ((l between:0.0 and:1.0) |
850 ((l between:0.0 and:1.0) |
851 and:[(r between:0.0 and:1.0) |
851 and:[(r between:0.0 and:1.0) |
852 and:[(t between:0.0 and:1.0) |
852 and:[(t between:0.0 and:1.0) |
853 and:[(b between:0.0 and:1.0)]]]) ifTrue:[ |
853 and:[(b between:0.0 and:1.0)]]]) ifTrue:[ |
854 newLayout |
854 newLayout |
855 leftFraction:l; |
855 leftFraction:l; |
856 rightFraction:r; |
856 rightFraction:r; |
857 topFraction:t; |
857 topFraction:t; |
858 bottomFraction:b. |
858 bottomFraction:b. |
859 ] ifFalse:[ |
859 ] ifFalse:[ |
860 newLayout |
860 newLayout |
861 leftOffset:l; |
861 leftOffset:l; |
862 rightFraction:0 offset:r; |
862 rightFraction:0 offset:r; |
863 topOffset:t; |
863 topOffset:t; |
864 bottomFraction:0 offset:b. |
864 bottomFraction:0 offset:b. |
865 ]. |
865 ]. |
866 ^ newLayout |
866 ^ newLayout |
867 |
867 |
868 " |
868 " |
869 (0.5@0.5 corner:0.75@0.75) asFractionalLayout |
869 (0.5@0.5 corner:0.75@0.75) asFractionalLayout |
870 (0.5@0.5 corner:0.75@0.75) asOffsetLayout |
870 (0.5@0.5 corner:0.75@0.75) asOffsetLayout |
871 (0.5@0.5 corner:0.75@0.75) asLayout |
871 (0.5@0.5 corner:0.75@0.75) asLayout |
872 (0@0 corner:1@1) asLayout |
872 (0@0 corner:1@1) asLayout |
873 (0@0 corner:1@1) asFractionalLayout |
873 (0@0 corner:1@1) asFractionalLayout |
874 (0@0 corner:1@1) asOffsetLayout |
874 (0@0 corner:1@1) asOffsetLayout |
875 " |
875 " |
876 |
876 |
877 "Modified: 5.6.1996 / 00:45:46 / cg" |
877 "Modified: 5.6.1996 / 00:45:46 / cg" |
878 ! |
878 ! |
879 |
879 |
943 width := (encoding at:4) - left. |
943 width := (encoding at:4) - left. |
944 height := (encoding at:5) - top |
944 height := (encoding at:5) - top |
945 |
945 |
946 |
946 |
947 " |
947 " |
948 Rectangle new fromLiteralArrayEncoding:#(Rectangle 100 200 300 500) |
948 Rectangle new fromLiteralArrayEncoding:#(Rectangle 100 200 300 500) |
949 " |
949 " |
950 ! |
950 ! |
951 |
951 |
952 literalArrayEncoding |
952 literalArrayEncoding |
953 "encode myself as an array, from which a copy of the receiver |
953 "encode myself as an array, from which a copy of the receiver |
954 can be reconstructed with #decodeAsLiteralArray. |
954 can be reconstructed with #decodeAsLiteralArray. |
955 The encoding is: (Rectangle orgX orgY cornX cornY)" |
955 The encoding is: (Rectangle orgX orgY cornX cornY)" |
956 |
956 |
957 ^ Array |
957 ^ Array |
958 with:#Rectangle |
958 with:#Rectangle |
959 with:left |
959 with:left |
960 with:top |
960 with:top |
961 with:(left + width) |
961 with:(left + width) |
962 with:(top + height) |
962 with:(top + height) |
963 |
963 |
964 |
964 |
965 " |
965 " |
966 Rectangle new fromLiteralArrayEncoding:#(Rectangle 100 200 300 500) |
966 Rectangle new fromLiteralArrayEncoding:#(Rectangle 100 200 300 500) |
967 (100@200 corner:300@500) literalArrayEncoding |
967 (100@200 corner:300@500) literalArrayEncoding |
968 " |
968 " |
969 |
969 |
970 "Modified: 1.9.1995 / 02:16:54 / claus" |
970 "Modified: 1.9.1995 / 02:16:54 / claus" |
971 "Modified: 22.4.1996 / 13:00:36 / cg" |
971 "Modified: 22.4.1996 / 13:00:36 / cg" |
972 ! |
972 ! |
973 |
973 |
974 rectangleRelativeTo:aRectangle preferred:prefRectHolder |
974 rectangleRelativeTo:aRectangle preferred:prefRectHolder |
975 "compute a displayRectangle, treating the receiver like a |
975 "compute a displayRectangle, treating the receiver like a |
976 layoutFrame. |
976 layoutFrame. |
977 This allows rectangles to be used interchangable with Layouts." |
977 This allows rectangles to be used interchangable with Layouts." |
978 |
978 |
979 ^ (self asLayout) rectangleRelativeTo:aRectangle preferred:prefRectHolder |
979 ^ (self asLayout) rectangleRelativeTo:aRectangle preferred:prefRectHolder |
980 |
980 |
981 " |
981 " |
982 (10@20 corner:20@30) rectangleRelativeTo:(0@0 corner:100@100) preferred:(0@0 corner:50@50) |
982 (10@20 corner:20@30) rectangleRelativeTo:(0@0 corner:100@100) preferred:(0@0 corner:50@50) |
983 |
983 |
984 (0.5@0.5) rectangleRelativeTo:(0@0 corner:100@100) preferred:(0@0 corner:50@50) |
984 (0.5@0.5) rectangleRelativeTo:(0@0 corner:100@100) preferred:(0@0 corner:50@50) |
985 " |
985 " |
986 |
986 |
987 "Modified: / 27.5.1998 / 10:20:20 / cg" |
987 "Modified: / 27.5.1998 / 10:20:20 / cg" |
988 ! ! |
988 ! ! |
989 |
989 |
1218 * speeds that up by almost a factor of 2 ... |
1218 * speeds that up by almost a factor of 2 ... |
1219 */ |
1219 */ |
1220 OBJ slf = self; |
1220 OBJ slf = self; |
1221 OBJ rct = aRectangle; |
1221 OBJ rct = aRectangle; |
1222 |
1222 |
1223 if (__isNonNilObject(rct) |
1223 if (__isNonNilObject(rct) |
1224 && __qClass(rct) == Rectangle) { |
1224 && __qClass(rct) == Rectangle) { |
1225 OBJ r_l, r_w, r_t, r_h, l, w, t, h; |
1225 OBJ r_l, r_w, r_t, r_h, l, w, t, h; |
1226 INT r_ir, r_il, r_ib, r_it; |
1226 INT r_ir, r_il, r_ib, r_it; |
1227 INT il, it, ir, ib, iw, ih; |
1227 INT il, it, ir, ib, iw, ih; |
1228 |
1228 |
1229 r_l = __OINST(rct, left); |
1229 r_l = __OINST(rct, left); |
1230 l = __OINST(slf, left); |
1230 l = __OINST(slf, left); |
1231 if (__bothSmallInteger(r_l, l)) { |
1231 if (__bothSmallInteger(r_l, l)) { |
1232 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1232 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1233 il = (INT)(l); |
1233 il = (INT)(l); |
1234 r_il = (INT)(r_l); |
1234 r_il = (INT)(r_l); |
1235 #else |
1235 #else |
1236 il = __intVal(l); |
1236 il = __intVal(l); |
1237 r_il = __intVal(r_l); |
1237 r_il = __intVal(r_l); |
1238 #endif |
1238 #endif |
1239 if (il > r_il) { RETURN (false); } /* left > aRectangle left */ |
1239 if (il > r_il) { RETURN (false); } /* left > aRectangle left */ |
1240 |
1240 |
1241 r_t = __OINST(rct, top); |
1241 r_t = __OINST(rct, top); |
1242 t = __OINST(slf, top); |
1242 t = __OINST(slf, top); |
1243 if (__bothSmallInteger(r_t, t)) { |
1243 if (__bothSmallInteger(r_t, t)) { |
1244 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1244 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1245 it = (INT)(t); |
1245 it = (INT)(t); |
1246 r_it = (INT)(r_t); |
1246 r_it = (INT)(r_t); |
1247 #else |
1247 #else |
1248 it = __intVal(t); |
1248 it = __intVal(t); |
1249 r_it = __intVal(r_t); |
1249 r_it = __intVal(r_t); |
1250 #endif |
1250 #endif |
1251 if (it > r_it) { RETURN (false); } /* top > aRectangle top */ |
1251 if (it > r_it) { RETURN (false); } /* top > aRectangle top */ |
1252 |
1252 |
1253 r_w = __OINST(rct, width); |
1253 r_w = __OINST(rct, width); |
1254 w = __OINST(slf, width); |
1254 w = __OINST(slf, width); |
1255 if (__bothSmallInteger(r_w, w)) { |
1255 if (__bothSmallInteger(r_w, w)) { |
1256 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1256 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1257 ir = il + (INT)(w); |
1257 ir = il + (INT)(w); |
1258 r_ir = r_il + (INT)(r_w); |
1258 r_ir = r_il + (INT)(r_w); |
1259 #else |
1259 #else |
1260 ir = il + __intVal(w); |
1260 ir = il + __intVal(w); |
1261 r_ir = r_il + __intVal(r_w); |
1261 r_ir = r_il + __intVal(r_w); |
1262 #endif |
1262 #endif |
1263 if (ir < r_ir) { RETURN (false); } /* (left + width) < aRectangle right */ |
1263 if (ir < r_ir) { RETURN (false); } /* (left + width) < aRectangle right */ |
1264 |
1264 |
1265 r_h = __OINST(rct, height); |
1265 r_h = __OINST(rct, height); |
1266 h = __OINST(slf, height); |
1266 h = __OINST(slf, height); |
1267 if (__bothSmallInteger(r_h, h)) { |
1267 if (__bothSmallInteger(r_h, h)) { |
1268 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1268 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1269 ib = it + (INT)(h); |
1269 ib = it + (INT)(h); |
1270 r_ib = r_it + (INT)(r_h); |
1270 r_ib = r_it + (INT)(r_h); |
1271 #else |
1271 #else |
1272 ib = it + __intVal(h); |
1272 ib = it + __intVal(h); |
1273 r_ib = r_it + __intVal(r_h); |
1273 r_ib = r_it + __intVal(r_h); |
1274 #endif |
1274 #endif |
1275 if (ib < r_ib) { RETURN (false); } /* (top + height) < aRectangle bottom */ |
1275 if (ib < r_ib) { RETURN (false); } /* (top + height) < aRectangle bottom */ |
1276 RETURN (true); |
1276 RETURN (true); |
1277 } |
1277 } |
1278 } |
1278 } |
1279 } |
1279 } |
1280 } |
1280 } |
1281 } |
1281 } |
1282 %}. |
1282 %}. |
1283 (left <= aRectangle left) ifTrue:[ |
1283 (left <= aRectangle left) ifTrue:[ |
1284 ((left + width) >= aRectangle right) ifTrue:[ |
1284 ((left + width) >= aRectangle right) ifTrue:[ |
1285 (top <= aRectangle top) ifTrue:[ |
1285 (top <= aRectangle top) ifTrue:[ |
1286 ((top + height) >= aRectangle bottom) ifTrue:[ |
1286 ((top + height) >= aRectangle bottom) ifTrue:[ |
1287 ^ true |
1287 ^ true |
1288 ] |
1288 ] |
1289 ] |
1289 ] |
1290 ] |
1290 ] |
1291 ]. |
1291 ]. |
1292 ^ false |
1292 ^ false |
1293 |
1293 |
1294 " |
1294 " |
1295 (0@0 corner:100@100) contains:(10@10 corner:90@90) |
1295 (0@0 corner:100@100) contains:(10@10 corner:90@90) |
1296 (0@0 corner:100@100) contains:(10@10 corner:100@100) |
1296 (0@0 corner:100@100) contains:(10@10 corner:100@100) |
1297 (0@0 corner:100@100) contains:(10@10 corner:110@100) |
1297 (0@0 corner:100@100) contains:(10@10 corner:110@100) |
1298 (0@0 corner:100@100) contains:(10@10 corner:100@110) |
1298 (0@0 corner:100@100) contains:(10@10 corner:100@110) |
1299 (10@10 corner:100@100) contains:(0@10 corner:100@100) |
1299 (10@10 corner:100@100) contains:(0@10 corner:100@100) |
1300 " |
1300 " |
1301 ! |
1301 ! |
1302 |
1302 |
1303 containsPoint:aPoint |
1303 containsPoint:aPoint |
1304 "return true, if the argument, aPoint is contained in the receiver" |
1304 "return true, if the argument, aPoint is contained in the receiver" |
1365 * speeds up drawing by almost a factor of 2 ... |
1365 * speeds up drawing by almost a factor of 2 ... |
1366 */ |
1366 */ |
1367 OBJ slf = self; |
1367 OBJ slf = self; |
1368 OBJ rct = aRectangle; |
1368 OBJ rct = aRectangle; |
1369 |
1369 |
1370 if (__isNonNilObject(rct) |
1370 if (__isNonNilObject(rct) |
1371 && __qClass(rct) == Rectangle) { |
1371 && __qClass(rct) == Rectangle) { |
1372 OBJ r_l, r_w, r_t, r_h, l, w, t, h; |
1372 OBJ r_l, r_w, r_t, r_h, l, w, t, h; |
1373 INT r_ir, r_il, r_ib, r_it; |
1373 INT r_ir, r_il, r_ib, r_it; |
1374 INT il, it, ir, ib, iw, ih; |
1374 INT il, it, ir, ib, iw, ih; |
1375 |
1375 |
1376 r_l = __OINST(rct, left); |
1376 r_l = __OINST(rct, left); |
1377 r_w = __OINST(rct, width); |
1377 r_w = __OINST(rct, width); |
1378 |
1378 |
1379 if (__bothSmallInteger(r_l, r_w)) { |
1379 if (__bothSmallInteger(r_l, r_w)) { |
1380 r_t = __OINST(rct, top); |
1380 r_t = __OINST(rct, top); |
1381 r_h = __OINST(rct, height); |
1381 r_h = __OINST(rct, height); |
1382 |
1382 |
1383 l = __OINST(slf, left); |
1383 l = __OINST(slf, left); |
1384 w = __OINST(slf, width); |
1384 w = __OINST(slf, width); |
1385 |
1385 |
1386 if (__bothSmallInteger(l, w)) { |
1386 if (__bothSmallInteger(l, w)) { |
1387 t = __OINST(slf, top); |
1387 t = __OINST(slf, top); |
1388 h = __OINST(slf, height); |
1388 h = __OINST(slf, height); |
1389 |
1389 |
1390 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1390 #ifndef POSITIVE_ADDRESSES /* tag in low-bit */ |
1391 r_il = (INT)(r_l); |
1391 r_il = (INT)(r_l); |
1392 r_ir = r_il + (INT)(r_w) - 1; |
1392 r_ir = r_il + (INT)(r_w) - 1; |
1393 il = (INT)(l); |
1393 il = (INT)(l); |
1394 if (r_ir < il) { RETURN (false); } |
1394 if (r_ir < il) { RETURN (false); } |
1395 ir = il + (INT)(w) - 1; |
1395 ir = il + (INT)(w) - 1; |
1396 if (r_il > ir) { RETURN (false); } |
1396 if (r_il > ir) { RETURN (false); } |
1397 #else /* tag in hi-bit */ |
1397 #else /* tag in hi-bit */ |
1398 r_il = __intVal(r_l); |
1398 r_il = __intVal(r_l); |
1399 r_ir = r_il + __intVal(r_w); /* aRectangle right */ |
1399 r_ir = r_il + __intVal(r_w); /* aRectangle right */ |
1400 il = __intVal(l); |
1400 il = __intVal(l); |
1401 if (r_ir < il) { RETURN (false); } /* (aRectangle right) < left */ |
1401 if (r_ir < il) { RETURN (false); } /* (aRectangle right) < left */ |
1402 |
1402 |
1403 ir = il + __intVal(w); |
1403 ir = il + __intVal(w); |
1404 if (r_il > ir) { RETURN (false); } /* (aRectangle left) > r */ |
1404 if (r_il > ir) { RETURN (false); } /* (aRectangle left) > r */ |
1405 #endif |
1405 #endif |
1406 |
1406 |
1407 if (__bothSmallInteger(r_t, r_h)) { |
1407 if (__bothSmallInteger(r_t, r_h)) { |
1408 if (__bothSmallInteger(t, h)) { |
1408 if (__bothSmallInteger(t, h)) { |
1409 #ifndef POSITIVE_ADDRESSES |
1409 #ifndef POSITIVE_ADDRESSES |
1410 r_it = (INT)(r_t); |
1410 r_it = (INT)(r_t); |
1411 r_ib = r_it + (INT)(r_h) - 1; /* aRectangle bottom */ |
1411 r_ib = r_it + (INT)(r_h) - 1; /* aRectangle bottom */ |
1412 it = (INT)(t); |
1412 it = (INT)(t); |
1413 if (r_ib < it) { RETURN (false); } /* (aRectangle bottom) < top */ |
1413 if (r_ib < it) { RETURN (false); } /* (aRectangle bottom) < top */ |
1414 |
1414 |
1415 ib = it + (INT)(h) - 1; |
1415 ib = it + (INT)(h) - 1; |
1416 if (r_it > ib) { RETURN (false); } /* (aRectangle top) > b */ |
1416 if (r_it > ib) { RETURN (false); } /* (aRectangle top) > b */ |
1417 #else |
1417 #else |
1418 r_it = __intVal(r_t); |
1418 r_it = __intVal(r_t); |
1419 r_ib = r_it + __intVal(r_h); /* aRectangle bottom */ |
1419 r_ib = r_it + __intVal(r_h); /* aRectangle bottom */ |
1420 it = __intVal(t); |
1420 it = __intVal(t); |
1421 if (r_ib < it) { RETURN (false); } /* (aRectangle bottom) < top */ |
1421 if (r_ib < it) { RETURN (false); } /* (aRectangle bottom) < top */ |
1422 |
1422 |
1423 ib = it + __intVal(h); |
1423 ib = it + __intVal(h); |
1424 if (r_it > ib) { RETURN (false); } /* (aRectangle top) > b */ |
1424 if (r_it > ib) { RETURN (false); } /* (aRectangle top) > b */ |
1425 #endif |
1425 #endif |
1426 RETURN (true); |
1426 RETURN (true); |
1427 } |
1427 } |
1428 } |
1428 } |
1429 } |
1429 } |
1430 } |
1430 } |
1431 } |
1431 } |
1432 %}. |
1432 %}. |
1433 (aRectangle right) < left ifTrue:[^ false]. |
1433 (aRectangle right) < left ifTrue:[^ false]. |
1434 (aRectangle bottom) < top ifTrue:[^ false]. |
1434 (aRectangle bottom) < top ifTrue:[^ false]. |
1435 r := left + width. |
1435 r := left + width. |
1495 origin translated by the argument, aPoint" |
1495 origin translated by the argument, aPoint" |
1496 |
1496 |
1497 |amountPoint| |
1497 |amountPoint| |
1498 |
1498 |
1499 (aPoint isMemberOf:SmallInteger) ifTrue:[ |
1499 (aPoint isMemberOf:SmallInteger) ifTrue:[ |
1500 "/ this is an stc optimization |
1500 "/ this is an stc optimization |
1501 ^ Rectangle |
1501 ^ Rectangle |
1502 left:(left - aPoint) |
1502 left:(left - aPoint) |
1503 top:(top - aPoint) |
1503 top:(top - aPoint) |
1504 width:width |
1504 width:width |
1505 height:height |
1505 height:height |
1506 ]. |
1506 ]. |
1507 |
1507 |
1508 amountPoint := aPoint asPoint. |
1508 amountPoint := aPoint asPoint. |
1509 ^ Rectangle left:(left - amountPoint x) |
1509 ^ Rectangle left:(left - amountPoint x) |
1510 top:(top - amountPoint y) |
1510 top:(top - amountPoint y) |
1511 width:width |
1511 width:width |
1512 height:height |
1512 height:height |
1513 |
1513 |
1514 "Modified: 25.1.1997 / 17:29:53 / cg" |
1514 "Modified: 25.1.1997 / 17:29:53 / cg" |
1515 "Created: 25.1.1997 / 17:30:21 / cg" |
1515 "Created: 25.1.1997 / 17:30:21 / cg" |
1516 ! |
1516 ! |
1517 |
1517 |
1518 areasOutside: aRectangle |
1518 areasOutside: aRectangle |
1519 "Answer an Array of Rectangles comprising the parts of the receiver not |
1519 "Answer an Array of Rectangles comprising the parts of the receiver not |
1520 intersecting aRectangle." |
1520 intersecting aRectangle." |
1521 |
1521 |
1522 | areas yOrigin yCorner origin corner| |
1522 | areas yOrigin yCorner origin corner| |
1523 |
1523 |
1524 origin := self origin. |
1524 origin := self origin. |
1525 corner := self corner. |
1525 corner := self corner. |
1526 |
1526 |
1527 "Make sure the intersection is non-empty" |
1527 "Make sure the intersection is non-empty" |
1528 (origin <= aRectangle corner and: [aRectangle origin <= corner]) |
1528 (origin <= aRectangle corner and: [aRectangle origin <= corner]) |
1529 ifFalse: [^ Array with: self]. |
1529 ifFalse: [^ Array with: self]. |
1530 areas := OrderedCollection new. |
1530 areas := OrderedCollection new. |
1531 aRectangle origin y > origin y |
1531 aRectangle origin y > origin y |
1532 ifTrue: [areas addLast: (origin corner: corner x @ (yOrigin := aRectangle origin y))] |
1532 ifTrue: [areas addLast: (origin corner: corner x @ (yOrigin := aRectangle origin y))] |
1533 ifFalse: [yOrigin := origin y]. |
1533 ifFalse: [yOrigin := origin y]. |
1534 aRectangle corner y < corner y |
1534 aRectangle corner y < corner y |
1535 ifTrue: [areas addLast: (origin x @ (yCorner := aRectangle corner y) corner: corner)] |
1535 ifTrue: [areas addLast: (origin x @ (yCorner := aRectangle corner y) corner: corner)] |
1536 ifFalse: [yCorner := corner y]. |
1536 ifFalse: [yCorner := corner y]. |
1537 aRectangle origin x > origin x |
1537 aRectangle origin x > origin x |
1538 ifTrue: [areas addLast: (origin x @ yOrigin corner: aRectangle origin x @ yCorner)]. |
1538 ifTrue: [areas addLast: (origin x @ yOrigin corner: aRectangle origin x @ yCorner)]. |
1539 aRectangle corner x < corner x |
1539 aRectangle corner x < corner x |
1540 ifTrue: [areas addLast: (aRectangle corner x @ yOrigin corner: corner x @ yCorner)]. |
1540 ifTrue: [areas addLast: (aRectangle corner x @ yOrigin corner: corner x @ yCorner)]. |
1541 ^areas |
1541 ^areas |
1542 |
1542 |
1543 "/ cg: the old code below was wrong ... |
1543 "/ cg: the old code below was wrong ... |
1544 |
1544 |
1545 "/ "---------------------------------------------------------------- |
1545 "/ "---------------------------------------------------------------- |
1546 "/ | added for GNU-ST compatibility |
1546 "/ | added for GNU-ST compatibility |
1547 "/ | |
1547 "/ | |
1548 "/ | author: Doug McCallum <uunet!!ico.isc.com!!dougm> |
1548 "/ | author: Doug McCallum <uunet!!ico.isc.com!!dougm> |
1549 "/ | |
1549 "/ | |
1550 "/ |areasOutside: aRectangle |
1550 "/ |areasOutside: aRectangle |
1551 "/ | most complicated of the Rectangle primitives |
1551 "/ | most complicated of the Rectangle primitives |
1552 "/ | The basic methodology is to first determine that there is an |
1552 "/ | The basic methodology is to first determine that there is an |
1553 "/ | intersection by finding the overlapping rectangle. From the |
1553 "/ | intersection by finding the overlapping rectangle. From the |
1554 "/ | overlapping rectangle, first determine if it runs along an edge. |
1554 "/ | overlapping rectangle, first determine if it runs along an edge. |
1555 "/ | If it doesn't, extend the rectangle up to the top edge and add |
1555 "/ | If it doesn't, extend the rectangle up to the top edge and add |
1556 "/ | the new rectangle to the collection and start the rest of the |
1556 "/ | the new rectangle to the collection and start the rest of the |
1557 "/ | process. If the left edge does not touch the left edge of self, |
1557 "/ | process. If the left edge does not touch the left edge of self, |
1558 "/ | extend it to the edge saving the new rectangle. Then do the |
1558 "/ | extend it to the edge saving the new rectangle. Then do the |
1559 "/ | same to the right edge. Then check top and bottom edges. Most |
1559 "/ | same to the right edge. Then check top and bottom edges. Most |
1560 "/ | of the time only 2 or 3 rectangles get formed, occasionally 4. |
1560 "/ | of the time only 2 or 3 rectangles get formed, occasionally 4. |
1561 "/ | It should be possible to never get more than 3 but requires more |
1561 "/ | It should be possible to never get more than 3 but requires more |
1562 "/ | work. |
1562 "/ | work. |
1563 "/ ----------------------------------------------------------------" |
1563 "/ ----------------------------------------------------------------" |
1567 "/ iRect := self intersect: aRectangle. |
1567 "/ iRect := self intersect: aRectangle. |
1568 "/ iRect isNil ifTrue: [^nil]. "case of no intersection" |
1568 "/ iRect isNil ifTrue: [^nil]. "case of no intersection" |
1569 "/ "the collect collection gathers Rectangles" |
1569 "/ "the collect collection gathers Rectangles" |
1570 "/ collect := OrderedCollection new: 4. |
1570 "/ collect := OrderedCollection new: 4. |
1571 "/ "is it floating or on the edge?" |
1571 "/ "is it floating or on the edge?" |
1572 "/ (((((iRect top) ~= self top) |
1572 "/ (((((iRect top) ~= self top) |
1573 "/ and: [ (iRect bottom) ~= self bottom ]) |
1573 "/ and: [ (iRect bottom) ~= self bottom ]) |
1574 "/ and: [ (iRect left) ~= self left ]) |
1574 "/ and: [ (iRect left) ~= self left ]) |
1575 "/ and: [ (iRect right) ~= self right ] ) |
1575 "/ and: [ (iRect right) ~= self right ] ) |
1576 "/ ifTrue: "entirely in the center." |
1576 "/ ifTrue: "entirely in the center." |
1577 "/ [tmp := Rectangle origin: (Point x: iRect left y: self top) |
1577 "/ [tmp := Rectangle origin: (Point x: iRect left y: self top) |
1664 r insetBy:( 10@10 corner:20@20 ) |
1664 r insetBy:( 10@10 corner:20@20 ) |
1665 " |
1665 " |
1666 ! |
1666 ! |
1667 |
1667 |
1668 insetOriginBy:originDelta cornerBy:cornerDelta |
1668 insetOriginBy:originDelta cornerBy:cornerDelta |
1669 "return a new rectangle which is inset by originDelta |
1669 "return a new rectangle which is inset by originDelta |
1670 and cornerDelta; both may be instances of Point or Number" |
1670 and cornerDelta; both may be instances of Point or Number" |
1671 |
1671 |
1672 ^ Rectangle |
1672 ^ Rectangle |
1673 origin:(left @ top) + originDelta asPoint |
1673 origin:(left @ top) + originDelta asPoint |
1674 corner:(self corner - cornerDelta asPoint) |
1674 corner:(self corner - cornerDelta asPoint) |
1675 " |
1675 " |
1676 |r| |
1676 |r| |
1677 r := Rectangle origin:10@10 corner:100@100. |
1677 r := Rectangle origin:10@10 corner:100@100. |
1678 r insetOriginBy:5 cornerBy:10. |
1678 r insetOriginBy:5 cornerBy:10. |
1679 r insetOriginBy:10@5 cornerBy:10. |
1679 r insetOriginBy:10@5 cornerBy:10. |
1680 r insetOriginBy:10 cornerBy:10@5. |
1680 r insetOriginBy:10 cornerBy:10@5. |
1681 r insetOriginBy:10@10 cornerBy:20@20. |
1681 r insetOriginBy:10@10 cornerBy:20@20. |
1682 " |
1682 " |
1683 ! |
1683 ! |
1684 |
1684 |
1685 intersect:aRectangle |
1685 intersect:aRectangle |
1686 "return a new rectangle covering the intersection of the receiver |
1686 "return a new rectangle covering the intersection of the receiver |
1687 and the argument, aRectangle (i.e. the area covered by both). |
1687 and the argument, aRectangle (i.e. the area covered by both). |
1688 the rectangles must intersect for a valid return" |
1688 the rectangles must intersect for a valid return" |
1689 |
1689 |
1690 ^ Rectangle left:(left max:(aRectangle left)) |
1690 ^ Rectangle left:(left max:(aRectangle left)) |
1691 right:((left + width) min:(aRectangle right)) |
1691 right:((left + width) min:(aRectangle right)) |
1692 top:(top max:(aRectangle top)) |
1692 top:(top max:(aRectangle top)) |
1693 bottom:((top + height) min:(aRectangle bottom)) |
1693 bottom:((top + height) min:(aRectangle bottom)) |
1694 |
1694 |
1695 " |
1695 " |
1696 |r1 r2| |
1696 |r1 r2| |
1697 |
1697 |
1698 r1 := Rectangle origin:10@10 corner:100@100. |
1698 r1 := Rectangle origin:10@10 corner:100@100. |
1700 r1 intersect:r2 |
1700 r1 intersect:r2 |
1701 " |
1701 " |
1702 ! |
1702 ! |
1703 |
1703 |
1704 merge:aRectangle |
1704 merge:aRectangle |
1705 "return a new rectangle covering both the receiver |
1705 "return a new rectangle covering both the receiver |
1706 and the argument, aRectangle" |
1706 and the argument, aRectangle" |
1707 |
1707 |
1708 ^ Rectangle left:(left min:(aRectangle left)) |
1708 ^ Rectangle left:(left min:(aRectangle left)) |
1709 right:((left + width) max:(aRectangle right)) |
1709 right:((left + width) max:(aRectangle right)) |
1710 top:(top min:(aRectangle top)) |
1710 top:(top min:(aRectangle top)) |
1711 bottom:((top + height) max:(aRectangle bottom)) |
1711 bottom:((top + height) max:(aRectangle bottom)) |
1712 |
1712 |
1713 " |
1713 " |
1714 (Rectangle origin:10@10 corner:100@100) |
1714 (Rectangle origin:10@10 corner:100@100) |
1715 merge:(Rectangle origin:20@20 corner:110@110) |
1715 merge:(Rectangle origin:20@20 corner:110@110) |
1716 |
1716 |
1717 (Rectangle origin:10@10 corner:100@100) |
1717 (Rectangle origin:10@10 corner:100@100) |
1718 merge:(Rectangle origin:20@20 corner:100@100) |
1718 merge:(Rectangle origin:20@20 corner:100@100) |
1719 " |
1719 " |
1720 ! |
1720 ! |
1721 |
1721 |
1722 nonIntersections:aRectangle |
1722 nonIntersections:aRectangle |
1723 "this is the same as areasOutside: - for ST/V compatibility only" |
1723 "this is the same as areasOutside: - for ST/V compatibility only" |
1724 |
1724 |
1725 ^ self areasOutside:aRectangle |
1725 ^ self areasOutside:aRectangle |
1726 ! |
1726 ! |
1727 |
1727 |
1728 quickMerge: aRectangle |
1728 quickMerge: aRectangle |
1729 "return the receiver if it encloses the given rectangle, |
1729 "return the receiver if it encloses the given rectangle, |
1730 or the merge of the two rectangles if it doesn't. |
1730 or the merge of the two rectangles if it doesn't. |
1731 This method is an optimized version of merge: to reduce extra rectangle creations." |
1731 This method is an optimized version of merge: to reduce extra rectangle creations." |
1732 |
1732 |
1733 | useRcvr rLeft rTop rRight rBottom minX maxX minY maxY | |
1733 | useRcvr rLeft rTop rRight rBottom minX maxX minY maxY | |
1734 |
1734 |
1735 useRcvr := true. |
1735 useRcvr := true. |
1747 rTop < minY ifTrue: [useRcvr := false. minY := rTop]. |
1747 rTop < minY ifTrue: [useRcvr := false. minY := rTop]. |
1748 maxY := self bottom. |
1748 maxY := self bottom. |
1749 rBottom > maxY ifTrue: [useRcvr := false. maxY := rBottom]. |
1749 rBottom > maxY ifTrue: [useRcvr := false. maxY := rBottom]. |
1750 |
1750 |
1751 useRcvr ifTrue: [ |
1751 useRcvr ifTrue: [ |
1752 ^ self |
1752 ^ self |
1753 ]. |
1753 ]. |
1754 |
1754 |
1755 minX = rLeft ifTrue:[ |
1755 minX = rLeft ifTrue:[ |
1756 maxX = rRight ifTrue:[ |
1756 maxX = rRight ifTrue:[ |
1757 minY = rTop ifTrue:[ |
1757 minY = rTop ifTrue:[ |
1758 maxY = rBottom ifTrue:[ |
1758 maxY = rBottom ifTrue:[ |
1759 ^ aRectangle |
1759 ^ aRectangle |
1760 ]. |
1760 ]. |
1761 ]. |
1761 ]. |
1762 ]. |
1762 ]. |
1763 ]. |
1763 ]. |
1764 |
1764 |
1765 ^ Rectangle left:minX top:minY right:maxX bottom:maxY. |
1765 ^ Rectangle left:minX top:minY right:maxX bottom:maxY. |
1766 |
1766 |
1767 " |
1767 " |
1768 (Rectangle origin:10@10 corner:100@100) |
|
1769 quickMerge:(Rectangle origin:20@20 corner:110@110) |
|
1770 |
|
1771 (Rectangle origin:10@10 corner:100@100) |
1768 (Rectangle origin:10@10 corner:100@100) |
1772 quickMerge:(Rectangle origin:20@20 corner:100@100) |
1769 quickMerge:(Rectangle origin:20@20 corner:110@110) |
|
1770 |
|
1771 (Rectangle origin:10@10 corner:100@100) |
|
1772 quickMerge:(Rectangle origin:20@20 corner:100@100) |
1773 " |
1773 " |
1774 ! |
1774 ! |
1775 |
1775 |
1776 scaledBy:scale |
1776 scaledBy:scale |
1777 "return a new rectangle which is the receiver |
1777 "return a new rectangle which is the receiver |
1778 scaled by scale" |
1778 scaled by scale" |
1779 |
1779 |
1780 |scalePoint sx sy| |
1780 |scalePoint sx sy| |
1781 |
1781 |
1782 (scale isMemberOf:SmallInteger) ifTrue:[ |
1782 (scale isMemberOf:SmallInteger) ifTrue:[ |
1783 "/ this is an stc optimization |
1783 "/ this is an stc optimization |
1784 ^ Rectangle left:left * scale |
1784 ^ Rectangle left:left * scale |
1785 top:top * scale |
1785 top:top * scale |
1786 width:width * scale |
1786 width:width * scale |
1787 height:height * scale |
1787 height:height * scale |
1788 ]. |
1788 ]. |
1789 |
1789 |
1790 scalePoint := scale asPoint. |
1790 scalePoint := scale asPoint. |
1791 sx := scalePoint x. |
1791 sx := scalePoint x. |
1792 sy := scalePoint y. |
1792 sy := scalePoint y. |
1793 ^ Rectangle left:left * sx |
1793 ^ Rectangle left:left * sx |
1794 top:top * sy |
1794 top:top * sy |
1795 width:width * sx |
1795 width:width * sx |
1796 height:height * sy |
1796 height:height * sy |
1797 " |
1797 " |
1798 (Rectangle origin:10@10 corner:50@50) scaledBy:2 |
1798 (Rectangle origin:10@10 corner:50@50) scaledBy:2 |
1799 " |
1799 " |
1800 |
1800 |
1801 "it is NOT destructive:" |
1801 "it is NOT destructive:" |
1802 " |
1802 " |
1803 |r1 r2| |
1803 |r1 r2| |
1804 |
1804 |
1805 r1 := Rectangle origin:10@10 corner:50@50. |
1805 r1 := Rectangle origin:10@10 corner:50@50. |
1806 r2 := r1 scaledBy:2. |
1806 r2 := r1 scaledBy:2. |
1807 r1 |
1807 r1 |
1808 " |
1808 " |
1809 ! |
1809 ! |
1810 |
1810 |
1811 scaledBy:scale translatedBy:translation |
1811 scaledBy:scale translatedBy:translation |
1812 "return a new rectangle which is translated (i.e. moved) |
1812 "return a new rectangle which is translated (i.e. moved) |
1813 by translation, aPoint or Number and scaled by scale, aPoint or number." |
1813 by translation, aPoint or Number and scaled by scale, aPoint or number." |
1814 |
1814 |
1815 |x y w h translationPoint scalePoint sx sy| |
1815 |x y w h translationPoint scalePoint sx sy| |
1816 |
1816 |
1817 (translation isNil and:[scale isNil]) ifTrue:[ |
1817 (translation isNil and:[scale isNil]) ifTrue:[ |
1818 ^ self. |
1818 ^ self. |
1819 ]. |
1819 ]. |
1820 |
1820 |
1821 x := left. |
1821 x := left. |
1822 y := top. |
1822 y := top. |
1823 w := width. |
1823 w := width. |
1824 h := height. |
1824 h := height. |
1825 |
1825 |
1826 scale notNil ifTrue:[ |
1826 scale notNil ifTrue:[ |
1827 (scale isMemberOf:SmallInteger) ifTrue:[ |
1827 (scale isMemberOf:SmallInteger) ifTrue:[ |
1828 "/ this is an stc optimization |
1828 "/ this is an stc optimization |
1829 x := x * scale. |
1829 x := x * scale. |
1830 y := y * scale. |
1830 y := y * scale. |
1831 w := w * scale. |
1831 w := w * scale. |
1832 h := h * scale. |
1832 h := h * scale. |
1833 ] ifFalse:[ |
1833 ] ifFalse:[ |
1834 scalePoint := scale asPoint. |
1834 scalePoint := scale asPoint. |
1835 sx := scalePoint x. |
1835 sx := scalePoint x. |
1836 sy := scalePoint y. |
1836 sy := scalePoint y. |
1837 x := x * sx. |
1837 x := x * sx. |
1838 y := y * sy. |
1838 y := y * sy. |
1839 w := w * sx. |
1839 w := w * sx. |
1840 h := h * sy. |
1840 h := h * sy. |
1841 ]. |
1841 ]. |
1842 ]. |
1842 ]. |
1843 translation notNil ifTrue:[ |
1843 translation notNil ifTrue:[ |
1844 (translation isMemberOf:SmallInteger) ifTrue:[ |
1844 (translation isMemberOf:SmallInteger) ifTrue:[ |
1845 "/ this is an stc optimization |
1845 "/ this is an stc optimization |
1846 x := x + translation. |
1846 x := x + translation. |
1847 y := y + translation. |
1847 y := y + translation. |
1848 ] ifFalse:[ |
1848 ] ifFalse:[ |
1849 translationPoint := translation asPoint. |
1849 translationPoint := translation asPoint. |
1850 x := x + translationPoint x. |
1850 x := x + translationPoint x. |
1851 y := y + translationPoint y. |
1851 y := y + translationPoint y. |
1852 ]. |
1852 ]. |
1853 ]. |
1853 ]. |
1854 |
1854 |
1855 ^ Rectangle left:x top:y width:w height:h. |
1855 ^ Rectangle left:x top:y width:w height:h. |
1856 |
1856 |
1857 " |
1857 " |
1858 (Rectangle origin:10@10 corner:50@50) scaledBy:2 translatedBy:10 |
1858 (Rectangle origin:10@10 corner:50@50) scaledBy:2 translatedBy:10 |
1859 " |
1859 " |
1860 ! |
1860 ! |
1861 |
1861 |
1862 translatedBy:amount |
1862 translatedBy:amount |
1863 "return a new rectangle which is translated (i.e. moved) |
1863 "return a new rectangle which is translated (i.e. moved) |
1864 by amount, aPoint or Number" |
1864 by amount, aPoint or Number" |
1865 |
1865 |
1866 |amountPoint| |
1866 |amountPoint| |
1867 |
1867 |
1868 (amount isMemberOf:SmallInteger) ifTrue:[ |
1868 (amount isMemberOf:SmallInteger) ifTrue:[ |
1869 "/ this is an stc optimization |
1869 "/ this is an stc optimization |
1870 ^ Rectangle |
1870 ^ Rectangle |
1871 left:(left + amount) |
1871 left:(left + amount) |
1872 top:(top + amount) |
1872 top:(top + amount) |
1873 width:width |
1873 width:width |
1874 height:height |
1874 height:height |
1875 ]. |
1875 ]. |
1876 |
1876 |
1877 amountPoint := amount asPoint. |
1877 amountPoint := amount asPoint. |
1878 ^ Rectangle left:(left + amountPoint x) |
1878 ^ Rectangle left:(left + amountPoint x) |
1879 top:(top + amountPoint y) |
1879 top:(top + amountPoint y) |
1880 width:width |
1880 width:width |
1881 height:height |
1881 height:height |
1882 " |
1882 " |
1883 (Rectangle origin:10@10 corner:50@50) translatedBy:10 |
1883 (Rectangle origin:10@10 corner:50@50) translatedBy:10 |
1884 " |
1884 " |
1885 |
1885 |
1886 "its NOT destructive:" |
1886 "its NOT destructive:" |
1887 " |
1887 " |
1888 |r1 r2| |
1888 |r1 r2| |
1889 |
1889 |
1890 r1 := Rectangle origin:10@10 corner:50@50. |
1890 r1 := Rectangle origin:10@10 corner:50@50. |
1891 r2 := r1 translatedBy:10. |
1891 r2 := r1 translatedBy:10. |
1892 r1 |
1892 r1 |
1893 " |
1893 " |
1894 ! ! |
1894 ! ! |
1895 |
1895 |
1896 !Rectangle methodsFor:'testing'! |
1896 !Rectangle methodsFor:'testing'! |
1897 |
1897 |
1930 |
1930 |
1931 rounded |
1931 rounded |
1932 "return a copy of the receiver with rounded coordinates. |
1932 "return a copy of the receiver with rounded coordinates. |
1933 Return the receiver if its coordinates are already integral." |
1933 Return the receiver if its coordinates are already integral." |
1934 |
1934 |
1935 (left isInteger |
1935 (left isInteger |
1936 and:[top isInteger |
1936 and:[top isInteger |
1937 and:[width isInteger |
1937 and:[width isInteger |
1938 and:[height isInteger]]]) |
1938 and:[height isInteger]]]) |
1939 ifTrue: [^ self]. |
1939 ifTrue: [^ self]. |
1940 |
1940 |
1941 ^ Rectangle left:(left rounded) |
1941 ^ Rectangle left:(left rounded) |
1942 top:(top rounded) |
1942 top:(top rounded) |
1943 width:(width rounded) |
1943 width:(width rounded) |
1944 height:(height rounded) |
1944 height:(height rounded) |
1945 ! |
1945 ! |
1946 |
1946 |
1947 truncated |
1947 truncated |
1948 "return a Rectangle whose origin and corner have any fractional parts removed. |
1948 "return a Rectangle whose origin and corner have any fractional parts removed. |
1949 Return the receiver if its coordinates are already integral." |
1949 Return the receiver if its coordinates are already integral." |
1950 |
1950 |
1951 (left isInteger |
1951 (left isInteger |
1952 and:[top isInteger |
1952 and:[top isInteger |
1953 and:[width isInteger |
1953 and:[width isInteger |
1954 and:[height isInteger]]]) |
1954 and:[height isInteger]]]) |
1955 ifTrue: [^ self]. |
1955 ifTrue: [^ self]. |
1956 |
1956 |
1957 ^ Rectangle |
1957 ^ Rectangle |
1958 left:left truncated |
1958 left:left truncated |
1959 top:top truncated |
1959 top:top truncated |
1960 width:width truncated |
1960 width:width truncated |
1961 height:height truncated. |
1961 height:height truncated. |
1962 ! ! |
1962 ! ! |
1963 |
1963 |
1964 !Rectangle class methodsFor:'documentation'! |
1964 !Rectangle class methodsFor:'documentation'! |
1965 |
1965 |
1966 version |
1966 version |