お世話になっております。
ただ今ユーザーに複数オブジェクトを選択させ、
その中にtrue colorで色の設定がされているオブジェクトがあれば、
その色に近しいインデックスカラーに設定を置き換えるautolispを作成中です。
色々検索して、
グループコード62がインデックスカラー、420がtrue colorを示すということがわかり、
https://www.theswamp.org/index.php?topic=52761.msg576434#msg576434
このページに載っているコードをchatGPTでautolispに変換するなど色々して
【以下のコードを読む意味はあんまりないかもです】
(defun c:ACItoRGBLookup ()
(list
(cons 1 '(255 0 0)) (cons 2 '(255 255 0))
(cons 3 '(0 255 0)) (cons 4 '(0 255 255))
(cons 5 '(0 0 255)) (cons 6 '(255 0 255))
;; 他のすべてのACI値に対応するRGB値を続ける...
;; ACI 1から255までの値と対応するRGB色(赤、緑、青の順)を指定
(cons 255 '(255 255 255))
)
)
;; 与えられたRGB値に最も近いACIを見つける関数
(defun c:FindClosestACI (r g b / aci-rgb-list min-dist aci color-diff rgb-list)
(setq aci-rgb-list (c:ACItoRGBLookup))
(setq min-dist 1e+8) ;; 最小距離を非常に大きな数で初期化
(setq aci 0)
;; 与えられたRGB値と各ACI値のRGB値との距離を計算し、最小距離のものを見つける
(foreach item aci-rgb-list
(setq rgb-list (cdr item))
(setq color-diff
(+ (expt (- r (nth 0 rgb-list)) 2)
(expt (- g (nth 1 rgb-list)) 2)
(expt (- b (nth 2 rgb-list)) 2)))
(if (< color-diff min-dist)
(progn
(setq min-dist color-diff)
(setq aci (car item))
)
)
)
aci
)
;; ユーザーにオブジェクトを選択させ、各オブジェクトの情報を表示し、色を近いインデックスカラーに変更する
(defun c:ReplaceColorsWithACI ()
(setq ss (ssget))
(if ss
(progn
(setq len (sslength ss))
(repeat len
(setq ent (ssname ss (setq i (1- len))))
(setq entdata (entget ent))
(setq objtype (cdr (assoc 0 entdata)))
(setq objname (cdr (assoc 330 entdata)))
(setq color (cdr (assoc 62 entdata)))
(princ (strcat "\nObject: " objtype " Handle: " handle " Color Index: " (itoa color)))
(if (and (/= color 0) (/= color 256)) ;; 現在の色がBYLAYERかBYBLOCKでない場合のみ変更
(progn
(prin1 objname)
(princ (strcat "はBYLAYERでもBYBLOCKでもない"))
(setq rgb (cdr (assoc 420 entdata))) ;; RGB値が設定されていれば、それを基に最も近いACI値を見つけて変更
(if rgb
(progn
(setq r (lsh rgb -16))
(setq g (lsh (logand rgb 65280) -8))
(setq b (logand rgb 255))
(princ (strcat "\nR:" (itoa r) " G:" (itoa g) " B:" (itoa b)))
(setq closest-aci (c:FindClosestACI r g b))
(princ (strcat "\nObject: " objtype " Handle: " handle " RGB(" (itoa r) ", " (itoa g) ", " (itoa b) ") -> ACI: " (itoa closest-aci)))
(setq entdata (subst (cons 62 closest-aci) (assoc 62 entdata) entdata))
(entmod entdata)
)
)
)
)
)
)
(princ "No objects selected.")
)
(princ)
)
(princ "\nType 'ReplaceColorsWithACI' to run.")
(princ)
ここまでできたのですが、こちらを実行してから実行後のオブジェクトのプロパティを見ても
色の設定がインデックスカラーによるものになっておらず、true colorのままです。
コマンド実行後にそのオブジェクトのDXF図形情報を見てみるとグループコード62は想定した数字になっているのですが、
なんならコマンド実行前の、新しくオブジェクトを作成して色をBylayerからtrue colorで全く別の色にしただけの段階でDXF図形情報を見ても、
グループコード62はグループコード420で表された色に近しい色の番号になっているのです。
(ということはこのコマンドはまったく何の意味も成さないということでしょうか?)
ここで、お聞きしたいことが2点あります。
① このコマンドを修正し、true colorで色が設定されたオブジェクトを
それに近しい色のインデックスカラーに書き換えられるものにするにはどうすればよいでしょうか?
② ①が実現したら、選択したオブジェクトの中に色設定がBYLAYERやBYBLOCKのものがあれば、
その場合はレイヤーやブロックの色設定をtrue colorからインデックスカラーに書き換えたいと思っています。
この場合、最終的にどのようなコードに変更すれば宜しいでしょうか?
一応、何故このようなことをしたいかと申しますと
普段図面を印刷する際、true colorで色を設定したオブジェクトのみカラーで、その他はすべて黒色で印刷されるように設定しているため
外部からtrue colorのオブジェクトまみれの図面をもらった際、カラフルすぎる図面が印刷されないよう、
true colorのオブジェクトの色設定を一括でインデックスカラーへ変更したいからです。
使用CADはAutoCAD2023です。
どうぞ宜しくお願いいたします。
true colorで設定された色をインデックスカラーへ一括変更したい
- タイ
- 2024/04/26 (Fri) 14:18:21