 ; Cobra: put entities on snap, change them if necessary.
 ; Caution - do not use this program from within the Dim command.
 ; Copyright 1991, 1995 by Rocket Software
 ; Dedicated to the Shriners - the only people who drive on snap.

 (DEFUN SNAC (asnum / fin x2 df y2)
  (setq fin (cdr (assoc asnum nn)))
  (setq x2 (car fin))
  (setq df (rem x2 bb))
  (if (> (abs df) (/ bb 2))
      (setq x2 (+ x2 (- bb df)))
      (setq x2 (- x2 df)))
  (setq y2 (cadr fin))
  (setq df (rem y2 cc))
  (if (> (abs df) (/ cc 2))
      (setq y2 (+ y2 (- cc df)))
      (setq y2 (- y2 df)))
  (setq nn (subst (cons asnum (list x2 y2)) (assoc asnum nn) nn)))

 (DEFUN C:COBRA ( / ss aa bb cc txa nn nam nam72 df rad txsav)
  (setvar "cmdecho" 0)
  (setq ss (ssget))                               ; select entities
  (command "undo" "mark")
  (setq aa (getvar "snapunit"))                   ; get snap settings
  (setq bb (car aa) cc (cadr aa))                 ; bb=X, cc=Y
  (while (setq txa (ssname ss 0))                 ; first in selection set
         (setq nn (entget txa))                   ; entity data
         (setq nam (cdr (assoc 0 nn)))            ; get entity type
         (if (assoc 72 nn)
             (setq nam72 (cdr (assoc 72 nn))))    ; get text justification

 ; 72 association codes: (= nam72 0)  ; left
 ;                       (= nam72 1)  ; centre
 ;                       (= nam72 2)  ; right
 ;                       (= nam72 3)  ; aligned
 ;                       (= nam72 4)  ; middle
 ;                       (= nam72 5)  ; fit

         (cond
               ((or (= nam "TEXT")                ; if text or
                    (= nam "ATTDEF"))             ; attribute
                (cond ((= nam72 0)                ; if left justified
                       (snac 10))
                      ((or (= nam72 3)            ; if aligned
                           (= nam72 5))           ; or fit
                       (snac 11)
                       (snac 10))
                      (t                          ; else m, r, or c
                       (snac 11)))
                (entmod nn))

               ((= nam "CIRCLE")                  ; if a circle
                (snac 10)
                (setq rad (cdr (assoc 40 nn)))
                (setq df (rem rad bb))
                (if (> (abs df) (/ bb 2))
                    (setq rad (+ rad (- bb df)))
                    (setq rad (- rad df)))
                (if (= rad 0)         ; radius should not be 0
                    (setq rad bb))
                (setq nn (subst (cons 40 rad) (assoc 40 nn) nn))
                (entmod nn))

               ((= nam "LINE")
                (snac 10)
                (snac 11)
                (entmod nn))

               ((or (= nam "TRACE")               ; if a trace
                    (= nam "SOLID"))              ; or a solid
                (snac 10)
                (snac 11)
                (snac 12)
                (snac 13)
                (entmod nn))

               ((= nam "DIMENSION")
                (snac 10)
                (snac 12)
                (snac 13)
                (snac 14)
                (entmod nn))

               ((= nam "POLYLINE")
                (setq txsav txa)
                (setq nn (entget (setq txa (entnext txa))))
                (setq nam (cdr (assoc 0 nn)))
                (while (/= nam "SEQEND")
                       (snac 10)
                       (entmod nn)
                       (entupd (cdr (assoc -1 nn)))
                       (setq nn (entget (setq txa (entnext txa))))
                       (setq nam (cdr (assoc 0 nn))))
                (setq txa txsav))

               ((= nam "INSERT")                  ; must move, not entmod
                (setq fin (cdr (assoc 10 nn)))    ; else atts don't move
                (setq x2 (car fin))
                (setq df (rem x2 bb))
                (if (> (abs df) (/ bb 2))
                    (setq x2 (+ x2 (- bb df)))
                    (setq x2 (- x2 df)))
                (setq y2 (cadr fin))
                (setq df (rem y2 cc))
                (if (> (abs df) (/ cc 2))
                (setq y2 (+ y2 (- cc df)))
                (setq y2 (- y2 df)))
                (command "move" txa "" fin (list x2 y2)))

               (t
                (progn (snac 10) (entmod nn))))
         (ssdel txa ss))                          ; delete from ss, while end
 (princ))