From: Ruminari
Subject: Import XYZ Modifications Help
Date: 
Message-ID: <1147811460.680257.111240@i39g2000cwa.googlegroups.com>
Hey Everyone,

I'm working on a research degree and have ran into some problems.  I'm
a newb to autocad lisp code and I'm looking for a little assitance.
I've gone through the vlips tutorials that ship with autocad, however
they have only provided a crude understanding of the vlips environment
and I really don't have the time to fully learn vlisp code.
Additionally, I have searched all over user forums trying to find a
solution to this problem.


My problem:

I have a collection of data (X Y Rotation) separated by spaces in a txt
format.  Next I'm wanting to import this data into autocad utilizing
Import XYZ.  However, instead of the XYZ, I basically want to do
XYRotation.  This will allow me to insert a basic block and rotate it
to the proper Rotational value.


Questions:

1. Is it very difficult to make this change?
2. How do I go about making this change?



Code:

;;;--- IMPORTXYZ.lsp - Import coords from a file.
;;;
;;;
;;;--- Copyright 2005 by JefferyPSanders.com
;;;    All rights reserved.
;;;
;;;--- Revisions
;;;
;;;    3/2/06 - Solved problem with blank Excel lines.


(defun C:IMPORTXYZ()

  (setq exitMessage "\n IMPORTXYZ.lsp Complete. \n ")




  ;;;--- Function to put the values of a range of cells in a list
  ;;;
  ;;;--- Parameters:
  ;;;
  ;;;      stRow = starting row number as integer
  ;;;      stCol = starting column number as integer
  ;;;      LsRow = last row number as integer
  ;;;      LsCol = last column number as integer

  (defun GetRangeCells(stRow stCol LsRow LsCol / cellList copyCol)

    ;;;--- Make a copy of the first column
    (setq copyCol stCol)

    ;;;--- Build an empty list to hold the cell's addresses and values
    (setq cellList(list))

    ;;;--- Save the column
    (setq tmpCol stCol)

    ;;;--- Set up a cell counter and a flag
    (setq cellCnt 0 oldstRow nil)

    ;;;--- Loop while we are inside the range
    (while (<= stRow LsRow )

      ;;;--- Increment the cell counter
      (setq cellCnt(+ cellCnt 1))

      ;;;--- Add the address and value to the cell list
      (setq cellList
        (append cellList

          ;;;--- Build a list containing the cell's row and value
          (list
            (cons

              ;;;--- Add the row
              stRow

              ;;;--- Add the value of the cell
              (vlax-variant-value
                (JXCL-get-value
                  (vlax-variant-value
                    (JXCL-get-item
                      (JXCL-get-cells (JXCL-get-ActiveSheet myApp))
                      (vlax-make-variant stRow)
                      (vlax-make-variant stCol)
                    )
                  )
                )
              )
            )
          )
        )
      )

      ;;;--- Inform the user of progress
      (if(> cellCnt 99)
        (progn
          (princ "\n Currently retrieving cells in Row ")
          (princ (strcat (itoa stRow) " of " (itoa LsRow)))
          (setq cellCnt 0)
        )
      )

      ;;;--- Increment the column
      (setq stCol(+ stCol 1))

      ;;;--- Make sure the column stays in the range
      (if(> stCol LsCol)
        (setq stCol copyCol stRow(+ stRow 1))
      )
    )

    ;;;--- Return the list
    cellList
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to get the selected worksheet name from the dialog
box
  (defun saveVars3()

    ;;;--- Get the index of the selected sheet
    (setq sheetIndex(atoi(get_tile "sheetlist")))

    ;;;--- Use the index to find the name of the sheet
    (setq sheetName(nth sheetIndex sheetList))
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to convert a column number to an excel column letter
  ;;;
  ;;;--- Parameters:
  ;;;
  ;;;       a = Column number as integer
  ;;;
  ;;;--- Returns:
  ;;;
  ;;;       Column name as in Excel  Ex. "A" or "AB"
  ;;;
  ;;;
  ;;;--- Limitations
  ;;;
  ;;;      Works from 1 to 702

  (defun N2C(a)
    (if(< a 27)
      (setq column (chr (+ a 64)))
      (setq column
        (strcat
          (if(= 91 (+ 64(fix(/ a 26.001))))
             "Z"
             (chr(+ 64(fix(/ a 26.001))))
          )
          (if(= 64 (+ 64(- a(* 26(fix(/ a 26))))))
            "Z"
            (chr(+ 64(- a(* 26(fix(/ a 26))))))
          )
        )
      )
    )
    column
  )



;;;---------------------------------------------------------------------------------------


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  ;;;
  ;;;--- Function to get the data from an Excel Sheet
  ;;;
  ;;;    Parameter - fileName = Excel Spread sheet name including path
if necessary
  ;;;

  (defun XL_GET (fileName / myApp sysDrive dataList myWBooks myWBook
sht shtCnt mySheets
                            sheetList cnt shtName ddiag mySht mySheet
myRange myAddress
                            myCells 1stRow 1stCol LstRow LstCol
dataList)

    ;;;--- Get the system drive
    (setq sysDrive (getenv "systemdrive"))

    ;;;--- If the excel object library is not found...load it
    (if (null Library)
      (progn

        ;;;--- Find out which version we should use
        (setq Library
          (cond
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office\\Excel8.olb")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office\\Excel9.olb")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office\\Excel10.olb")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office\\Excel.exe")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office10\\Excel.exe")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office11\\Excel.exe")))
            ((findfile (strcat sysDrive "\\Program Files\\Microsoft
Office\\Office11\\XL5EN32.OLB")))
          )
        )

        ;;;--- If the library was found...
        (if Library
          (progn

            ;;;--- Strip off
            (setq LibVer (substr (vl-filename-base Library) 6))
            (cond
              ((= LibVer "8")(princ "\n Opening Excel Version 8..."))
              ((= LibVer "9")(princ "\n Opening Excel Version 9..."))
              ((= LibVer "1")(princ "\n Opening Excel Version 10..."))
              ((= LibVer "") (princ "\n Opening Excel Version
2000+..."))
              ((= LibVer "3")(princ "\n Opening Excel Version
2003..."))

            )
            (vlax-import-type-library
              :tlb-filename Library
              :methods-prefix "JXCL-"
              :properties-prefix "JXCL-"
              :constants-prefix "JXCL-"
            )
            (princ " Done.")
          )
          (alert "Excel Object Library was not found!\n\nSee the XL
HELP on my web site.")
        )
      )
    )

    ;;;--- If an excel application is not loaded, proceed...

    (if (null myApp)
      (progn

        ;;;--- If Excel...
        (if(setq myapp(vlax-get-or-create-object "Excel.Application"))
          (progn

            ;;;--- Open the workbook
            (vlax-invoke-method (vlax-get-property myapp 'WorkBooks)
'Open fileName)

            ;;;--- Set it to invisible mode
            (vla-put-visible myApp 0)

            ;;;--- Get the workbooks object
            (setq myWBooks(vlax-get myApp "Workbooks"))

            ;;;--- Open the excel file
            (setq myWBook(vla-open myWBooks fileName))

            ;;;;--- Get the sheets object
            (setq mySheets(vlax-get myWBook "Sheets"))

            ;;;--- Get a list of the sheet names
            (princ "\n Getting Sheet Names from Excel...")
            (setq shtCnt(vla-get-count mySheets))
            (setq sheetList(list))
            (setq cnt 1)
            (while(<= cnt shtCnt)
              (setq sht(JXCL-get-item mySheets cnt))
              (setq shtName(vla-get-name sht))
              (setq sheetList(append sheetList(list shtName)))
              (setq cnt(+ cnt 1))
            )
            (princ " Done.")
            ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
            ;;;--- Let the user select a sheet  ;;;
            ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;


            ;;;--- See if it is already loaded
            (if (not (new_dialog "XL_GET" dcl_id))
              (progn
                (alert "Could not find the IMPORTXYZ.DCL file!")
                (exit)
              )
            )

            ;;;--- Add the layer names to the dialog box
            (start_list "sheetlist" 3)
            (mapcar 'add_list sheetList)
            (end_list)

            ;;;--- Set the first sheet as default
            (set_tile "sheetlist" "0")

            ;;;--- If an action event occurs, do this function
            (action_tile "cancel" "(setq ddiag1 1)(done_dialog)")
            (action_tile "accept" "(setq ddiag1
2)(saveVars3)(done_dialog)")

            ;;;--- Display the dialog box
            (start_dialog)

            ;;;--- If the "Okay" button was pressed
            (if (= ddiag1 2)
              (progn

                ;;;--- Get the selected worksheet
                (setq mySht(vlax-get-property mySheets 'Item
sheetName))

                ;;;--- Make the selected worksheet active
                (vlax-invoke-method mysht "Activate")

                ;;;--- Get the used range of the worksheet
                (setq myRange(vlax-get-property mySht 'UsedRange))

                ;;;--- Get the cells from the range
                (setq myCells(vlax-get-property myRange 'Cells))

                ;;;--- Get the addresses of the top left and bottom
right cells
                (setq myAddress(JXCL-get-address myRange myCells 2 3
1))

                ;;;--- Strip off the workbook and worksheet names
                (setq myAddress(substr myAddress (+ 3 (vl-string-search
"!" myAddress))))

                ;;;--- Get the starting row number of the range
                (setq 1stRow(fix(atof myAddress)))

                ;;;--- Get the starting column number of the range
                (setq 1stCol(fix(atof (substr myAddress (+ (strlen
(itoa 1stRow)) 2)))))

                ;;;--- Strip off the first row and column from the
address string
                (setq myAddress(substr myAddress (+ 3 (vl-string-search
":" myAddress))))

                ;;;--- Get the ending row number of the range
                (setq LstRow(fix(atof myAddress)))

                ;;;--- Get the ending column number of the range
                (setq LstCol(fix(atof (substr myAddress (+ (strlen
(itoa LstRow)) 2)))))

                ;;;--- Get the data by row into a list
                (princ "\n Getting Excel Data...")

                ;;;--- Get each cells value and store it in a list
                (setq dataList (getRangeCells 1stRow 1stCol LstRow
LstCol))

                (princ " Done.")

                (princ "\n Exiting EXCEL...")
                (princ)

                ;;;--- Shut Excel down
                (cond
                  (
                    (not(vlax-object-released-p myApp))
                    (vlax-invoke-method myApp 'QUIT)
                    (vlax-release-object myApp)
                  )
                )

                (princ " Done.")
              )
            )
          )
          (alert "Could not start Excel application!")
        )
      )
      (alert "Could not Find the Excel Object Library!\nSee the XL HELP
section on my Web site.")
    )

    ;;;--- Return the list of data from Excel
    dataList
  )





;;;-----------------------------------------------------------------------------------------------------




  ;;;--- Function to change an attributes value

  (defun repAttVal(en tagName newVal)

    ;;;--- Get the DXF group codes of the entity
    (setq enlist(entget en))

    ;;;--- Get the name of the block
    (setq blkName(cdr(assoc 2 enlist)))

    ;;;--- Check to see if the block's attribute flag is there
    (if(cdr(assoc 66 enlist))
      (progn

        ;;;--- Get the entity name
        (setq en(entnext en))

        ;;;--- Get the entity dxf group codes
        (setq enlist(entget en))

        ;;;--- Get the type of block
        (setq blkType (cdr(assoc 0 enlist)))

        ;;;--- If group 66 then there are attributes nested inside this
block
        (setq group66(cdr(assoc 66 enlist)))

        ;;;--- Loop while the type is an attribute or a nested
attribute exist
        (while(or (= blkType "ATTRIB")(= group66 1))

          ;;;--- Get the block type
          (setq blkType (cdr(assoc 0 enlist)))

          ;;;--- Get the block name
          (setq entName (cdr(assoc 2 enlist)))

          ;;;--- Check to see if this is the first attribute
          (if(= blkType "ATTRIB")
            (progn

              ;;;--- Get the attribute tag
              (setq attTag(cdr(assoc 2 enlist)))

              ;;;--- Get the value of the attribute
              (setq attVal(cdr(assoc 1 enlist)))

              ;;;--- If this tag matches our search tag name
              (if(= (strcase tagName)(strcase attTag))
                (progn

                  ;;;--- Replace the attribute's value
                  (setq enlist(subst (cons 1 newVal)(assoc 1
enlist)enlist))
                  (entmod enlist)
                  (entupd en)
                )
              )
            )
          )
          ;;;--- Get the next sub-entity or nested entity as you will
          (setq en(entnext en))

          ;;;--- Get the dxf group codes of the next sub-entity
          (setq enlist(entget en))

          ;;;--- Get the block type of the next sub-entity
          (setq blkType (cdr(assoc 0 enlist)))

          ;;;--- See if the dxf group code 66 exist.  if so, there are
more nested attributes
          (setq group66(cdr(assoc 66 enlist)))

        )
      )
    )
  )





;;;---------------------------------------------------------------------------------------





  ;;;--- Function to save the variables from the dialog box

  (defun saveVars()
    (princ "\n Saving variables from dialog box...")
    (setq fileName(get_tile "filename"))
    (setq decPlaces(nth (atoi(get_tile "decplaces")) decList))
    (setq dNode(get_tile "dnode"))
    (setq dCirc(get_tile "dcirc"))
    (setq dLine(get_tile "dline"))
    (setq dBloc(get_tile "dbloc"))
    (setq dAttr(get_tile "dattr"))
    (setq dNote(get_tile "dnote"))
    (setq layerIndex(atoi(get_tile "layers")))
    (setq layerName(nth layerIndex layerList))
    (setq cDia(distof(get_tile "cdia")))
    (setq blkIndex(atoi(get_tile "blocks")))
    (if blkList(setq blkName(nth blkIndex blkList)))
    (setq xtag(get_tile "xtag"))
    (setq ytag(get_tile "ytag"))
    (setq ztag(get_tile "ztag"))
    (princ " Done.")
  )





;;;---------------------------------------------------------------------------------------



  (defun xyz_help()

    (setq helpList(list))
    (setq helpList
      (list
        "ImportXYZ - Help"
        " "
        "   Select a file and press the GETXYZ COORDS button.  The
first 50"
        "   coordinates will show up in the list box for a sanity check
on"
        "   the results.  Next, select the type of action you want to
perform."
        "   When you are ready, press the OKAY button."
        " "
        " FILENAME :"
        " "
        "   The name of the file to open.  Can be an ascii text file
that is delimited"
        "   by spaces, commas, tabs, or number of characters.   Can
also be an EXCEL"
        "   file.  Press the BROWSE FOR FILENAME button to select from
a directory."
        " "
        " "
        " DECIMAL PLACES TO DISPLAY :"
        " "
        "   This will effect the decimal places shown in the list box
only.  This will"
        "   NOT alter the actual point in AutoCAD."
        " "
        " "
        " GETXYZ COORDS : "
        " "
        "   Press this button to open the file and import the
coordinates.  The"
        "   first 50 results will be shown in the list box for a sanity
check."
        " "
        " "
        " DRAW A NODE :"
        "   This will draw an autocad node entity [point] on each
coordinate."
        " "
        " "
        " DRAW A CIRCLE :"
        "   This will draw an autocad circle entity on each
coordinate."
        " "
        " "
        " DRAW LINES :"
        "   This will draw a line from coordinate to coordinate in
order."
        " "
        " "
        " INSERT A BLOCK :"
        "   This will insert a block entity on every coordinate with
the option"
        "   to select the block from a directory."
        " "
        " "
        " EDIT ATTRIBUTE :"
        "   This will insert a block entity on every coordinate with
the options"
        "   to select the block from a directory and input the tag
names to edit."
        "   This will also change the value of the attribute to match
the xyz coords."
        "   Try it using the included example block IMPORTXYZATT.dwg."
        " "
        " "
        " INSERT EXCEL NOTE :"
        "   This function will write the data from the first column in
excel"
        "   on each coordinate with a leader.  ( If each row contains
four items,"
        "   the program assumes the first column of data is a note. )
The program"
        "   will use the default text style and height."
        " "
        "
---------------------------------------------------------------------------"
        " "
        " If you still need help, please email ···@jefferypsanders.com
with any"
        " questions."
        " "
        " "
      )
    )


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
    ;;;
    ;;;--- We need to load a dialog box to show the help information
    ;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

    ;;;--- See if the definition is already loaded
    (if (not (new_dialog "XYZ_HELP" dcl_id))
      (progn
        (alert "The IMPORTXYZ.dcl file could not be found.")
        (exit)
      )
    )

    ;;;--- Add the layer list to the dialog box drop down list
    (start_list "helplist")
    (mapcar 'add_list helpList)
    (end_list)

    ;;;--- Set up an action event
    (action_tile "cancel" "(done_dialog)")

    ;;;--- Display the dialog box
    (start_dialog)
  )



;;;---------------------------------------------------------------------------------------



  ;;;--- Function to get a file name to extract xyz coords from

  (defun getFileName()

    ;;;--- Clear the data from the dialog list-box
    (start_list "xyz")
    (add_list "")
    (end_list)

    ;;;--- Clear the main data list
    (setq dataList(list))

    ;;;--- Get a new file name
    (if(setq filN(getfiled "Select File to Import From" "" "*" 16))

      ;;;--- Display the filename in the dialog box
      (set_tile "filename" filN)
    )
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to save the setting from the secondary dialog box

  (defun saveVars2()
    (setq charNum nil)
    (cond
      ((= (get_tile "type7") "1")(setq delimType 7))
      ((= (get_tile "type8") "1")(setq delimType 8))
      ((= (get_tile "type9") "1")(progn(setq charNum(atoi(get_tile
"charnum")))(setq delimType 9)))
    )

    ;;;--- Return the delimiter type
    delimType
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to enable or disable the character number edit box

  (defun modeCharNum(a)
    (if(= a 1)
      (mode_tile "charnum" 1)
      (mode_tile "charnum" 0)
    )
  )




;;;---------------------------------------------------------------------------------------




  ;;;--- Function to determine which type of delimiter to use

  (defun findDelimiter()

    ;;;--- Start off with no delimiter
    (setq delimType nil)

    ;;;--- Open the file name to read a line of data out for testing
    (if(setq fil(open fileName "r"))
      (progn

        ;;;--- Read the line of data
        (if(setq dataLine(read-line fil))
          (progn

            ;;;--- Test the data against the delimiter patterns
            (cond
              ((wcmatch dataLine (cadr pat1))(setq delimType (car
pat1))) ;type 4
              ((wcmatch dataLine (cadr pat2))(setq delimType (car
pat2))) ;type 3
              ((wcmatch dataLine (cadr pat3))(setq delimType (car
pat3))) ;type 2
              ((wcmatch dataLine (cadr pat4))(setq delimType (car
pat4))) ;type 1
              ((wcmatch dataLine (cadr pat5))(setq delimType (car
pat5))) ;type 6
              ((wcmatch dataLine (cadr pat6))(setq delimType (car
pat6))) ;type 5
              (T (setq delimType 0))
            )
          )
        )

        ;;;--- Close the file
        (close fil)
      )
    )


    ;;;--- If the delimiter was set to zero, then it is either type 7 8
or 9
    (if(= delimType 0)
      (progn


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
        ;;;
        ;;;--- We need to load a dialog box with selections for
delimiter types
        ;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

        ;;;--- See if the definition is already loaded
        (if (not (new_dialog "FINDDELIM" dcl_id))
          (progn
            (alert "The IMPORTXYZ.dcl file could not be found.")
            (exit)
          )
        )

        ;;;--- Disable the number of characters text box
        (mode_tile "charnum" 1)

        ;;;--- Set up some action events
        (action_tile "type7" "(modeCharNum 1)")
        (action_tile "type8" "(modeCharNum 1)")
        (action_tile "type9" "(modeCharNum 2)")
        (action_tile "cancel" "(setq delimType nil)(done_dialog)")
        (action_tile "accept" "(saveVars2)(done_dialog)")

        ;;;--- Display the dialog box
        (start_dialog)

      )
    )

    ;;;--- Return the delimiter type

    delimType
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to get the x y and or z coord from a string of data
based on
  ;;;    the type of delimiter to be used
  ;;;
  ;;;    Parameters:
  ;;;
  ;;;       data = a data string
  ;;;      typeD = the delimiter type 1 through 9
  ;;;
  ;;;         type 1 = x space y
  ;;;         type 2 = x space y space z
  ;;;         type 3 = x comma y
  ;;;         type 4 = x comma y comma z
  ;;;         type 5 = x tab y
  ;;;         type 6 = x tab y tab z
  ;;;         type 7 = x enter y enter
  ;;;         type 8 = x enter y enter z
  ;;;         type 9 = x = # of chars  y = # of chars  z = rest of
characters

  (defun getxyzList(data typeD / x y z)

    (cond

      ;;;--- Delimiter type = x space y
      (
        (= typeD 1)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search " "
data)))))
          (setq z 0.0)
        )
      )
      ;;;--- Delimiter type = x space y space z
      (
        (= typeD 2)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search " "
data)))))
          (setq z (atof (substr data (+ 2 (vl-string-position 32 data 0
T)))))
        )
      )
      ;;;--- Delimiter type = x comma y
      (
        (= typeD 3)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search ","
data)))))
          (setq z 0.0)
        )
      )
      ;;;--- Delimiter type = x comma y comma z
      (
        (= typeD 4)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search ","
data)))))
          (setq z (atof (substr data (+ 2 (vl-string-position 44 data 0
T)))))
        )
      )
      ;;;--- Delimiter type = x tab y
      (
        (= typeD 5)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search (chr 9)
data)))))
          (setq z 0.0)
        )
      )
      ;;;--- Delimiter type = x tab y tab z
      (
        (= typeD 6)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search (chr 9)
data)))))
          (setq z (atof (substr data (+ 2 (vl-string-position 9 data 0
T)))))
        )
      )
      ;;;--- Delimiter type = x enter y
      (
        (= typeD 7)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search " "
data)))))
          (setq z 0.0)
        )
      )
      ;;;--- Delimiter type = x enter y enter z
      (
        (= typeD 8)
        (progn
          (setq x (atof data))
          (setq y (atof (substr data (+ 2 (vl-string-search " "
data)))))
          (setq z (atof (substr data (+ 2 (vl-string-position 32 data 0
T)))))
        )
      )
      ;;;--- Delimiter type = # of characters
      (
        (= typeD 9)
        (progn
          (setq x (atof (substr data 1 charNum)))
          (setq y (atof (substr data (+ charNum 1) charNum)))
          (setq z (atof (substr data (+ charNum charNum 2) charNum)))
        )
      )
    )

    ;;;--- Return a list of real numbers

    (list x y z)
  )






;;;---------------------------------------------------------------------------------------




  ;;;--- Function to get the data from a file
  ;;;
  ;;;    The type of files can be:
  ;;;
  ;;;    An ascii file delimited with a space, comma, or tab.
  ;;;    An ascii file delimited by the enter key or new line
character.
  ;;;    An EXCEL spread sheet.

  (defun getData()

    ;;;--- If the file name in the dialog text box does not exist...
    (if(= "" (setq fileName(get_tile "filename")))

      ;;;--- Alert the user to enter a file name
      (alert "Enter a file name first!")

      ;;;--- Else the file name exist...
      (progn

        ;;;--- Figure out what type of file it is by it's extension
        (setq fileType(strcase (substr fileName (- (+ 1(strlen
fileName)) 3))))

        ;;;--- Inform the user of action...
        (princ (strcat "\n Opening " fileType " file..."))

        ;;;--- If the file is not an EXCEL file...
        (if(/= fileType "XLS")
          (progn

            (princ "\n Determining delimiter...")

            ;;;--- Go find the type of delimeter to use on the ascii
file
            (if(setq delimType(findDelimiter))
              (progn

                (princ " Done.")

                (princ "\n Counting line numbers...")
                ;;;--- Open the file to read and count the number of
lines
                ;;;    We will need this for the progress bar
                (if(setq filt(open fileName "r"))
                  (progn

                    ;;;--- Set up a line counter
                    (setq linecnt 0)

                    ;;;--- While a next line exist, count the lines
inside the file
                    (while (read-line filt)(setq linecnt(+ linecnt 1)))

                    ;;;--- Close the file
                    (close filt)

                    (princ " Done.")

                    ;;;--- Open the file again for reading
                    (setq fil(open fileName "r"))

                    ;;;--- Set the main data list to nil and a line
counter to zero
                    (setq dataList(list) thisLine 0)

                    (princ "\n Extracting coords...")

                    ;;;--- Read the file as long as there are lines to
read
                    (while (setq dataLine(read-line fil))

                      ;;;--- Increment the line counter
                      (setq thisLine(+ thisLine 1))

                      ;;;--- Update the progress bar with a percentage
complete
                      (updateProgressBar (/ (float thisLine) lineCnt))

                      ;;;--- If the delimiter type is 7  [ x enter y
enter ]...
                      (if(= delimType 7)

                        ;;;--- If the next line is available to read to
get the y coord
                        (if(setq a(read-line fil))

                          ;;;--- Add the y coord to the data line
                          (setq dataLine(strcat dataLine " " a))

                          ;;;--- Else the file has ended and there is
no y coord to be read
                          (progn

                            ;;;--- Let the user know you are going to
substitute in a fake y coord
                            ;;;    instead of crashing the program
                            (alert "The data file does not have a
finishing Y-Coordinate.\nAdding -1 for Y-Coord!")

                            ;;;--- Add the fake y coord to the data
line
                            (setq dataLine(strcat dataline " -1.0"))
                          )
                        )
                      )

                      ;;;--- If the delimiter is type 8 [ x enter y
enter z enter ]...
                      (if(= delimType 8)

                        ;;;--- If the next line is available to read to
get the y coord...
                        (if(setq a(read-line fil))

                          ;;;--- If the next line is available to read
to get the z coord...
                          (if(setq b(read-line fil))


                            ;;;--- Add the y and z coord to the data
line
                            (setq dataLine(strcat dataLine " " a " "
b))

                            ;;;--- Else, the z coord was not available.
Let the user know ...
                            (progn

                              ;;;--- Alert the user we are going to
substitute in a fake z coord
                              ;;;    instead of crashing the program
                              (alert "The data file does not have a
finishing Y-Coordinate.\nAdding -1 for Y-Coord!")

                              ;;;--- Add the z coord to the data line
                              (setq dataLine(strcat dataLine " " a "
-1.0"))
                            )
                          )

                          ;;;--- Else there was not y coord available
to read...
                          (progn

                            ;;;--- Alert the user we are going to
substitute in a fake y & z coord
                            ;;;    instead of crashing the program

                            (alert "The data file does not have a
finishing Y or Z Coordinate.\nAdding -1 for Y & Z Coord!")

                            ;;;--- Add the fake y and z coord to the
data line
                            (setq dataLine(strcat dataLine " " "-1.0
-1.0"))
                          )
                        )
                      )


                      ;;;--- Send the data line to the function to
create a point list from a string
                      ;;;    based on the type of delimiter required to
read the string
                      (setq xyzList(getxyzList dataLine delimType))

                      ;;;--- Add the xyz point list to the main data
list
                      (setq dataList(append dataList (list xyzList)))
                    )

                    (princ " Done.")

                    ;;;--- We are finally finished reading the file,
update the progress bar
                    (updateProgressBar 100)

                    ;;;--- Close the file
                    (close fil)

                    (princ (strcat"\n Closed " fileType " file."))

                    ;;;--- Display the first 50 lines of data in the
dialog box
                    (displayXYZ)

                  )

                  ;;;--- Else we could not open the file for reading
                  (alert "Could not open file!\n\nMake sure it is not
opened or protected!")
                )
              )
            )
          )

          ;;;--- Else, this must be an EXCEL file
          (progn

            ;;;--- Send the EXCEL file name to the XL_GET routine to
extract the xyz data
            (if(setq XList(XL_GET fileName))
              (progn

                ;;;--- Clear the main data list
                (setq dataList(list))


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
                ;;;
                ;;;--- Cycle through the data returned from the EXCEL
file
                ;;;
                ;;;    Do this carefully.  The excel file could contain
a lot of data
                ;;;    so we do not want to have two list containing
the data.
                ;;;
                ;;;    XList contains the data retrieved from EXCEL.
                ;;;      Data in the form of:
                ;;;        ( (rowNum xString) (rowNum yString) )
                ;;;                         or
                ;;;        ( (rowNum xString) (rowNum yString) (rowNum
zString) )
                ;;;
                ;;;    dataList will contain the data converted to a
point list.
                ;;;      Data in the form of:
                ;;;         (x y z)  - z will be substituted in if
necessary as 0.0
                ;;;
                ;;;    I need to convert the data from XList [ row
xyzString ] into a
                ;;;    point list containing the x y and z coords [ "x
y z" ] for
                ;;;    the dataList.
                ;;;
                ;;;    So I will take the first row,
                ;;;    whether it contains two items or three and make
one point list
                ;;;    out of it containing an x y and z coord
(possibly fake z coord),
                ;;;    then add it to the datalist.  At the same time I
will remove the
                ;;;    row from the XList.  This way there will not be
two list of
                ;;;    data that are possibly enormous in size.
                ;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;


                ;;;--- While there are items left in the XList

                (while XList

                  ;;;--- Get the first item in the XList  [ row xString
]
                  (setq a(car XList))

                  ;;;--- Get the row number
                  (setq row(car a))

                  ;;;--- Start building a list of strings containing
the x coord
                  (setq data(list (cdr a)))

                  ;;;--- Remove the x coord from the XList
                  (setq XList(cdr XList))

                  ;;;--- While the row number matches something in the
XList...
                  (while (assoc row XList)

                    ;;;--- Get the y and z coords and add them to the
list
                    (setq data(append data (list(cdr(car XList)))))

                    ;;;--- If you add something to the data list,
remove it from the XList
                    (setq XList(cdr XList))
                  )

                  ;;;--- If a z coord was not found...
                  (if(= (length data) 2)

                    ;;;--- Add a fake z coord in
                    (setq data(append data (list 0.0)))
                  )

                  ;;;--- Add the xyz list to the main data list
                  (setq dataList(append dataList (list data)))
                )

                ;;;--- Display the first 50 results in the dialog box
                (displayXYZ)
              )
            )
          )
        )
      )
    )
  )





;;;---------------------------------------------------------------------------------------



  ;;;--- Function to display the x y z coords in the dialog box

  (defun displayXYZ()

    ;;;--- Inform the user
    (princ "\n Displaying data...")

    ;;;--- Set a flag to ignore note data
    (setq moreData nil)

    ;;;--- Get the number of decimal places the user has chosen
    (setq decPlaces(atoi(nth (atoi(get_tile "decplaces")) decList)))

    ;;;--- If there is valid data...
    (if(> (length dataList) 0)
      (progn

        ;;;--- Remove all rows with nil in them
        (setq tmpData(list))
        (foreach a dataList
          (if(not(member nil a))
            (setq tmpData(append tmpData(list a)))
          )
        )
        (setq dataList tmpData tmpData nil)


        ;;;--- Check to see if we have more data in the list than x y &
z, a note perhaps
        (if(> (length (car dataList)) 3)
          (setq moreData T)
        )


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
        ;;;
        ;;;--- Use the first 500 items to find the longest integer to
display
        ;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

        ;;;--- Set the longest integer variable up
        (setq longestInt 0)

        ;;;--- Set up a counter so we don't exceed 500 values  [ time
issue ]
        (setq cnt 0)

        ;;;--- While we do not exceed the 500th item...
        (while(< cnt 500)

          ;;;--- And there are items left in the dataList
          (if(> (length dataList) cnt)
            (progn

              ;;;--- Get the nth item from the dataList
              (setq a(nth cnt dataList))

              (if moreData
                (progn
                  ;;;--- Get the integer part of the x y and z coords
as a string
                  (setq x(itoa(fix(nth 1 a))))
                  (setq y(itoa(fix(nth 2 a))))
                  (setq z(itoa(fix(nth 3 a))))
                )
                (progn
                  ;;;--- Get the integer part of the x y and z coords
as a string
                  (setq x(itoa(fix(nth 0 a))))
                  (setq y(itoa(fix(nth 1 a))))
                  (setq z(itoa(fix(nth 2 a))))
                )
              )

              ;;;--- Check the "integer" string lengths for a longer
one
              (if(> (strlen x) longestInt)(setq longestInt(strlen x)))
              (if(> (strlen y) longestInt)(setq longestInt(strlen y)))
              (if(> (strlen z) longestInt)(setq longestInt(strlen z)))
            )
          )

          ;;;--- Increment the counter to get the next item
          (setq cnt(+ cnt 1))
        )


        ;;;--- Set up a string to display as a header in the dialog
list box
        (setq x "X" y "Y" z "Z")
        (while(< (strlen x) (+ longestInt 2 decPlaces))(setq x(strcat x
" ")))
        (while(< (strlen y) (+ longestInt 2 decPlaces))(setq y(strcat y
" ")))
        (while(< (strlen z) (+ longestInt 2 decPlaces))(setq z(strcat z
" ")))

        ;;;--- Add the header to the dialog list box
        (start_list "xyz")
        (add_list (strcat X Y Z))
        (end_list)

        ;;;--- Start the routine to add the first 50 xyz coords to the
list box
        (start_list "xyz" 2)

        ;;;--- Set up a counter to make sure we do not display more
than 50 [time issue]
        (setq cnt 0)

        ;;;--- While there are items to display and we have not
exceeded 50
        (while(and (> (length dataList) cnt)(< cnt 50))

          ;;;--- Get the nth item from the data list
          (setq a(nth cnt dataList))

          (if moreData
            (progn
              (setq x(rtos (nth 1 a) 2 decPlaces))
              (setq y(rtos (nth 2 a) 2 decPlaces))
              (setq z(rtos (nth 3 a) 2 decPlaces))
            )
            (progn
              ;;;--- Get the xy and z coords as strings
              (setq x(rtos (nth 0 a) 2 decPlaces))
              (setq y(rtos (nth 1 a) 2 decPlaces))
              (setq z(rtos (nth 2 a) 2 decPlaces))
            )
          )

          ;;;--- Pad the xy & z if necessary for display purposes
          (while(< (strlen x) (+ longestInt 1 decPlaces))(setq x(strcat
" " x)))
          (while(< (strlen y) (+ longestInt 1 decPlaces))(setq y(strcat
" " y)))
          (while(< (strlen z) (+ longestInt 1 decPlaces))(setq z(strcat
" " z)))

          ;;;--- Add the xyz coord to the dialog list box
          (add_list (strcat x " " y " " z))

          ;;;--- Increment the counter to get the next point
          (setq cnt(+ cnt 1))
        )

        ;;;--- Finalize the list box
        (end_list)

        ;;;--- Enable tiles
        (mode_tile "dnode" 0)
        (mode_tile "dcirc" 0)
        (mode_tile "dline" 0)
        (mode_tile "dbloc" 0)
        (mode_tile "dattr" 0)
        (mode_tile "dnote" 0)
        (mode_tile "layers" 0)
        (mode_tile "blocks" 1)
        (mode_tile "getblkname" 1)
        (mode_tile "cdia" 1)
        (mode_tile "xtag" 1)
        (mode_tile "ytag" 1)
        (mode_tile "ztag" 1)
      )
    )
    (princ " Done.")
  )





;;;---------------------------------------------------------------------------------------


  ;;;--- Functions to enable and disable tiles as necessary

  (defun modeDnode()
    (mode_tile "layers" 0)
    (mode_tile "cdia" 1)
    (mode_tile "blocks" 1)
    (mode_tile "getblkname" 1)
    (mode_tile "xtag" 1)
    (mode_tile "ytag" 1)
    (mode_tile "ztag" 1)
  )

  (defun modeDcirc()
    (mode_tile "layers" 0)
    (mode_tile "cdia" 0)
    (mode_tile "blocks" 1)
    (mode_tile "getblkname" 1)
    (mode_tile "xtag" 1)
    (mode_tile "ytag" 1)
    (mode_tile "ztag" 1)
  )

  (defun modeDline()
    (mode_tile "layers" 0)
    (mode_tile "cdia" 1)
    (mode_tile "blocks" 1)
    (mode_tile "getblkname" 1)
    (mode_tile "xtag" 1)
    (mode_tile "ytag" 1)
    (mode_tile "ztag" 1)
  )

  (defun modeDbloc()
    (mode_tile "layers" 1)
    (mode_tile "cdia" 1)
    (mode_tile "blocks" 0)
    (mode_tile "getblkname" 0)
    (mode_tile "xtag" 1)
    (mode_tile "ytag" 1)
    (mode_tile "ztag" 1)
  )

  (defun modeDattr()
    (mode_tile "layers" 1)
    (mode_tile "cdia" 1)
    (mode_tile "blocks" 0)
    (mode_tile "getblkname" 0)
    (mode_tile "xtag" 0)
    (mode_tile "ytag" 0)
    (mode_tile "ztag" 0)
  )

  (defun modeDnote()
    (mode_tile "layers" 0)
    (mode_tile "cdia" 1)
    (mode_tile "blocks" 1)
    (mode_tile "getblkname" 1)
    (mode_tile "xtag" 1)
    (mode_tile "ytag" 1)
    (mode_tile "ztag" 1)
  )




;;;---------------------------------------------------------------------------------------



  ;;;--- Function to update the progress bar
  ;;;
  ;;;    Parameter a = percentage complete   [ a = 0.50 = Fifty percent
complete ]

  (defun upDateProgressBar(a)
    (setq width (dimx_tile "progbar") height (dimy_tile "progbar"))
    (start_image "progbar")
    (fill_image 0 0 width height 250)     ;background color = 250 =
black
    (setq x (fix(* width a)))             ;fill the used area [ width *
percentage used ]
    (fill_image 0 0 x height 1)           ;foreground color = 1 = red
    (end_image)
  )





;;;---------------------------------------------------------------------------------------




  (defun getAttTags(en)

    ;;;--- Set up a list to hold the tag names
    (setq attList(list))

    ;;;--- Get the DXF group codes of the entity
    (setq enlist(entget en))

    ;;;--- Get the name of the block
    (setq blkName(cdr(assoc 2 enlist)))

    ;;;--- Check to see if the block's attribute flag is there
    (if(cdr(assoc 66 enlist))
      (progn

        ;;;--- Get the entity name
        (setq en(entnext en))

        ;;;--- Get the entity dxf group codes
        (setq enlist(entget en))

        ;;;--- Get the type of block
        (setq blkType (cdr(assoc 0 enlist)))

        ;;;--- If group 66 then there are attributes nested inside this
block
        (setq group66(cdr(assoc 66 enlist)))

        ;;;--- Loop while the type is an attribute or a nested
attribute exist
        (while(or (= blkType "ATTRIB")(= group66 1))

          ;;;--- Get the block type
          (setq blkType (cdr(assoc 0 enlist)))

          ;;;--- Get the block name
          (setq entName (cdr(assoc 2 enlist)))

          ;;;--- Check to see if this is the first attribute
          (if(= blkType "ATTRIB")
            (progn

              ;;;--- Get the attribute tag
              (setq attTag(cdr(assoc 2 enlist)))

              ;;;--- Add the tag to the tag list
              (setq attList(append attList (list attTag)))

            )
          )
          ;;;--- Get the next sub-entity or nested entity as you will
          (setq en(entnext en))

          ;;;--- Get the dxf group codes of the next sub-entity
          (setq enlist(entget en))

          ;;;--- Get the block type of the next sub-entity
          (setq blkType (cdr(assoc 0 enlist)))

          ;;;--- See if the dxf group code 66 exist.  if so, there are
more nested attributes
          (setq group66(cdr(assoc 66 enlist)))

        )
      )
    )

    ;;;--- Return the tag list
    attList
  )






;;;---------------------------------------------------------------------------------------





  ;;;--- Function to get a block name from file and it's attribute tags

  (defun getBlkFromFile()

    ;;;--- If the user selects a block...
    (if(setq blk(getfiled "Select Block" "" "dwg" 16))
      (progn

        ;;;--- See if the block name already exist
        (if(not(member (vl-filename-base blk) blkList))
          (progn

            ;;;--- Add the block name to the block list
            (setq blkList(append blkList (list blk)))

            ;;;--- Add the block name to the block popup list in the
dialog box
            (start_list "blocks")
            (mapcar 'add_list blkList)
            (end_list)

            ;;;--- Set the currently selected block to the item added
            (set_tile "blocks" (itoa (- (length blkList) 1)))

          )

          ;;;--- Else the block exist so, select it in the dialog block
popup list
          (progn

            (setq a(member (vl-filename-base blk) blkList))
            (setq blkIndex (- (length blkList) (length a)))
            (set_tile "blocks" (itoa blkIndex))

          )
        )
      )
    )
  )




;;;---------------------------------------------------------------------------------------






;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  ;;;
;;;
  ;;;  888       888          888           8888888      8888   888
;;;
  ;;;  8888     8888         88888            888        88888  888
;;;
  ;;;  88888   88888        888 888           888        888888 888
;;;
  ;;;  888888 888888       888   888          888        888 888888
;;;
  ;;;  888 88888 888      88888888888         888        888  88888
;;;
  ;;;  888  888  888     888       888      8888888      888   8888
;;;
  ;;;
;;;
  ;;;
;;;
  ;;;           888            888888888        888888888
;;;
  ;;;          88888           888   888        888   888
;;;
  ;;;         888 888          888   888        888   888
;;;
  ;;;        888   888         888888888        888888888
;;;
  ;;;       88888888888        888              888
;;;
  ;;;      888       888       888              888
;;;
  ;;;
;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;


  ;;;--- Turn the command echo off
  (setvar "cmdecho" 0)

  ;;;--- Set the main list to nil
  (setq dataList (list))

  ;;;--- Build match patterns for delimiter checking
  (setq pat1(list 4 "*`,*`,*"))
  (setq pat2(list 3 "*`,*"))
  (setq pat3(list 2 "* * *"))
  (setq pat4(list 1 "* *"))
  (setq pat5(list 6 "*\t*\t*"))
  (setq pat6(list 5 "*\t*"))

  ;;;--- Turn the note flag to off [ no notes attached to data ]
  (setq moreData nil)

  ;;;--- Build a list to hold the layer names
  (setq layerList(list))

  ;;;--- Get the first layer name in the drawing
  (if(setq layN(tblnext "LAYER" T))
    (progn

      ;;;--- Save the layer name in the list
      (setq layerList(append layerList (list (cdr (assoc 2 layN)))))

      ;;;--- Loop through all of the remaining layers
      (while(setq layN(tblnext "LAYER"))
        (setq layerList(append layerList (list (cdr(assoc 2 layN)))))
      )
    )
  )

  ;;;--- Build a list to hold the block names
  (setq blkList(list))

  ;;;--- Get the first block name in the drawing
  (if(setq blkN(tblnext "BLOCK" T))
    (progn

      ;;;--- Save the block name in the list
      (setq blkList(append blkList (list (cdr (assoc 2 blkN)))))

      ;;;--- Loop through all of the remaining blocks
      (while(setq blkN(tblnext "BLOCK"))
        (setq blkList(append blkList (list (cdr(assoc 2 blkN)))))
      )
    )
  )


  ;;;--- Build a list of valid decimal places
  (setq decList(list "0" "1" "2" "3" "4" "5" "6" "7" "8"))

  ;;;--- Load the dialog box file
  (setq dcl_id (load_dialog "IMPORTXYZ.dcl"))

  ;;;--- See if the definition is already loaded
  (if (not (new_dialog "IMPORTXYZ" dcl_id))
    (progn
      (alert "The IMPORTXYZ.dcl file could not be found.")
      (exit)
    )
  )

  ;;;--- Add the layer list to the dialog box drop down list
  (start_list "layers")
  (mapcar 'add_list layerList)
  (end_list)

  ;;;--- Add the block list to the dialog box drop down list
  (start_list "blocks")
  (mapcar 'add_list blkList)
  (end_list)

  ;;;--- Add the decimal places list to the dialog box drop down list
  (start_list "decplaces")
  (mapcar 'add_list decList)
  (end_list)

  (setq width (dimx_tile "progbar") height (dimy_tile "progbar"))
  (start_image "progbar")
  (fill_image 0 0 width height 250)  ;250 = AutoCAD black
  (end_image)

  ;;;--- Disable tiles
  (mode_tile "dnode" 1)
  (mode_tile "dcirc" 1)
  (mode_tile "dline" 1)
  (mode_tile "dbloc" 1)
  (mode_tile "dattr" 1)
  (mode_tile "dnote" 1)
  (mode_tile "layers" 1)
  (mode_tile "cdia" 1)
  (mode_tile "blocks" 1)
  (mode_tile "getblkname" 1)
  (mode_tile "xtag" 1)
  (mode_tile "ytag" 1)
  (mode_tile "ztag" 1)

  ;;;--- If an action event occurs, do this function
  (action_tile "help" "(xyz_help)")
  (action_tile "dnode" "(modeDnode)")
  (action_tile "dcirc" "(modeDcirc)")
  (action_tile "dline" "(modeDline)")
  (action_tile "dbloc" "(modeDbloc)")
  (action_tile "dattr" "(modeDattr)")
  (action_tile "dnote" "(modeDnote)")
  (action_tile "getblkname" "(getBlkFromFile)")
  (action_tile "getfile" "(getFileName)")
  (action_tile "getdata" "(getData)")
  (action_tile "decplaces" "(displayXYZ)")
  (action_tile "cancel" "(setq ddiag 1)(done_dialog)")
  (action_tile "accept" "(setq ddiag 2)(saveVars)(done_dialog)")

  ;;;--- Display the dialog box
  (start_dialog)

  ;;;--- Unload the dialog box from memory, it is not need any longer
  (unload_dialog dcl_id)

  ;;;--- If the cancel button was pressed - display message
  (if (= ddiag 1)
    (setq exitMessage "\n IMPORTXYZ Cancelled. \n ")
  )

  ;;;--- If the "Create" button was pressed
  (if (= ddiag 2)
    (progn

      ;;;--- Save the current snap settings
      (setq oldSnap(getvar "osmode"))

      ;;;--- Turn the osnaps off
      (setvar "osmode" 0)

      ;;;--- Save the current layer
      (setq oldLay(getvar "clayer"))

      ;;;--- Set the layer
      (setvar "clayer" layerName)


      ;;;--- Run a series of test based on the item chosen in the
dialog box
      (cond

        ;;;--- If the user wanted to draw a node on each point
        (
          (= dNode "1")
          (progn

            ;;;--- Display a message on the command line
            (princ "\n Placing nodes...")

            ;;;--- Cycle through each point in the list
            (foreach a dataList

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Draw a node on the point
                (command "point" (cdr a))

                ;;;--- Else, draw a node on the point
                (command "point" a)
              )
            )

            (princ " Done.")

          )
        )

        ;;;--- If the user wanted to draw a circle on each point
        (
          (= dCirc "1")
          (progn

            ;;;--- Display a message on the command line
            (princ "\n Placing circles...")

            ;;;--- Cycle through each point in the list

            (foreach a dataList

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Draw a node on the point
                (command "circle" (cdr a) "D" cDia)


                ;;;--- Else, draw the circle
                (command "circle" a "D" cDia)
              )
            )

            (princ " Done.")

          )
        )

        ;;;--- If the user wanted to draw lines to each point
        (
          (= dLine "1")
          (progn


            ;;;--- Display a message on the command line
            (princ "\n Drawing lines...")

            ;;;--- If the point is prefixed with a note
            (if moreData

              ;;;--- Start the line command on the first point
              (command "line" (cdr(car dataList)))

              ;;;--- Else, start the line command on the first point
like this
              (command "line" (car dataList))
            )


            ;;;--- Cycle through each point in the list except the
first [ already used ]
            (foreach a (cdr dataList)

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Send the point to the line command
                (command (cdr a))

                ;;;--- Else, send the point to the line command like
this
                (command a)
              )
            )

            ;;;--- End the line command
            (command)

            (princ " Done.")

          )
        )

        ;;;--- If the user wanted to insert a block on each point
        (
          (= dBloc "1")
          (progn

            ;;;--- Set up a counter to keep the user informed
            (setq cnt 0)

            ;;;--- Cycle through each point in the list
            (foreach a dataList

              ;;;--- Increment the counter
              (setq cnt(+ cnt 1))

              ;;;--- Inform the user of progress
              (princ "\n Inserting block # ")(princ cnt)

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Insert the block using the dimscale and rotation
of zero
                (command "-insert" blkName (cdr a) (getvar "dimscale")
"" 0)

                ;;;--- Else, insert the block using the dimscale and
rotation of zero
                (command "-insert" blkName a (getvar "dimscale") "" 0)
              )
            )

            (princ "\n Finished inserting ")(princ cnt)(princ "
blocks.")

          )
        )

        ;;;--- If the user wanted to insert a block on each point and
upate attributes in the block
        (
          (= dAttr "1")
          (progn

            ;;;--- Save the current state of the attribute request
system variable
            (setq oldAttReq(getvar "attreq"))

            ;;;--- Turn the attribute request off
            (setvar "attreq" 0)

            ;;;--- Set up a counter to keep the user informed
            (setq cnt 0)


            ;;;--- Cycle through each point in the list
            (foreach a dataList

              ;;;--- Increment the counter
              (setq cnt(+ cnt 1))

              ;;;--- Inform the user of progress
              (princ "\n Inserting block # ")(princ cnt)

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Insert the block using the dimscale and rotation
of zero
                (command "-insert" blkName (cdr a) (getvar "dimscale")
"" 0)

                ;;;--- Else, insert the block using the dimscale and
rotation of zero
                (command "-insert" blkName a (getvar "dimscale") "" 0)
              )

              ;;;--- Get the entity name of the last inserted block
              (setq en(entlast))

              ;;;--- If the point is prefixed with a note
              (if moreData
                (progn

                  ;;;--- Replace the x y and z tags of the attribute
                  (repAttVal en xTag (rtos(nth 1 a)))
                  (repAttVal en yTag (rtos(nth 2 a)))
                  (repAttVal en zTag (rtos(nth 3 a)))
                )

                ;;;--- Else,
                (progn

                  ;;;--- Replace the x y and z tags of the attribute
                  (repAttVal en xTag (rtos(nth 0 a)))
                  (repAttVal en yTag (rtos(nth 1 a)))
                  (repAttVal en zTag (rtos(nth 2 a)))
                )
              )
            )

            (princ "\n Finished inserting ")(princ cnt)(princ " blocks
and updating their attributes.")

            ;;;--- Reset the attribute request to previous state
            (setvar "attreq" oldAttReq)
          )
        )

        ;;;--- If the user wanted to insert a note from excel on each
point
        (
          (= dNote "1")
          (progn

            ;;;--- Display a message on the command line
            (princ "\n Placing notes...")

            ;;;--- Cycle through each point in the list
            (foreach a dataList

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Draw a node on the point
                (command "dim1" "Lea" (cdr a) (polar (cdr a) (* pi
0.25) (* 4.0(getvar "textsize"))) "" (car a))

                ;;;--- Else, draw a node on the point
                (command "point" a)
              )
            )

            (princ " Done.")
          )
        )

      )

      ;;;--- Reset the osnaps to previous state
      (setvar "osmode" oldSnap)

      ;;;--- Reset the current layer to previous state
      (setvar "clayer" oldLay)
    )
  )

  ;;;--- Reset the command echo
  (setvar "cmdecho" 1)

  ;;;--- Display a message
  (princ exitMessage)

  ;;;--- Suppress the last echo for a clean exit
  (princ)
)

From: Kalle Olavi Niemitalo
Subject: Re: Import XYZ Modifications Help
Date: 
Message-ID: <87iro5cg24.fsf@Astalo.kon.iki.fi>
"Ruminari" <········@hotmail.com> writes:

> I have a collection of data (X Y Rotation) separated by spaces in a txt
> format.  Next I'm wanting to import this data into autocad utilizing
> Import XYZ.  However, instead of the XYZ, I basically want to do
> XYRotation.  This will allow me to insert a basic block and rotate it
> to the proper Rotational value.

It's been years since I had access to AutoCAD, but I think the
following changes might make the function use the Z coordinates
as rotations instead, when it inserts blocks.  However, any
attached notes will still get Z coordinates.

In case this doesn't work, you may find more knowledgeable people
on comp.cad.autocad.

              ;;;--- If the point is prefixed with a note
              (if moreData

                ;;;--- Insert the block using the dimscale and rotation of zero
OLD:            (command "-insert" blkName (cdr a) (getvar "dimscale") "" 0)
NEW:            (command "-insert" blkName (cdr a) (getvar "dimscale") "" (nth 3 a))

                ;;;--- Else, insert the block using the dimscale and rotation of zero
OLD:            (command "-insert" blkName a (getvar "dimscale") "" 0)
NEW:            (command "-insert" blkName a (getvar "dimscale") "" (nth 2 a))
              )

              ;;;--- Get the entity name of the last inserted block
              (setq en(entlast))

              ;;;--- If the point is prefixed with a note
              (if moreData
                (progn

                  ;;;--- Replace the x y and z tags of the attribute
                  (repAttVal en xTag (rtos(nth 1 a)))
                  (repAttVal en yTag (rtos(nth 2 a)))
OLD:              (repAttVal en zTag (rtos(nth 3 a)))
NEW:              (repAttVal en zTag (rtos 0.0))
                )

                ;;;--- Else,
                (progn

                  ;;;--- Replace the x y and z tags of the attribute
                  (repAttVal en xTag (rtos(nth 0 a)))
                  (repAttVal en yTag (rtos(nth 1 a)))
OLD:              (repAttVal en zTag (rtos(nth 2 a)))
NEW:              (repAttVal en zTag (rtos 0.0))
                )
              )
From: Ruminari
Subject: Re: Import XYZ Modifications Help
Date: 
Message-ID: <1148074215.868665.12680@38g2000cwa.googlegroups.com>
Kalle,

Awesome,  thanks for the coding.  I'll give it a run as soon as I get a
chance and see if it works.
From: Ruminari
Subject: Re: Import XYZ Modifications Help
Date: 
Message-ID: <1148342966.095046.97660@j73g2000cwa.googlegroups.com>
Kalle,

I just got a chance to make the changes and it appears that things are
working correctly.  I greatly appreciate your help.  It would have
taken me forever to figure out the 4 small changes that I needed to do.

Thanks Again.