home *** CD-ROM | disk | FTP | other *** search
Wrap
/* Routine to export a Sculpt object file. Only vertices and edges are saved - you have to fill in the outlines yourself in Sculpt. Do this BEFORE extruding. Written by Don Cox, Dec. '93. Copyright. Not Public Domain. */ msg = PDSetup.rexx(2,0) /* load gdarexxsupport.library */ units = getclip(pds_units) if msg ~= 1 then exit_msg(msg) call pdm_SetWireFrame(1) numeric digits 8 cr = '0a'x userpath = getclip(pduserpath) shapefile = pdm_GetFilename("Select file for saving", userpath) if shapefile = "" then exit_msg("No file selected") call pdm_ShowStatus(" Analysing objects...") success = open("Output2",shapefile,"W") if success = 0 then exit_msg("File "shapefile" could not be opened") success = open("Output","ram:tempfile","W") if success = 0 then exit_msg("Temporary file could not be opened") pos1 = lastpos("/",shapefile) if pos1 = 0 then pos1 = lastpos(":",shapefile) fileonly = substr(shapefile,pos1+1) pathonly = left(shapefile,pos1) call setclip(pduserpath,pathonly) /* First go through getting rough size, for setting point intervals for curve conversion */ object = pdm_SelFirstObj() objectnumber = 1 totalpoints = 0 if object = 0 then exit_msg("No objects selected") do until object = 0 if pdm_IsEllipse(object) = 1 then call pdm_EllipseToGraphic(object) if pdm_IsText(object) = 1 then do textobject = pdm_SelectObj(object) call pdm_TextToGraphic() end if pdm_IsBezier(object)=1 then do numpoints = pdm_GetObjOrder(object) totalpoints = totalpoints+numpoints VisSize = pdm_GetObjVisSize(object) VisPos = pdm_GetObjVisPosn(object) parse var VisSize VisWidth VisHeight parse var VisPos Xcoord Ycoord if objectnumber = 1 then do smallestY = Ycoord /* pick up first Y value in file */ smallestX = Xcoord biggestX = Xcoord biggestY = Ycoord end if Ycoord>biggestY then biggestY = Ycoord if Ycoord<smallestY then smallestY = Ycoord if Xcoord>biggestX then biggestX = Xcoord if Xcoord<smallestX then smallestX = Xcoord Ycoord = Ycoord+VisHeight /* Look at bottom right corner */ Xcoord = Xcoord+VisWidth if Ycoord>biggestY then biggestY = Ycoord if Ycoord<smallestY then smallestY = Ycoord if Xcoord>biggestX then biggestX = Xcoord if Xcoord<smallestX then smallestX = Xcoord end object = pdm_SelNextObj(object) objectnumber = objectnumber+1 end if objectnumber = 1 then exit_msg("No objects selected") /* This is what we really want but the sqrt function in the gdarexxsupport.library doesn't work. totalpoints = trunc(sqrt(totalpoints)*20) */ totalpoints = totalpoints*2 /* will have to do instead */ if totalpoints>300 then totalpoints=300 /* arbitrary limits */ if totalpoints<40 then totalpoints=40 resolution = pdm_GetForm("Set curve point resolution", 10,"Resolution number :"totalpoints) if ~datatype(resolution,n) then resolution = 60 string = "" /* This time, convert curves and get accurate size */ totalsize = (biggestX-smallestX)+(biggestY-smallestY) oldControl2X = 0 oldControl2Y = 0 oldXcoord = 0 oldYcoord = 0 object = pdm_SelFirstObj() objectnumber = 1 gridflag = 0 /* grid as lines or dots requester flag */ do until object = 0 if pdm_IsBezier(object)=1 then do numpoints = pdm_GetObjOrder(object) numpoints = numpoints -1 /* Counts from zero */ pointnumber = 0 do until pointnumber > numpoints pointinfo = pdm_GetPoint(object, pointnumber) parse var pointinfo Xcoord Ycoord control1X control1Y control2X control2Y pointinfo = Xcoord" "Ycoord||cr /* default for straight lines */ /* See if it's a curved line and add points if so */ if (control1X~=0 | control1Y~=0 | oldControl2X~=0 | oldControl2Y~=0) & pointnumber ~=0 & resolution~=0 then call Bezier2 oldControl2X = control2X oldControl2Y = control2Y oldXcoord = Xcoord oldYcoord = Ycoord string = string||pointinfo if length(string)>20000 then do call writech("Output",string) string = "" end pointnumber = pointnumber+1 end end object = pdm_SelNextObj(object) objectnumber = objectnumber+1 string = string||cr /* Blank line between objects */ end call writech("Output",string) call finalize exit_msg("Finished") /* +++++++++++++++++++++++++++++++++ +++++++++++++++++++++++++++++++++ */ exit_msg() exit_msg: procedure expose units do parse arg message if message ~= '' then call pdm_Inform(1,message,) call pdm_ClearStatus() call pdm_SetUnits(units) call pdm_AutoUpdate(1) exit end /* ++++++++++++++++++++++++++++++ +++++++++++++++++++++++++++++++++++ */ Bezier2: /* Bezier2.SUB From Fundamentals of Interactive Computer Graphics From article by Steve Enns in Byte, Dec. '86 (2D version only) Calculates cubic parametric freeform Bezier curves XC.,YC. are the coords of the 4 hull points, which are the current and previous points and their inner control points. */ XC.1 = oldXcoord XC.2 = oldControl2X+oldXcoord /* control handle coords are relative */ XC.3 = control1X+Xcoord XC.4 = Xcoord YC.1 = oldYcoord YC.2 = oldControl2Y+oldYcoord YC.3 = control1Y+Ycoord YC.4 = Ycoord curvesize = abs(Xcoord-oldXcoord)+abs(Ycoord-oldYcoord) curveratio = curvesize/totalsize increment = 1/(resolution * curveratio) if increment>0.5 then increment = 0.5 /* just put 1 in the middle */ /* Returns CurveXcoord. and CurveYcoord. as the points Returns XNS as the number of curve points */ IS=1 pointinfo = "" do T=increment to 0.98 by increment /* 0.98 so as not to do a point right at the end of the curve, too close to first poit of next curve */ T2=T*T T3=T2*T NC1=1-3*T+3*T2-T3 NC2=3*T3-6*T2+3*T NC3=3*T2-3*T3 NC4=T3 CurveXcoord=(NC1*XC.1)+(NC2*XC.2)+(NC3*XC.3)+(NC4*XC.4) CurveYcoord=(NC1*YC.1)+(NC2*YC.2)+(NC3*YC.3)+(NC4*YC.4) pointinfo = pointinfo||CurveXcoord" "CurveYcoord||cr IS=IS+1 end pointinfo = pointinfo||Xcoord" "Ycoord||cr XNS = IS-1 /* number of points */ RETURN /* +++++++++++++++++++++++++++++++++++ +++++++++++++++++++++++++++++++++ */ gridexpand: /* do the other points of a grid */ return /* ++++++++++++++++++++++++++++++++++++ ++++++++++++++++++++++++++++++++ */ finalize: /* Normalize and invert Y values, save to output file. */ call pdm_ShowStatus(" Constructing Sculpt object file...") call seek("Output",0,"B") Znumber = d2c(0,4) /* all flat in Z plane */ vertexnumber = 0 numverts = 0 if ~open("Output3","ram:tempfile3","W") then exit_msg("Second temporary file could not be opened") if ~open("Output5","ram:tempfile5","W") then exit_msg("Third temporary file could not be opened") outstring1 = "FORM" outstring2 = "SC3DVERT" outstring3 = "" /* list of vertices */ out3length = 0 /* length of this list in bytes */ outstring4 = "EDGE" outstring5 = "" /* list of edges */ out5length = 0 /* length of edge list */ biggestY = biggestY-smallestY do until eof("Output") numbers = readln("Output") if numbers = "" then do /* blank line is end of polyline */ if numverts>1 then do /* do list of edges */ thisvertex = vertexnumber-numverts lastnumber = vertexnumber-1 /* Sculpt count vertices from zero */ if Xnumber = startX & Ynumber = startY then lastnumber = thisvertex /* closed loop */ do i = 1 to (numverts-1) outstring5 = outstring5 || d2c(thisvertex,4) || d2c(thisvertex+1,4) out5length = out5length+8 if length(outstring5)>20000 then do call writech("Output5",outstring5) outstring = "" end thisvertex = thisvertex+1 end outstring5 = outstring5 || d2c(vertexnumber-1,4) || d2c(lastnumber,4) out5length = out5length+8 end numverts = 0 end parse var numbers Xnumber Ynumber if datatype(Xnumber,n) & datatype(Ynumber,n) then do if Xnumber = startX & Ynumber = startY then break /* closed loop */ vertexnumber = vertexnumber+1 numverts = numverts+1 if numverts=1 then do startX = Xnumber startY = Ynumber end Ynumber = Ynumber-smallestY /* put baseline at zero */ Ynumber = biggestY-Ynumber /* and invert */ Ynumber = trunc(Ynumber*10000) /* make it an integer */ Ynumber = d2c(Ynumber,4) Xnumber = Xnumber - smallestX /* also set left side to zero */ Xnumber = trunc(Xnumber*10000) Xnumber = d2c(Xnumber,4) numbers = Xnumber||Ynumber||Znumber outstring3 = outstring3||numbers out3length = out3length+12 /* total length including any saved */ end if length(outstring3)>20000 then do call writech("Output3",outstring3) outstring = "" end end call writech("Output3",outstring3) call writech("Output5",outstring5) outstring4 = outstring4 || d2c(out5length,4) outlength = out3length+out5length+12 /* total length for form chunk */ outstring6 = outstring1||d2c(outlength,4) || outstring2||d2c(out3length,4) call writech("Output2",outstring6) call seek("Output3",0,'B') do until eof("Output3") instring = readch("Output3",20000) inlength = length(instring) call writech("Output2",instring) end call writech("Output2",outstring4) call seek("Output5",0,'B') do until eof("Output5") instring = readch("Output5",20000) inlength = length(instring) call writech("Output2",instring) end call close("Output2") call close("Output3") call close("Output5") call close("Output") address command 'delete "ram:tempfile"' 'delete "ram:tempfile3"' 'delete "ram:tempfile5"' return