AfraLISP - Learn AutoLISP for AutoCAD productivity

External Data

by Kenny Ramage

Do you have a library full of blocks taking up vast amounts of disk space?
Do you find it difficult to locate a specific block because you've got so many or cannot remember what you called it?
By using external data you can parametrically draw these objects. If you look at my Structural Steel Programme DDSTEEL you will notice that every section is drawn using data retrieved from an external data file.
The following tutorial will show you how to retrieve external data, format it into something that Autolisp can use, then place the data into individual variables.

First of all you need to create the external data file.
Create a text file called Test.dat and type in the following data :

*6
152.0,10.0,124.0
*7
178.0,12.0,135.0
*8
203.0,14.0,146.0
*9
229.0,16.0,158.0

This type of data file is known as a comma deliminating text file.
The data represents values that we would use to draw a specific object.
The first line (*6) represents the name of the object
and the second line (152.0,10.0,124.0) are the values that we are
attempting to retrieve.

Next, create a Lisp file called Test.Lsp and type in the following :

(defun C:Test (/ item data dline maxs 
                    count chrct numb size)
  (setq size 
    (getstring "\nEnter Size <6, 7, 8 or 9>: "))	;enter size req'd
  (setq	dlist nil
	size  (strcat "*" size)				;add asterix to size
	file  (findfile "test.dat")			;find data file
	fp    (open file "r")				;open file to read
	item  (read-line fp)				;first line is label for file
  );setq
  (while item						;process each line of file
    (if	(= item size)					;compare values
      (setq data (read-line fp)				;read a line
	    item nil					;stop searching for item
      );setq
      (setq item (read-line fp))			;keep searching for item
    );if
  );while
  (if data						;if the size has been found
    (progn
      (setq maxs  (strlen data)				;establish length of input
	    count 1					;initiliaze count
	    chrct 1					;initiliaze char position
      );setq
      (while (< count maxs)				;process string one chr at a time
	(if (/= "," (substr data count 1))		;look for the commas
	  (setq chrct (1+ chrct))			;increment to next position
	  (setq	numb  (atof 
               (substr data 
		  (1+ (- count chrct)) chrct))  	;convert to real
		dlist (append dlist (list numb))	;add it to the list
		chrct 1					;resets field ct
	  );setq
	);if
	(setq count (1+ count))				;increment the counter
      );while
      (setq numb  (atof 
           (substr data 
                  (1+ (- count chrct))))        	;convert to real
	    dlist (append dlist (list numb))		;add it to the list
      );setq
    );progn
  );if data
  (close fp)						;close data file
(mapcar 'set '(a b c) dlist)				;allocate to variables
);defun

The programme basically does the following :

  • Gets the name of the object who's data we want to retrieve.(eg 6)
  • Adds a * to the front of it. (eg *6)
  • Searches for the Data file (Test.Dat) and opens it to read.
  • Reads each line of the file until it finds one matching our objects name.
  • Reads the next line and stores the data.

Unfortunately, the data we have looks something like this :

(152.0,10.0,124.0)

Oh No, Commas...Don't worry the next section of the program deals with them. It parses the data and removes all commas so that we end up with a LIST looking like this :

(152.0 10.0 124.0)

Now by using the mapcar function we can allocate each item in the list to its own variable.

(mapcar 'set '(a b c) dlist)

I have deliberately not declared these variables as locals so that you can view them within AutoCAD.

Type !dlist to view the data list.
Type !a to see the first item in the list.
Type !b to see the second item in the list.
Type !c to see the third item in the list.

You can now use this data to draw your object.

As you can see, this is a much more efficient way of drawing objects that are the same shape but have differing dimensions.

To save you having to type here is the source code for the whole
of this routine. Now don't you think I'm good to you?

Test Zip (7 Kb)