Get Anonymous References
See also Effective Block Name
|Function Syntax||(LM:getanonymousreferences <blk>)|
|blk||String||Block name or wildcard pattern for which to return anonymous references|
|List||List of Anonymous Block Names, else nil if none|
When the properties of a dynamic block reference are altered, the dynamic block is converted to an anonymous block whose EffectiveName property is equal to the name of the original dynamic block.
Hence, when utilising the ssget function with a filter list to obtain a selection set of all references of a particular dynamic block, only those references whose dynamic block properties are unaltered from the time of insertion (and hence aren't anonymous) will be included in the set.
A common workaround is to include all anonymous blocks in the filter list, iterate through the set, and only process those blocks which have the required EffectiveName.
The disadvantage of this workaround is that, when prompted for selection, the user may include all anonymous blocks in the selection, without knowing which blocks will actually be processed by the program.
This GetAnonymousReferences function will iterate over the block table and return a list of the names of all anonymous references associated with a supplied block name or all block names matching a given wildcard pattern.
Armed with a list of the names of all anonymous references for a particular dynamic block, an appropriate ssget filter list may be constructed to include only those references which are relevant to the desired dynamic block.
The function uses my Effective Block Name function to compare the value of the EffectiveName property of the anonymous block references with the supplied block name or wildcard pattern.
I have included the Vanilla AutoLISP version of this function in the code shown below since the Visual LISP EffectiveName property will omit Unicode characters from the block name.
;; Get Anonymous References - Lee Mac ;; Returns the names of all anonymous references of a block. ;; blk - [str] Block name/wildcard pattern for which to return anon. references (defun LM:getanonymousreferences ( blk / ano def lst rec ref ) (setq blk (strcase blk)) (while (setq def (tblnext "block" (null def))) (if (and (= 1 (logand 1 (cdr (assoc 70 def)))) (setq rec (entget (cdr (assoc 330 (entget (tblobjname "block" (setq ano (cdr (assoc 2 def))) ) ) ) ) ) ) ) (while (and (not (member ano lst)) (setq ref (assoc 331 rec)) ) (if (and (entget (cdr ref)) (wcmatch (strcase (LM:al-effectivename (cdr ref))) blk) ) (setq lst (cons ano lst)) ) (setq rec (cdr (member (assoc 331 rec) rec))) ) ) ) (reverse lst) ) ;; Effective Block Name - Lee Mac ;; ent - [ent] Block Reference entity (defun LM:al-effectivename ( ent / blk rep ) (if (wcmatch (setq blk (cdr (assoc 2 (entget ent)))) "`**") (if (and (setq rep (cdadr (assoc -3 (entget (cdr (assoc 330 (entget (tblobjname "block" blk) ) ) ) '("acdbblockrepbtag") ) ) ) ) (setq rep (handent (cdr (assoc 1005 rep)))) ) (setq blk (cdr (assoc 2 (entget rep)))) ) ) blk )
The following example program demonstrates how to use the above GetAnonymousReferences function to construct an ssget filter list to include only those anonymous references which are associated with a specific block name.
(defun c:test ( / blk ) (setq blk (getstring t "\nSpecify name of block to select: ")) (if (tblsearch "block" blk) (sssetfirst nil (getblockselection blk)) (princ (strcat "\n" blk " doesn't exist.")) ) (princ) ) (defun getblockselection ( blk ) (ssget "_X" (list '(0 . "INSERT") (cons 2 (apply 'strcat (cons blk (mapcar '(lambda ( x ) (strcat ",`" x)) (LM:getanonymousreferences blk) ) ) ) ) ) ) )
See also Effective Block Name