;;; AutoCATS 리습 자료실
;; 명령: TXSWAP
;; 기능: 두 TEXT의 내용만 서로 바꾸고 위치·높이·스타일은 유지합니다.
;; 출처: https://www.autocats.co.kr/lisp/text-swap
;; 버전: 1.0 (2026-10-23)
;; 라이선스: 자유 사용·수정, 재배포 시 출처(autocats.co.kr) 표기
;; 안전: 잠긴 레이어·외부참조 보호, 변경은 UNDO 그룹, 명령별 범위는 상세 가이드 참고

(vl-load-com)

(defun autocats-txswap-safe-p (ent / data row block)
  (setq data (entget ent)
    row (tblsearch "LAYER" (cdr (assoc 8 data))))
  (and data row (= 0 (logand 4 (cdr (assoc 70 row))))
    (or (/= "INSERT" (cdr (assoc 0 data)))
      (and (setq block (tblsearch "BLOCK" (cdr (assoc 2 data))))
        (= 0 (logand 12 (cdr (assoc 70 block))))))))

(defun autocats-txswap-replace-pair (code value data)
  (if (assoc code data) (subst (cons code value) (assoc code data) data)
    (append data (list (cons code value)))))

(defun autocats-txswap-put (ent property value / data)
  (if (autocats-txswap-safe-p ent)
    (progn
      (setq data (autocats-txswap-replace-pair 1 value (entget ent)))
      (if (entmod data) (progn (entupd ent) T)))))

(defun autocats-txswap-get (ent property)
  (cdr (assoc 1 (entget ent))))

(defun autocats-txswap-apply (a b / av bv)
  (and (/= a b) (autocats-txswap-safe-p a) (autocats-txswap-safe-p b)
    (= "TEXT" (cdr (assoc 0 (entget a)))) (= "TEXT" (cdr (assoc 0 (entget b))))
    (setq av (autocats-txswap-get a 'TextString) bv (autocats-txswap-get b 'TextString))
    (null (vl-string-search "%<" av)) (null (vl-string-search "%<" bv))
    (autocats-txswap-put a 'TextString bv)
    (if (autocats-txswap-put b 'TextString av) T (progn (autocats-txswap-put a 'TextString av) nil))))

(defun c:TXSWAP (/ *error* undo-open a b selection)
  (defun *error* (msg)
    (if undo-open (progn (command-s "_.UNDO" "_End") (setq undo-open nil)))
    (if (and msg (not (wcmatch (strcase msg) "*CANCEL*,*QUIT*,*EXIT*,*취소*")))
      (princ (strcat "\n[TXSWAP] 중단: " msg)))
    (princ))

  (setq a (entsel "\n첫 번째 TEXT: ") b (if a (entsel "\n두 번째 TEXT: ")))
  (if (and a b)
    (progn
      (command "_.UNDO" "_Begin")
      (setq undo-open T)
      (if (autocats-txswap-apply (car a) (car b)) (princ "\n교환 완료") (princ "\n지원 대상·잠금·필드를 확인하세요."))
      (command "_.UNDO" "_End") (setq undo-open nil)))

  (princ))

(princ "\n[AutoCATS] TXSWAP 로드 완료")
(princ)
