--beadsmove2.mesa August 27, 1979 11:22 AM -- move beads -- use deltas to find deltaX and deltaY DIRECTORY IODefs:FROM"IODefs", InlineDefs:FROM"InlineDefs", BeadsDefs:FROM"BeadsDefs"; BeadsMove:PROGRAM IMPORTS InlineDefs,IODefs,BeadsDefs EXPORTS BeadsDefs = BEGIN OPEN BeadsDefs; Error:SIGNAL=CODE; oldtopBead:CARDINAL; maxCache:INTEGER=100; index:CARDINAL_ 0; cache:ARRAY [0..maxCache] OF Bead; --saves state until after transformation address:ARRAY [0..maxCache] OF CARDINAL; abort:ARRAY [0..maxCache] OF BOOLEAN; --this bead is abortable shift:ARRAY [0..maxCache] OF BOOLEAN; --this bead is shiftable noMoves:INTEGER_0; maxMoves:INTEGER=20; ShiftLeft,ShiftRight,ShiftUp,ShiftDown:BOOLEAN; shortLegalOK:BOOLEAN_FALSE; maxPathLength:INTEGER= 20; step:INTEGER[0..maxPathLength]; path:ARRAY [0..maxPathLength] OF Step; --contains the current path Step:TYPE= RECORD[bead:CARDINAL,v:Variant]; deleteindex:CARDINAL[0..20]_ 0; delete:ARRAY [0..20] OF CARDINAL; --cache of beads to be deleted --************************************************************************ Process:PUBLIC PROCEDURE= BEGIN i:CARDINAL; FOR i IN [0..index) DO IF shift[i] AND ~RoomFor[address[i]] THEN BEGIN Abort[]; IODefs.WriteString["no room,"]; EXIT; END; ENDLOOP; FOR i IN [0..index) DO IF shift[i] AND ~Move[bead,address[i],0,0] THEN BEGIN Restore[]; RETURN; END; ENDLOOP; Commit[]; END; --************************************************************************ --path detection and removal Find:PUBLIC PROCEDURE[b:BeadType,i:CARDINAL] RETURNS[CARDINAL]=BEGIN bpi:BeadPtr_Get[i]; tie:CARDINAL_bpi.beadT; bpt:BeadPtr_Get[tie]; RETURN[IF bpt.t=b THEN tie ELSE bpt.beadT]; END; FindPath:PUBLIC PROCEDURE[i,j:CARDINAL,v:Variant] RETURNS[BOOLEAN]= BEGIN bpi:BeadPtr_Get[i]; step_ 0; IF v#left AND RecursiveFindPath[i,bpi.beadR,j,right] THEN RETURN[TRUE]; IF v#right AND RecursiveFindPath[i,bpi.beadL,j,left ] THEN RETURN[TRUE]; IF v#up AND RecursiveFindPath[i,bpi.beadD,j,down ] THEN RETURN[TRUE]; IF v#down AND RecursiveFindPath[i,bpi.beadU,j,up ] THEN RETURN[TRUE]; IF v#tied AND RecursiveFindPath[i,bpi.beadT,j,tied ] THEN RETURN[TRUE]; RETURN[FALSE]; END; RemovePaths:PUBLIC PROCEDURE[i,j:CARDINAL,v:Variant]=BEGIN k:INTEGER; IF i=noBead OR j=noBead THEN RETURN; WHILE FindPath[i,j,v] DO Remove[path[0].bead]; k_1; WHILE NumRelatives[path[k].bead]< 2 AND k< step DO Remove[path[k].bead]; k_ k+ 1; ENDLOOP; ENDLOOP; END; RecursiveFindPath:PROCEDURE[s,i,j:CARDINAL,v:Variant] RETURNS[BOOLEAN]=BEGIN bpi:BeadPtr_Get[i]; IF i=noBead THEN RETURN[FALSE]; IF i=j THEN RETURN[TRUE]; IF s=i THEN RETURN[FALSE]; IF bpi.t=dd OR bpi.t=ddV THEN RETURN[FALSE]; IF bpi.t=tt OR bpi.t=ttV THEN RETURN[FALSE]; IF step> maxPathLength THEN RETURN[FALSE]; path[step].bead_ i; path[step].v_ v; step_ step+ 1; IF v#left AND RecursiveFindPath[s,bpi.beadR,j,right] THEN RETURN[TRUE]; IF v#right AND RecursiveFindPath[s,bpi.beadL,j,left ] THEN RETURN[TRUE]; IF v#up AND RecursiveFindPath[s,bpi.beadD,j,down ] THEN RETURN[TRUE]; IF v#down AND RecursiveFindPath[s,bpi.beadU,j,up ] THEN RETURN[TRUE]; IF v#tied AND RecursiveFindPath[s,bpi.beadT,j,tied ] THEN RETURN[TRUE]; step_ step- 1; RETURN[FALSE]; END; --************************************************************************ --queries about the beads NumRelatives:PUBLIC PROCEDURE[i:CARDINAL] RETURNS[num:CARDINAL]= BEGIN bpi:BeadPtr_Get[i]; num_(IF bpi.beadR=noBead THEN 0 ELSE 1) +(IF bpi.beadL=noBead THEN 0 ELSE 1) +(IF bpi.beadU=noBead THEN 0 ELSE 1) +(IF bpi.beadD=noBead THEN 0 ELSE 1) +(IF bpi.beadT=noBead THEN 0 ELSE 1); END; AndOfRelatives:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[BOOLEAN]= BEGIN bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; RETURN[bpi.beadL#noBead AND bpj.beadL#noBead OR bpi.beadR#noBead AND bpj.beadR#noBead OR bpi.beadU#noBead AND bpj.beadU#noBead OR bpi.beadD#noBead AND bpj.beadD#noBead]; END; Tied:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[BOOLEAN]= BEGIN bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; ti:BeadType_ bpi.t; --the 3way contacts are treated special tj:BeadType_ bpj.t; IF ti=wireR AND tj=bg THEN RETURN[Related[i,bpj.beadT]]; IF ti=wireG AND tj=rb THEN RETURN[Related[i,Get[bpj.beadT].beadT]]; IF tj=wireR AND ti=bg THEN RETURN[Related[j,bpi.beadT]]; IF tj=wireG AND ti=rb THEN RETURN[Related[j,Get[bpi.beadT].beadT]]; RETURN[FALSE]; END; Related:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[BOOLEAN]= BEGIN bpi:BeadPtr_Get[i]; --is i a relative of j? RETURN[SELECT j FROM i,bpi.beadT,bpi.beadU,bpi.beadD,bpi.beadL,bpi.beadR,Get[bpi.beadT].beadT =>TRUE, ENDCASE =>FALSE]; END; Overlap:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[BOOLEAN]= BEGIN bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; RETURN[(bpi.x IN [bpj.x..bpj.x+bpj.w) OR bpj.x IN [bpi.x..bpi.x+bpi.w)) AND (bpi.y IN [bpj.y..bpj.y+bpj.h) OR bpj.y IN [bpi.y..bpi.y+bpi.h))] END; Slack:PROCEDURE[i:CARDINAL,variant:Variant] RETURNS[INTEGER]= BEGIN bpi:BeadPtr_Get[i]; bpv:BeadPtr; t1,t2:INTEGER; SELECT variant FROM left => BEGIN bpv_Get[bpi.beadL]; t1_ bpv.y- bpi.y; t2_ bpv.h+ t1- bpi.h; END; right => BEGIN bpv_Get[bpi.beadR]; t1_ bpv.y- bpi.y; t2_ bpv.h+ t1- bpi.h; END; up => BEGIN bpv_Get[bpi.beadU]; t1_ bpv.x- bpi.x; t2_ bpv.w+ t1- bpi.w; END; down => BEGIN bpv_Get[bpi.beadD]; t1_ bpv.x- bpi.x; t2_ bpv.w+ t1- bpi.w; END; ENDCASE => NULL; IF t1>0 AND t2>0 THEN RETURN[MIN[t1,t2]]; IF t1<0 AND t2<0 THEN RETURN[MAX[t1,t2]]; RETURN[0]; END; Push:PROCEDURE[i,j:CARDINAL] RETURNS[dx,dy:INTEGER]= BEGIN --i pushes on j. How far must j move? bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; w,h,x,y:INTEGER; w_ IF bpi.x< bpj.x THEN bpj.x- (bpi.x+ bpi.w) ELSE bpi.x- (bpj.x+ bpj.w); h_ IF bpi.y< bpj.y THEN bpj.y- (bpi.y+ bpi.h) ELSE bpi.y- (bpj.y+ bpj.h); IF (x_ w- MinSepInX[i,j])< 0 AND (y_ h- MinSepInY[i,j])< 0 THEN BEGIN dx_ IF bpi.x< bpj.x THEN -x ELSE x; dy_ IF bpi.y< bpj.y THEN -y ELSE y; SELECT TRUE FROM ~bpj.wire => IF x> y THEN dy_ 0 ELSE dx_ 0; bpj.beadL#noBead => dx_0; bpj.beadU#noBead => dy_0; ENDCASE; RETURN[dx,dy]; END; RETURN[0,0]; END; MinSepInY:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[deltaY:INTEGER]= BEGIN [,deltaY]_Deltas[i,j]; END; MinSepInX:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[deltaX:INTEGER]= BEGIN [deltaX,]_Deltas[i,j]; END; HorizontalWire:PROCEDURE[bpi:BeadPtr] RETURNS[BOOLEAN]=INLINE BEGIN RETURN[bpi.wire AND bpi.beadU= noBead]; END; VerticalWire:PROCEDURE[bpi:BeadPtr] RETURNS[BOOLEAN]=INLINE BEGIN RETURN[bpi.wire AND bpi.beadR= noBead]; END; --************************************************************************ --procedures that modify the beads structure Initialize:PUBLIC PROCEDURE= BEGIN -- cache_ LOOPHOLE[work]; --address_ LOOPHOLE[work+ 16*maxCache]; -- abort_ LOOPHOLE[work+ 17*maxCache]; -- shift_ LOOPHOLE[work+ 18*maxCache]; oldtopBead_ topBead; Clear[Get[noBead]]; END; Clear:PROCEDURE[bpi:BeadPtr]= BEGIN bpi.beadL_bpi.beadR_bpi.beadU_bpi.beadD_bpi.beadT_ noBead; END; Attach:PUBLIC PROCEDURE[i:CARDINAL,variant:Variant,j:CARDINAL]= BEGIN --Attach i to the variant of j bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; m,n:CARDINAL; Save[i,FALSE,FALSE]; Save[j,FALSE,FALSE]; SELECT variant FROM left => BEGIN Save[m_bpi.beadR,FALSE,FALSE]; Save[n_bpj.beadL,FALSE,FALSE]; Get[m].beadL_ noBead; Get[n].beadR_ noBead; IF i#noBead THEN bpi.beadR_ j; bpj.beadL_ i; END; right => BEGIN Save[m_bpj.beadR,FALSE,FALSE]; Save[n_bpi.beadL,FALSE,FALSE]; Get[m].beadL_ noBead; Get[n].beadR_ noBead; bpj.beadR_ i; IF i#noBead THEN bpi.beadL_ j; END; up => BEGIN Save[m_bpj.beadU,FALSE,FALSE]; Save[n_bpi.beadD,FALSE,FALSE]; Get[m].beadD_ noBead; Get[n].beadU_ noBead; bpj.beadU_ i; IF i#noBead THEN bpi.beadD_ j; END; down => BEGIN Save[m_bpi.beadU,FALSE,FALSE]; Save[n_bpj.beadD,FALSE,FALSE]; Get[m].beadD_ noBead; Get[n].beadU_ noBead; IF i#noBead THEN bpi.beadU_ j; bpj.beadD_ i; END; tied => BEGIN bpi.x_ bpj.x+ (bpj.w- bpi.w)/2; bpi.y_ bpj.y+ (bpj.h- bpi.h)/2; Save[m_bpi.beadT,FALSE,FALSE]; Save[n_bpj.beadT,FALSE,FALSE]; Get[m].beadT_ noBead; Get[n].beadT_ noBead; IF i#noBead THEN bpi.beadT_ j; bpj.beadT_ i; END; ENDCASE; END; AttachAll:PUBLIC PROCEDURE[i,j:CARDINAL]= BEGIN bi:BeadPtr_Get[i]; IF bi.beadL#noBead THEN Attach[bi.beadL,left ,j]; IF bi.beadR#noBead THEN Attach[bi.beadR,right,j]; IF bi.beadU#noBead THEN Attach[bi.beadU,up ,j]; IF bi.beadD#noBead THEN Attach[bi.beadD,down ,j]; IF bi.beadT#noBead THEN Attach[bi.beadT,tied ,j]; END; Move:PUBLIC PROCEDURE[variant:Variant,i:CARDINAL,dx,dy:INTEGER] RETURNS[r:BOOLEAN] = BEGIN bpi:BeadPtr_ Get[i]; x,y,w,h,u,d,r,l,needed,d5,d7:INTEGER_ 0; k:CARDINAL; bpd:BeadPtr_Get[bpi.beadD]; bpu:BeadPtr_Get[bpi.beadU]; bpl:BeadPtr_Get[bpi.beadL]; bpr:BeadPtr_Get[bpi.beadR]; w_ bpi.w; h_ bpi.h; IF i=noBead THEN RETURN[TRUE]; IF variant#tied AND variant#bead THEN BEGIN needed_ Slack[i, variant]; d5_Des5[desP[bpu.t].short][desP[bpd.t].short]; d7_Des7[desP[bpl.t].short][desP[bpr.t].short]; u_ bpu.y; d_ bpd.y+ bpd.h; r_ bpr.x; l_ bpl.x+ bpl.w; END; SELECT variant FROM left => BEGIN IF bpi.wire THEN w_ MAX[d7,r-l]; dx_ l- bpi.x; dy_ needed; END; down => BEGIN IF bpi.wire THEN h_ MAX[d5,u-d]; dy_ d- bpi.y; dx_ needed; END; right => BEGIN IF bpi.wire THEN w_ MAX[d7,r-l]; dy_ needed; dx_ r- (bpi.x+ w); END; up => BEGIN IF bpi.wire THEN h_ MAX[d5,u-d]; dx_ needed; dy_ u- (bpi.y+ h); END; ENDCASE; IF dx=0 AND dy=0 AND bpi.w=w AND bpi.h=h AND variant#bead THEN RETURN[TRUE]; x_bpi.x+ dx; y_bpi.y+ dy; IF x<0 OR y<0 OR x+w>maxX OR y+h>maxY THEN BEGIN -- IODefs.WriteString["out of bounds,"];-- GOTO False; END;--bounds noMoves_ noMoves+ 1; IF noMoves> maxMoves THEN BEGIN --IODefs.WriteString[">maxMoves,"];-- GOTO False; END; --limit Save[i,TRUE,FALSE]; bpi.x_ x; bpi.y_ y; bpi.w_ w; bpi.h_ h; IF variant#up AND ~Move[down ,bpi.beadU, 0, 0] THEN GOTO False; IF variant#right AND ~Move[left ,bpi.beadR, 0, 0] THEN GOTO False; IF variant#down AND ~Move[up ,bpi.beadD, 0, 0] THEN GOTO False; IF variant#left AND ~Move[right,bpi.beadL, 0, 0] THEN GOTO False; IF variant#tied AND ~Move[tied ,bpi.beadT,dx,dy] THEN GOTO False; IF variant#tied AND (k_Get[bpi.beadT].beadT)# i AND ~Move[tied ,k ,dx,dy] THEN GOTO False; IF ~Legal[i] THEN GOTO False; RETURN[TRUE]; EXITS False => RETURN[FALSE]; END; Legal:PROCEDURE[i:CARDINAL] RETURNS[r:BOOLEAN]= BEGIN RETURN[IF shortLegalOK THEN LegalShort[i] ELSE LegalLong[i]]; END; LegalLong:PROCEDURE[i:CARDINAL] RETURNS[BOOLEAN]= BEGIN --make the rest of the world legal with respect to i j:CARDINAL; dx,dy:INTEGER; FOR j IN [0..topBead] DO BEGIN IF Get[j].t=none THEN LOOP; [dx,dy]_ Push[i,j]; SELECT TRUE FROM dx=0 AND dy=0 OR Related[i,j] OR Tied[i,j] =>NULL; ~Move[bead,j,dx,dy] =>RETURN[FALSE]; ENDCASE; END; ENDLOOP; RETURN[TRUE]; END; LegalShort:PROCEDURE[i:CARDINAL] RETURNS[r:BOOLEAN]= BEGIN Error; RETURN[TRUE]; END; Put:PUBLIC PROCEDURE[i:CARDINAL,dx,dy,h,w:INTEGER]= BEGIN bpi:BeadPtr_Get[i]; Save[i,FALSE,TRUE]; bpi.x_ bpi.x+ dx; bpi.y_ bpi.y+ dy; IF h#0 THEN bpi.h_ h; IF w#0 THEN bpi.w_ w; END; Create:PROCEDURE[t:BeadType,x,y,h,w,circuit:INTEGER] RETURNS[CARDINAL]= BEGIN bpt:BeadPtr_ Get[topBead+1]; IF (topBead_ topBead+ 1)>= noBead THEN Error; Clear[bpt]; bpt.x_ x; bpt.y_ y; bpt.circuit_ circuit; bpt.w_ IF w=0 THEN desP[t].w ELSE w; bpt.h_ IF h=0 THEN desP[t].h ELSE h; bpt.t_ t; bpt.external_ 0; --is this correct? bpt.wire_ t=wireG OR t=wireB OR t=wireR; bpt.noodle_ topNoodle; bpt.nextBelow_ noBelow; InitBeadWork[topBead,bpt]; RETURN[topBead]; END; InsertJogs:PUBLIC PROCEDURE[i:CARDINAL,horizontal,vertical:Variant]= BEGIN bpi:BeadPtr_ Get[i]; IF bpi.beadR#noBead THEN InsertJog[i,bpi.beadR,left,horizontal]; IF bpi.beadL#noBead THEN InsertJog[i,bpi.beadL,right,horizontal]; IF bpi.beadU#noBead THEN InsertJog[i,bpi.beadU,down,vertical]; IF bpi.beadD#noBead THEN InsertJog[i,bpi.beadD,up,vertical]; END; InsertJog:PROCEDURE[contact,wire:CARDINAL,whichEnd,bend:Variant]= BEGIN wt:BeadType_ Get[wire].t; bpc:BeadPtr_ Get[contact]; vert:BOOLEAN_ whichEnd=up OR whichEnd=down; s:INTEGER_ IF wt= wireB THEN 6 ELSE 4; jt:BeadType_ SELECT wt FROM wireR => jctnR,wireB => jctnB, ENDCASE => jctnG; j1:CARDINAL_ Create[jt,bpc.x,bpc.y,s,s,bpc.circuit]; j2:CARDINAL_ Create[jt,bpc.x,bpc.y,s,s,bpc.circuit]; w1:CARDINAL_ IF vert THEN Create[wt,bpc.x,bpc.y+s,-s,s,bpc.circuit] ELSE Create[wt,bpc.x+s,bpc.y,s,-s,bpc.circuit]; w2:CARDINAL_ IF vert THEN Create[wt,bpc.x+s,bpc.y,s,-s,bpc.circuit] ELSE Create[wt,bpc.x,bpc.y+s,-s,s,bpc.circuit]; Attach[contact,whichEnd,w1]; Attach[j2,whichEnd,wire]; Attach[w1,whichEnd,j1]; Attach[j2,bend,w2]; Attach[w2,bend,j1]; END; --************************************************************************ --find room for a group of beads RoomFor:PUBLIC PROCEDURE[i:CARDINAL] RETURNS[r:BOOLEAN]= BEGIN --make i legal with respect to the rest of the world j:CARDINAL; dx,dy:INTEGER; FOR j IN [0..topBead] DO BEGIN IF Get[j].t=none THEN LOOP; [dx,dy]_ Push[i,j]; SELECT TRUE FROM dx=0 AND dy=0 =>NULL; Related[i,j] =>NULL; Tied[i,j] =>NULL; ~Shift[-dx,-dy] =>RETURN[FALSE]; ENDCASE; END; ENDLOOP; RETURN[TRUE]; END; ClearShift:PUBLIC PROCEDURE= BEGIN ShiftLeft_ ShiftRight_ ShiftUp_ ShiftDown_ FALSE; END; Shift:PUBLIC PROCEDURE[dx,dy:INTEGER] RETURNS[BOOLEAN]= BEGIN i:CARDINAL; IF dx<0 AND ShiftLeft THEN RETURN[FALSE] ELSE ShiftLeft_ TRUE; IF dx>0 AND ShiftRight THEN RETURN[FALSE] ELSE ShiftRight_ TRUE; IF dy<0 AND ShiftDown THEN RETURN[FALSE] ELSE ShiftDown_ TRUE; IF dy>0 AND ShiftUp THEN RETURN[FALSE] ELSE ShiftUp_ TRUE; FOR i IN [0..index) DO IF shift[i] THEN BEGIN bpa:BeadPtr_Get[address[i]]; bpa.x_ bpa.x+ dx; bpa.y_ bpa.y+ dy; END; ENDLOOP; RETURN[TRUE]; END; --************************************************************************ --procedures that save state until a transformation is complete Save:PROCEDURE[a:CARDINAL,abortable,shiftable:BOOLEAN]= BEGIN IF a= noBead THEN RETURN; IF a> oldtopBead THEN RETURN; IF index> maxCache THEN Error; --you should increase maxCache cache[index]_ Get[a]^; address[index]_ a; abort[index]_ abortable; shift[index]_ shiftable; index_ index+ 1; END; Remove:PUBLIC PROCEDURE[i:CARDINAL]=BEGIN --get the bead out of the way bpi:BeadPtr_Get[i]; t:CARDINAL_ bpi.beadT; bpt:BeadPtr_Get[t]; Save[i,FALSE,FALSE]; delete[deleteindex]_ i; deleteindex_ deleteindex+ 1; IF bpi.beadR#noBead THEN BEGIN Save[bpi.beadR,FALSE,FALSE]; Get[bpi.beadR].beadL_ noBead; END; IF bpi.beadL#noBead THEN BEGIN Save[bpi.beadL,FALSE,FALSE]; Get[bpi.beadL].beadR_ noBead; END; IF bpi.beadU#noBead THEN BEGIN Save[bpi.beadU,FALSE,FALSE]; Get[bpi.beadU].beadD_ noBead; END; IF bpi.beadD#noBead THEN BEGIN Save[bpi.beadD,FALSE,FALSE]; Get[bpi.beadD].beadU_ noBead; END; IF bpi.beadT#noBead THEN BEGIN IF Get[t].beadT#i THEN t_ bpt.beadT; Save[t,FALSE,FALSE]; bpt.beadT_ noBead; END; bpi.x_ 2*maxX; bpi.y_ 2*maxY; Clear[bpi]; END; Restore:PUBLIC PROCEDURE= BEGIN a,i:CARDINAL; --IODefs.WriteLine["failed"]; FOR i DECREASING IN [0..index) DO Get[a_address[i]]^_ cache[i]; ENDLOOP; noMoves_ deleteindex_ index_ 0; topBead_ oldtopBead; END; Abort:PUBLIC PROCEDURE=BEGIN i:CARDINAL; noMoves_0; FOR i DECREASING IN [0..index) DO IF abort[i]=TRUE THEN Get[address[i]]^_ cache[index_ i]; ENDLOOP; END; Commit:PUBLIC PROCEDURE=BEGIN i:INTEGER; FOR i IN [0..deleteindex) DO IF delete[i] IN [topBead-deleteindex..topBead] THEN BEGIN DeleteBead[delete[i]]; delete[i]_ noBead; END; ENDLOOP; FOR i IN [0..deleteindex) DO IF delete[i]#noBead THEN DeleteBead[delete[i]]; ENDLOOP; noMoves_ index_ deleteindex_0; oldtopBead_ topBead; --IODefs.WriteLine["done"]; END; DeleteBead:PUBLIC PROCEDURE[i:CARDINAL]=BEGIN j:CARDINAL; bpi:BeadPtr_Get[i]; bpt:BeadPtr_Get[topBead]; --switch the bead with the topBead IF i=topBead THEN BEGIN topBead_topBead-1; RETURN; END; IF (j_bpt.beadU)#noBead THEN Get[j].beadD_i; IF (j_bpt.beadD)#noBead THEN Get[j].beadU_i; IF (j_bpt.beadR)#noBead THEN Get[j].beadL_i; IF (j_bpt.beadL)#noBead THEN Get[j].beadR_i; IF (j_bpt.beadT)#noBead THEN FOR j_topBead, Get[j].beadT DO IF Get[j].beadT=topBead THEN BEGIN Get[j].beadT_i; EXIT; END; ENDLOOP; bpi^_bpt^; topBead_topBead-1; END; --************************************************************************ Rotate:PUBLIC PROCEDURE=BEGIN i,s:CARDINAL; t:INTEGER; FindBoundingBox[]; FOR i IN [0..topBead] DO BEGIN bpi:BeadPtr_Get[i]; bi:Bead_bpi^; t_bi.y; bi.y_maxX-bi.x-bi.w; bi.x_t; t_bi.w; bi.w_bi.h; bi.h_t; s_bi.beadL; bi.beadL_bi.beadD; bi.beadD_bi.beadR; bi.beadR_bi.beadU; bi.beadU_s; bi.t_desP[bi.t].rotate; bpi^_bi; END ENDLOOP; END; Reflect:PUBLIC PROCEDURE=BEGIN i,s:CARDINAL; t:INTEGER; FindBoundingBox[]; FOR i IN [0..topBead] DO BEGIN bpi:BeadPtr_Get[i]; bi:Bead_bpi^; t_bi.y; bi.y_bi.x; bi.x_t; t_bi.w; bi.w_bi.h; bi.h_t; s_bi.beadL; bi.beadL_bi.beadD; bi.beadD_s; s_bi.beadR; bi.beadR_bi.beadU; bi.beadU_s; bi.t_desP[bi.t].rotate; bpi^_bi; END ENDLOOP; END; RotateBack:PUBLIC PROCEDURE=BEGIN i,s:CARDINAL; t:INTEGER; FindBoundingBox[]; FOR i IN [0..topBead] DO BEGIN bpi:BeadPtr_Get[i]; bi:Bead_bpi^; t_bi.x; bi.x_maxY-bi.y-bi.h; bi.y_t; t_bi.w; bi.w_bi.h; bi.h_t; s_bi.beadL; bi.beadL_bi.beadU; bi.beadU_bi.beadR; bi.beadR_bi.beadD; bi.beadD_s; bi.t_desP[bi.t].rotate; bpi^_bi; END ENDLOOP; END; END.. MinSepInY:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[INTEGER]= BEGIN bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; si:CARDINAL=desP[bpi.t].short; sj:CARDINAL=desP[bpj.t].short; SELECT TRUE FROM desP[bpi.t].lessLevel#desP[bpj.t].lessLevel =>RETURN[-maxY]; bpi.wire AND bpj.wire => RETURN[IF Overlap[i,j] THEN maxY ELSE -maxY]; bpi.circuit#bpj.circuit => RETURN[Des4[sj][si]]; si=sj AND si IN [5..7] AND ~bpi.wire AND ~bpj.wire => RETURN[-MAX[bpi.h,bpj.h]]; ENDCASE=>RETURN[Des5[sj][si]]; END; MinSepInX:PUBLIC PROCEDURE[i,j:CARDINAL] RETURNS[INTEGER]= BEGIN bpi:BeadPtr_Get[i]; bpj:BeadPtr_Get[j]; si:CARDINAL=desP[bpi.t].short; sj:CARDINAL=desP[bpj.t].short; SELECT TRUE FROM desP[bpi.t].lessLevel#desP[bpj.t].lessLevel =>RETURN[-maxX]; bpi.wire AND bpj.wire => RETURN[IF Overlap[i,j] THEN maxX ELSE -maxX]; bpi.circuit#bpj.circuit => RETURN[Des6[sj][si]]; si=sj AND si IN [5..7] AND ~bpi.wire AND ~bpj.wire => RETURN[-MAX[bpi.w,bpj.w]]; ENDCASE=>RETURN[Des7[sj][si]]; END; (1792)\47i10I366i38I83i22I42i22I220i25I115i28I77b7B423b2Bi27bI4B189b8B499b11B282b17B862b2Bi24bI12B301b14B299b4B124i37I306b7B80i21I147b7B258b5B144i4I101i5I100i2I103i4I227b4B59i37I566b9B94b9B94b14B104b12B181i43bI10B225b5B100b6B68i28I22i1I21i2I14i1I43i1I24i4I189i5I188i2I191i4I189i4I278b9B327b4B1209i5I8i6I109i5I9i5I127i5I64i5I64i5I64i5I64i5I100i5I27i5I24i6I24b5B116b11B51i50I302b12B76b5B195b6B320i16I151b10B360b9B865i31bI7B60i50I331b10B85b5B575i62bI4B154i28I128b6B38i27I22i1I24i1I21i3I647i2I51b7B214b5B167b6B375b10B69i1I27i1I4i32I507b6B376b7B368b10B383b9B503b9B