非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
三.撰写 AutoLISP的动机?1.欲强化 AutoCAD原有指令时. 2.欲创造更有用的 AutoCAD新指令. 3.欲简化繁琐的环境设定或绘图步骤时.
单元一:AutoLISP主角潇洒登场一. AutoLISP是何方神圣?1. AutoLISP是 AutoCAD的最佳拍檔! 2. AutoLISP内含于 AutoCAD软件内,不用另外花钱买! 3. AutoLISP是强化 AutoCAD最好、最直接的『程序语言』! 4. AutoLISP易学、易用,即使不会程序设计的 AutoCAD使用者,都能在最短的时间内,写出令人惊讶、赞叹的功能! 5.若说 AutoLISP的出现,是替 AutoCAD创造一片天的『最大功臣』,实不为过一点也不夸张! 6. AutoLISP希望您去学习它、改善它、发挥它、享受它.真的!它的威力、魅力无穷!
4.欲处理参数式绘图时. 5.欲做图面资料读文件、写文件. 6.欲做 AutoCAD简报展示时. 7.欲达到真正灵活掌控 AutoCAD时. 8.欲提升自己跨上 AutoCAD高手列车时.
四.AutoLISP的效益评估?1.对公司负责人或设计主管而言: A.也许某员工或干部花了 20个小时撰写一个 AutoLISP程序,表面上,这将近三天的时间,他连一张图都没有画,甚至可能偶有发呆、沈思,若此程序一天可以替公司绘图部门节省 1小时绘图时间,那算一算,只要 20天就抵销开发成本,而 20天以后都是赚的,『用的愈久,省的愈多』! B.若员工皆有此动力,在不影响正常工作,『鼓励』都来不及,那有『压抑』的道理,甚至还要派遣优秀人员出去受训,学习更好的设计技巧与创意呢?! C.千万不要因为您的不懂或压抑,SHOW您的权威与 POWER,如此,不但对员工造成打击,甚至您可能成为阻碍了公司计算机化进步的罪魁祸首 D.当然,若要撰写的程序很多,内部设计人员的程序功力距离太远,达成需求的时间反而变得遥遥无期,那倒不如求助于市面上已有的相关 AutoCAD支持软件。 2.对设计人员而言: A.得到一笔提升绩效奖金呢?当然,无形中,『AutoCAD高手的封号』也将黄功力又往前迈出了一大步,对个人的成长帮助匪浅,幸运的话,搞不好还可以袍加身,不亦乐乎!!! B.『半桶水、响叮当』,千万不要因为会写 AutoLISP程序而自傲、孤僻、嚣张起来,功力的增长,只是让您有更多『服务他人、服务公司』的机会,若自恃过重,宁可不要! C. AutoLISP程序功力的累进,是无远弗届的,千万不要『孤芳自赏』,『人外有人,天外有天』,也许您觉得是『宝贝加三级』的程序,只是其它设计师基本程序中的一部份罢了!第 1页,共 27页
二. AutoLISP程序语言的特质分析:学习 AutoLISP是非常容易的,对初学者而言,即使没有学习过任何的程序语言,都能很快的上手,写出精彩漂亮的 AutoLISP程序!语法简单不用特殊的变量宣告,非常富有弹性,比起其它的程序语言,它的语
法可说是非常简单而有其独特的风格!除一般性的功能函数外,又拥有为数不少控制配合 AutoCAD的特功能函数强殊函数,再加上 AutoLISP可直接呼叫执行所有 AutoCAD的指令,大以及掌握运用所有的 AutoCAD系统变量,功能之强大令人欣喜不已!撰写的环境只要是一般的文书编辑软件都适用!如:Windows的记事本、 PE2、不挑剔 PE3、DW3、书中仙、汉书、EDIT....等直译式程序不用再作编译,『即写即测、即测即用』,马上可以在 AutoCAD中响应效果,马上就有成就感! AutoLISP却可在不改写的原貌下,加载与执行!
横跨各作业悠然自得,虽然 AutoCAD有 DOS、 Windows版本之分但是平台
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
D.既然 AutoLISP是 AutoCAD的『最大功臣』,当然不会轻易被舍弃,如此,您的学习,保证不会白费! E.『精益求精』、『虚心求教』、『用心学习、观摩』、『决心成为高手』 3.对程序本身而言: A.少少的几行,却可能有『大大满意』的时候!!! B.充份掌握了控制、创造 AutoCAD的『尚方宝剑』,让您在 AutoCAD的设计运作中『得心应手』,享受无比的快乐与成就感!!!
3.重要的 AutoLISP的基本语法结构规则 1:以括号组成表达式,、相对称左右括号数一定要成双成对规则 2:表达式型态:(操作数运算子运算子运算子) 1.1操作数包括『功能函数』&『自定函式』 1.2运算子(自变量)包括: A.整数(Integer)如 8,-17,500,9999 ..... B.实数(Real)如 8.5,-17.456 ..... C.字符串(String)如"AutoCAD","123" D.串行(List)如 ("a""b""c"),(x y) E.像素名称代码如<entity name: 6000f262> F.档案代码如<file:#12438>..... G.选择群集代码如<Selection set:1>规则 3:表达式中的『运算子』,可以是另一『表达式』或『子程序』规则 4:多重的括号表达式,运算的先后顺序是『由内而外、由左而右』规则 5:以档案型态存在的 AutoLISP程序(ASCII档案),其扩展名必须是.lsp规则 6:撰写的环境,只要是一般的文书编辑软件、记事本,可编辑 ASCII档案者都适用规则 7:以 defun功能函数定义新的指令或新的功能函式规则 8:新定义的功能函式名称,若为『C:函式名』,则此函式可为 AutoCAD新指令规则 9:加载 AutoLISP程序的作法:=>指令:后直接键入 (load"LISP主檔名")规则 10: AutoLISP程序中,在『分号;』后的内容均为批注,程序不处理,适时的增加批注,将使程序更具可看性、学习性及完整性规则 11: AutoLISP最常用的变量型态是『整数』、『实数』、『字符串』、『点串行』四种,变量的型态依据设定值而自动定义,变量会一直储存该值,直到被重新设定值或绘图结束自动消失规则 12:以 setq功能函数设定变量值 (setq变量名称设定值)规则 13:欲在 AutoCAD
的环境中,查看一变量值,指令:下键入『!变量名』即可规则 14:以(defun C:函式名(自变量/变数) ........)程序中,程序中的变量若在『/』右边变量内,则称为『区域变量』,否则为『整体变量』
五.如何有效的学习 AutoLISP?1.先由小程序着手,认识 AutoLISP语法规定! 2.浏览所有的 AutoLISP功能函数,重要的功能函数要熟记脑海,俗语说的好『一回生,二回熟』,除非您不用心,否则没有学不好的道理!!! 3.要懂得偷懒:不要认为在绘图的过程中,繁琐的步骤是合理的,困难的绘图过程是必须忍耐的,试着用 AutoLISP解决看看! 4.多观摩别人的程序设计,吸取精华,像海棉一样=>『吸』『吸』『吸』、、 !!! 5.动手『写』程序比用眼睛看程序,更能够领略深记脑海! 6.随时随地整理您的程序,并加以批注,以免因时间的飞逝,当时用心的成果也烟消云散,忘的一干二净!!! 7.『决心』是学好 AutoLISP最重要的关键! 8.期许自己,要由操作者变成创造者!!!
单元二:AutoLISP的关键、基本结构及语法一、学好 AutoLISP的关键、基本结构与语法:1. AutoLISP程序语言的特质 A.语法简单 B.功能函数强大 C.撰写的环境不挑剃 D.直译式程序,『即写即测、即测即用』 E.横跨 AutoCAD各作业平台,悠然自得 (注:以上五点,读者可以参考上一章的剖析!!!) 2.学好 AutoLISP的关键:充份掌握『语法结构』&『功能函数』的搭配!!!
第 2页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
二、学好 AutoLISP的关键:充份掌握『语法结构』&『功能函数』的搭配!!!其时这个关键亦是学习其它程序语言的关键. 『语法结构』AutoLISP的语法结构规定的并不多,变量不用事先定义及宣告,读者可熟记下一单元有关重要的 AutoLISP基本语法结构,十四条设计上要求的『规则』『功能函数』AutoLISP之所以能功能如此强大,都有赖功能函数,其成员共约 200个: 1.一般性函数 170个 2. ADS定义特殊函数 9个 3.配合 DCL交谈框设计函数 22个各功能函数在使用上要求配合的运算子(自变量)型态,均有其规定,当然,您可不能乱给!例如:指令:(+ 1 2 3"ABC")传回:error: bad argument type (自变量型态错误)因为『+』函数不接受字符串,而"abc"正是字符串指令:(rtos"abc")传回:error: bad argument type (自变量型态错误)因为『rtos』函数只接受实数转字符串详细内容可参考下一章『快速浏览 AutoLISP功能函数』至于各功能函数详细的语法与实例应用,读者请参阅本书『第三篇 AutoLISP功能函数详解』
指令:(min 75 a 63)响应最小值 50 (因为变量值 a代表 50)错误的范例:指令:(setq a (* 12.5 4) 1>传回 1>表示少了一个括号 1> )此时,只要再补上一个 )即可指令:(setq a (* 12.5 4 2>传回 2>表示少了二个括号 2>
))此时,只要再补上二个 )即可规则 2:表达式型态 (操作数运算子运算子运算子 ...)或 (函数(式)自变量自变量自变量 ...)或 (函数(式)元素元素元素 ...) 1.1操作数包括『功能函数』&『自定函式』功能函数:如上练习中的+、max、menucmd、getint、 setq、*、min,详细内容可参考下一章『快速浏览 AutoLISP功能函数』&『第三篇 AutoLISP功能函数详解』自定函式:由设计者自行定义的新函式或子程序 1.2运算子(又称自变量或元素)包括: A.整数(Integer):如 8,-17,500,9999 正常范围: 2的 16次方,介于-32768与+32767之间特殊范围:若以 float函数将其转为实数,则范围 2的 32次方,介于 -2147483648与+2147483647之间 B.实数(Real):如 8.5,-17.456 正常范围:带有小数点的数,精度可达 14位有效数字 C.字符串(String):如"AutoCAD","123","Enter Real:","7.5", 正常范围:以双引号内夹『字符』为认定,字符数不受限制 D.串行(List):如 ("a""b""c"),(x y),(x y z),("a" 8 3.5),....正常范围:以左右括号内夹『元素』为认定,元素型态非常弹性使用频率:在 AutoLISP程序设计中应用非常高范例说明: ("a" 8 3.5 kk (1 2))表示此串行内有五个元素"a"表示字符串 a、8表示整数 8、3.5表示实数 3.5、 kk表示变量 kk、(1 2)表示串行(1 2) 2D点坐标(x y)表示法=>以二实数形成串行第 3页,共 27页
三、重要的 AutoLISP的基本语法结构:规则 1:以括号组成表达式,左右括号数一定要成双成对、相对称请依序在『指令:』列 (或指令:)后面直接键入以下表达式指令:(+ 1 2 3 4 5)传回加总和 15指令:(max 14.5 8.9 35)传回最大值 35指令:(menucmd"p1=*")显示拉下 POP1指令:(getint"Enter Real:")传回 Enter Real:要求输入一个实数指令:(setq a (* 12.5 4))传回相乘值 50,同时设定给『变量 a』指令:!a回应 50 (注:!号可用来查询变数值)
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
3D点坐标(x y z)表示法=>以三实数形成串行 E.像素名称代码:如<entity name: 6000f262> ...使用范围: AutoCAD会自动赋予像素指向代码,透过此代码可找到像素的数据库记录范例说明: (setq en (entlast))传回<entity name: 60000062> (entget en)可找到像素的数据库串行 F.档案代码:如<file:#12438> 使用范围:开启(open)档案作读档(r)、写档(w)使用时,所产生的代码,如下:范例说明: (setq ffr (open"test.txt""r"))回应<file:#24138> (setq ffw (open"abc.txt""w"))回应<file:#34812> G.选择群集代码:如<Selection set:1>、<Selection set:1> 使用范围:一个或数个像素所形成的选择集范例说明: (setq ss (ssget))选取对象: (可选择物体)选取对象: (可选择物体)选取对象: (按[ENTER]键)回应<Selection set:1>规则 3:表达式中的『运算子』,可以是另一『表达式』或『子程序』功
能函数使用语法: (strcat字符串 1字符串 2字符串 3 ....)字符串结合功能函数 (getstring提示)要求键入一个字符串 (rtos实数)将实数转换成字符串范例说明 1: (strcat"abc""123""LISP")传回:"abc123LISP"范例说明 2: (strcat"abc" (getstring"Enter String:" ) (rtos 123.45))执行结果: Enter String:键入任一字符串,假设是键入 *HELLO*回应"abc*HELLO*123.45"本例中的 strcat函数在语法中要求的『运算子』必须是『字符串』型态『运算子 1』="abc"是正常的字符串运算子
『运算子 2』=表达式 (getstring"Enter String:")传回结果是一字符串"*HELLO*"『运算子 3』=表达式 (rtos 123.45)传回结果是一字符串"123.45"规则 4:多重的括号表达式,运算的先后顺序是『由内而外、由左而右』范例说明:请将 10.25+ 17 - 13.2/ 7的结果,设定给变量 kk,并转换成 AutoLISP的表达式解法技巧 A: 1:运用『二分法、加括号』:(10.25+ 17) - (13.2/ 7) 2:操作数往前提: kk= (- (10.25+ 17) (13.2/ 7)) 3:操作数再往前提:kk= (- (+ 10.25 17) (/ 13.2 7)) 4:转换完成: (setq kk (- (+ 10.25 17) (/ 13.2 7)))解法技巧 B: 1:运用『二分法、加括号』:(10.25+ (17 - (13.2/ 7))) 2:操作数往前提: kk= (+ 10.25 (17 - (13.2/ 7))) 3:操作数再往前提:kk= (+ 10.25 (- 17 (/ 13.2 7))) 4:转换完成: (setq kk (+ 10.25 (- 17 (/ 13.2 7))))规则 5:以档案型态存在的 AutoLISP程序(ASCII档案),其扩展名必须是.LSP规则 6:撰写的环境,只要是一般的文书编辑软件,可编辑 ASCII档案者都适用如:PE2、PE3、DW3、书中仙、汉书、EDIT、记事本....等规则 7:以 defun功能函数定义新的指令或新的功能函式 (注:自变量及区域变量可省略)程序结构型态:(defun函式名称(自变量/区域变量)::::程序内容:: )规则 8:新定义的功能函式名称,若为『C:函式名』,则此函式可为 AutoCAD新指令 (注:自变量及区域变量可省略)程序结构型态: (defun C:KK(自变量/区域变量)::程序内容::第 4页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
:: )则加载此 LISP程序后,可在指令:后直接键入新定义的 KK指令规则 9:加载 AutoLISP程序的作法:指令:后直接键入 (load"LISP主檔名")注:load与字符串间的空格,可有可无注:load与双引号间的空格,可有可无 (load"LISP主檔名")范例:在 c:\lsptools目录下有一 LISP程序 tt.lsp,而您目前的工作目录在 c:\dwg下 若『环境设定』之『支持档案搜寻路径』有指定到 c:\lsptools目录,则
)规则 11:AutoLISP最常用的变量型态是『整数』、『实数』、『字符串』、『点串行』四种,变量的型态依据设定值而自动定义,变量会一直储存该值,直到被重新设定值或绘图结束自动消失规则 12:以 setq功能函数设定变量值 (setq变量名称设定
值)范例: (setq a 100);变量 a值设定成整数 100 (setq b 123.56);变量 b值设定成实数 123.56 (setq c"Good morning!!!");变量 c值设定成字符串 (setq pt1 (getpoint"Enter POINT:"));变量 pt1值设定成点串行 (setq pt2 (list a b));此时,a值是 100,b值是 123.56变量 pt2值设定成点串行(100 123.56) (setq pt3 '(297 210));变量 pt3值设定成点串行 (297 210)注意:直接设定成点串行时,不能省略单引号『'』否则会被误认 (297 210)又是一个表达式, 297是操作数而出错!规则 13:欲在 AutoCAD的环境中,查看一变量值,指令:下键入『!变量名』即可范例:指令:(setq aa (+ 100 75))传回:175指令:!aa传回:175指令:(setq pp (list 90 50))传回:(90 50)指令:!pp传回: (90 50)指令:!ww传回:nil空值无设定规则 14:以(defun C:函式名(自变量/变数) ........)程序中,程序中的变量若在『/』右边变量内,则称为『区域变量』,否则为『整体变量』 (注:在 AutoLISP中,未赋予值的变量,其值皆响应 nil)『区域变量』于此程序执行完毕后,其值自动消失『整体变量』于此程序执行完毕后,其值仍然存在范例: test.lsp内容如下 (defun c:tt(/ sa sb sc) (setq sa 100) (setq sb 20)
欲使用加载 tt.lspa指令:后键入 (load"tt")即可若『环境设定』之『支持档案搜寻路径』无指定到 c:\lsptools目录,则键入 (load"tt")后,会出现错误讯息如下:
无法开启「tt.lsp」做输入错误:载入失败(LOAD"tt")*取消*此时您可键入:指令:(load"c:\\lsptools\\tt")或指令:(load"c:"/lsptools/tt)不可键入: (load"c:\lsptools\tt")因为『\』在 AutoLISP结构语法中已经用于『跳脱码控制』了规则 10:AutoLISP程序中,在『分号;』后的内容均为批注,程序不处理,适时的增加批注,将使程序更具可看性、学习性及完整性范例: pp.lsp内容如下:;本程序功能可快速画门、窗;设计者:QQ博士;版权所有,欢迎使用 (defun c:pp()::;以下为画门子程序::;以下为画窗子程序,::::
第 5页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
(setq sc 10) (setq sd (+ sa sb sc)) )回到:指令:键入(load"tt")传回:c:tt指令:tt传回:130指令:!sa传回:nil (属区域变量)指令:!sb传回:nil (属区域变量)指令:!sc传回:nil (属区域变量)指令:!sd传回:130 (属整体变量)
1.4 1.5 1.6 1.7 1.8 1.9 1.10 1.11
(/数值数值 ...) (1+数值) (1-数值) (abs数值) (atan数值) (cos角度) (exp数值) (expt基数指数) (fix数值) (float数值) (gcd数值 1数值 2) (log数值) (max数值数值 ...) (min数值数值 ...) pi (rem数值 1数值 2) (sin角度) (sqrt数值)
第一个数值除以第二个以后数值的商数值+1数值-1数值的绝对值反正切值角度的余弦值,角度值为弪度数值的指数基数的指数值将数值转换为整数值将数值转换为实数值二数
值的最大公因子数值的自然对数值数值中的最大值数值中的最小值常数 p,其值约为 3.1415926二数值的相除的余数角度的正旋值,角度值为弪度数值的平方根
单元三:快速分类浏览 AutoLISP功能函数(一)一 看到以下那么多的 AutoLISP功能函数,洋洋洒洒 17大类:1.您第一个念头,一定惊讶怎么会那么多,您可能快吓坏了! 2.您第二个念头,一定会想『那么多,怎么记得下来』,您可能快放弃了!二 其实,您应该要『很兴奋』而『充满信心』的,怎么说呢? 1. 2. 3.您有那么多的『大将』协助您撰写 AutoLISP程序,当然左右又逢源,不但轻松,而且要快乐的不得了!!!这些函数只要您先浏览有印象,要用时,再翻查该函数,了解用途语法再加入到您的程序中就可以了!!!常用的函数,写久、用久后,自然会深深牢记脑海,想忘都很难,不常用的函数,若硬要您记下来,相信连高手都很困难,更何况是初学的您!!!您不用再摸不着头绪了,因为您幸运的拥有了本书,就是您成功的开始!!!第一类数学运算功能函数项目 1.1 1.2 1.3函数语法 (+数值数值 ...) (-数值数值 ...) (*数值数值 ...)传累计实数或整数数值减去数值所有数值乘积回
1.12 1.13 1.14 1.15 1.16 1.17 1.18 1.19 1.20 1.21项目 2.1 2.2 2.3 2.4第 6页,共 27页
4.
第二类检验&逻辑运算功能函数函数语法 (=表示式 1表示式 2) (/=表示式 1表示式 2) (<表示式 1表示式 2) (<=表示式 1表示式 2)字符串比较表示式 1是否大于等于表示式 2比较表示式 1是否<小于表示式 2比较表示式 1是否<=小于等于表示式 2传回
比较表示式 1是否等于表示式 2适用数值及
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
2.5 2.6 2.7 2.8 2.9 2.10 2.11
(>表示式 1表示式 2) (>=表示式 1表示式 2) (~数值)
比较表示式 1是否>大于表示式 2比较表示式 1是否大于等于表示式 2传回:数值的位 not值,(1的补码) 4.3 4.4 4.5 4.6 4.7 4.8 4.9 4.10传回 4.11 4.12角度转成的字符串值字符串转成实数值字符串转成整数值 4.13 4.14 4.15 4.16
行) (car串行) (cadr串行) (caddr串行) (cdr串行) (cons新元素串行)串行中的第一个元素通常用来求 x坐标串行中的第二个元素通常用来求 y坐标串行中的第三个元素通常用来求 z坐标除去第一个元素后的串行将新元素结合到串行
(and表示式 1表示式 2 )逻辑 and的结果 (boole函数整数整数 )位式布尔运算 (eq表示式 1表示式 2)比较表示式 1与表示式 2是否相同,适用串行比较(实际相同)
(equal表示式 1表示式 2比较表示式 1与表示式 2是否相同,差量可[差量])省略(内容相同)第三类转换运算功能函数
(foreach名称串行表示将串行的每一元素对应至名称再依表示式执式)行响
应 (length串行) (list元素元素 ) (listp元素)串行内的元素数量将所有元素结合成一串行判断元素是否为一串
项目 3.1 3.2 3.3 3.4 3.5 3.6 3.7 3.8 3.9
函数语法 (angtof字符串[模式]) (angtos角度[模式[精度]]) (atof字符串) (atoi字符串)
角度值的字符串转成实数
(mapcar函数串行 1串将串行 1、串行 2、 等串行的元素配合函行 2 ...)数,求得新串行 (member关键元素串行) (nth n串行) (reverse串行) (subst新项旧项串行)依关键元素(含)以后的串行串行的第 n个元素将串行元素依顺序颠倒过来的串行替换新旧串行后的串行
(cvunit数值原始单位转数值转换单位后的值转换根据 acad.unt换单位)档案 (distof字符串[模式]) (itoa整数) (rtos数值模式[精度]) (trans点原位置新位置[位移])依模式将字符串转成实数值整数转成字符串实数转成字符串转换坐标系统值
第五类字符串、字符、档案处理功能函数项目 5.1 5.2 5.3函数语法 (ascii字符串) (chr整数) (close文件名称) (open文件名模式) (read字符串) (read-char[档案代码])传回
字符串第一个字符的『ASCII』码整数所对应的 ASCII单一字符串关闭档案开启档案代码,准备读取或写入数据串行中的字符串的第一组元素经由键盘或档案中读取单一字符
第四类串行处理功能函数项目 4.1 4.2函数语法 (append串行串行 ...)传回
5.4 5.5 5.6第 7页,共 27页
结合所有串行成一个串行
(assoc关键元素联合串依关键元素找寻联合串行中关系数据
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
5.7 5.8 5.9 5.10 5.11 5.12 5.13 5.14
(read-line[档案代码]) (strcase字符串[字样]) (strcat字符串 1字符串 2 ...) (strlen字符串) (substr字符串起始长度) (wcmatch字符串格式) (write-char数值[档案代码]) (write-line字符串[档案代码])
经由键盘或档案中读取一行字符串转换字符串大小写将各字符串结合成一字符串字符串构成的字符数(即字符串长度)取出子字符串 T或 nil,将字符串与通用字符进行比对将一 ASCII字符写到档案或屏幕
项目 7.1 7.2 7.3 7.4 7.5 7.6
函数语法 (angle点 1点 2) (distance点 1点 2)
传取得二点的角度弪度值取得二点的距离
回
(inters点 1点 2点 3点取得两条线的交点 4[模式]) (osnap点模式字符串) (polar基点弪度距离) (textbox像素串行)依辅助抓点模式取得另一坐标点依极坐标法取得另一坐标点取得文字符串的二对角点坐标
第八类像素处理功能函数项目函数语法 (entdel像素名称)传删除或逆删除像素回
将字符串写到档案或屏幕上
8.1 8.2
第六类等待输入功能函数项目 6.1 6.2 6.3 6.4 6.5 6.6 6.7 6.8 6.9 6.10函数语法 (getangle[基点][提示]) (getcorner基点[提示]) (getdist[基点][
提示]) (getint[提示]) (getkword[提示]) (getorient[基点][提示]) (getpoint[基点][提示]) (getreal[提示]) (getstring[提示]) (initget[位]字符串)传回
(entget像素名称[应用程序取出像素名称的数据串行串行]) (entlast) (entmake像素串行) (entmod像素串行) (entnext[像素名称]) (entsel[提示]) (entupd像素名称) (handent图码) (nentsel[提示]) (nentselp[提示][点])取出图形数据中的最后一个像素建立一个新的像素串行依更新的数据串行更新屏幕上元体找寻图面中的下一个像素请求选取一个像素,响应包含像素名称及选点坐标的串行更新屏幕上复元体图形图码的元体名称 BLOCK所含副元体像素数据串行 BLOCK所含副元体像素数据(以 4 x 4矩形表示)
请求输入十进制角度数值,响应一弪度值提示及参考点可有可无请求输入另一矩框对角点坐标请求输入一段距离请求输入一整数值请求输入『关键词』请求输入十进制角度,响应一弪度值不受 angbase、angdir影响请求输入一个点坐标请求输入一实数请求输入一字符串设定下次 getxxx函数的有效输入
8.3 8.4 8.5 8.6 8.7 8.8 8.9 8.10 8.11
第七类几何运算功能函数
单元四:快速分类浏览 AutoLISP功能函数(二)第 8页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
第九类选择集、符号表处理功能函数项目 9.1 9.2 9.3 9.4 9.5 9.6 9.7 9.8 9.9函数语法 (ssadd[像素名称][选择集]) (ssdel像素名称选择集) (ssget[模式][点 1][点 2]) (ssget"X"[过滤串行]) (sslenth选择集) (ssmemb像素名称选择集)传回
10.6 10.7
(setvar"系统变量"值) (regapp应用类项)
设定该系统变量的值将目前的 AutoCAD图形登记为一个应用程序名称
将像素加入选择集或建立一新选择集将像素自选择集中移出取得一个选择集取得依过滤串行所指定范围的选择集计算选择集的像素个数 11.3响应像素名称是否包含于选择集内 11.4 11.5 11.2项目 11.1
第十一类判断式、循环相关功能函数函数语法 (if<比较式><表示式 1>[表示式 2]) (repeat整数[<表达式><表达式> ...])号) (cond"环境变量") (progn表达式 1表达式 2 ...)传回
检算比较式结果,如果为真,执行<表示式 1>否则,执行<表示式 2>重复执行<整数>次数
(while标题内定档名扩展名旗透过标准 AutoCAD档案对话 DCL交谈框求得档案取得该环境变量的设定值,以字符串表示连结其内的表达式为一组,常用于配合 if、cond等函数
(ssname选择集索引依索引值取出选择集中的像素名称值) (tblnext符号表名称[T])检视符号表,有效的符号表:"LAYER"、"LTYPE"、"VIEW"、"STYLE"、"BLOCK"
第十二类函数处理、定义、追踪&错误处理功能函数项目 12.1 12.2 12.3 12.4 12.5 12.6 12.7 12.8函数语法 (*error*字符串) (alert
字符串) (apply功能函数串行) (defun名称自变量串行表示式 ...) (eval表示式) (exit) (lambda自变量表示式) (progn表达式 1表达式 2 ...)传回
(tblsearch符号表名称在符号表中搜寻符号符号)第十类 AutoCAD相关查询、控制功能函数
程序错误时的警示讯息以交谈框式显示出警告字符串将功能函数与串行结合后执行自定函数或子程序传回:表示式的执行结果强制退出目前的应用程序定义未具名的函数连结其内的表达式为一组,常用于配合 if、cond等函数
项目 10.1 10.2 10.3 10.4 10.5
函数语法
传
回
(command"AutoCAD指令" ...)呼叫执行 AutoCAD指令 (findfile檔名) (getfiled标题内定档名扩展名旗号) (getenv"环境变量") (getvar"系统变量")传回:应该文件名的路径及文件名透过标准 AutoCAD档案对话 DCL交谈框求得档案取得该环境变量的设定值,以字符串表示取得该系统变量的设定值,以字符串表示第 9页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
12.9 12.10
(quit)
强制退出目前的应用程序
13.13 (terpri) 13.14 (textscr) 13.15 (textpage) 13.16 (vports)
在屏幕上显示新列作图环境切换到文字画面清除文字画面文字类似 DOS的 cls指令传回:窗口组态串行第十四类符号、元素、表示式处理功能函数
(tablet代码[列 1列 2列 3方取用或建立对数字板的校调向])对函数设定追踪旗号,辅助除错对函数设定解除追踪旗号
12.11 (trace函数 ) 12.12 (untrace函数 )
第十三类显示、打印控制功能函数项目 13.1 13.2 13.3 13.4 13.5 13.6 13.7 13.8 13.9函数语法 (graphscr) (grclear) (grdraw起点终点颜色[亮显]) (grread[追踪])传回
项目 14.1
函数语法 (atom元素) (atoms-family格式[符号串行]) (boundp表示式) (minusp元素) (not元素) (null元素) (numberp元素) (... '表示式) (quote表示式)
传
回
如果元素不是串行,响应 T,否则为 nil传回:一组已定义函数的符号串行传回:T或 nil,响应表示式是否有值存在传回:T或 nil,元素是否为负值传回:T或 nil,判定元素是否为 nil传回:T或 nil判定元素是否被赋予 nil值传回:T或 nil,元素是否为整数或实数响应表示式未检算前状态响应表示式未检算前状态,同『'』功能将表示式结果设定给带单引号 '符号设定表示式结果给各符号传回:元素的数据型态传回:T或 nil,元素是否为 0值
作图环境切换到图形画面暂时清除模前的屏幕画面
14.2 14.3
暂时性的画出一条线 14.4由输入设备读取追踪值 14.5 14.6暂时性的画出多条线 14.7提供在 AutoLISP中呼叫各菜单将表示式打印于命令区或已开启的档案,句柄字符则以"\"为前缀展开除句柄字符则不以"\"为前缀展开外其余同 prin1除表示式会往下一新行列出,及一空
格外其余同 prin1将讯息显示于屏幕的命令区,并随后响应一个 nil讯息重绘整张图或依像素名称重绘该图形 14.11 14.8 14.9
(grtext位置字符串[亮显])将字符串显示在状态列或屏幕菜单上 (grvecs向量串行[转置矩阵]) (menucmd字符串) (prin1[表示式[档案代码]) (princ[表示式[档案代码])
14.10 (set符号表示式) (setq符号 1表示式 1[符号 2表示式 2]...)
13.10 (print[表示式[档案代码]) 13.11 (prompt讯息) 13.12 (redraw[像素名称[模式]])
14.12 (type元素) 143.13 (zerop元素)项目 15.1 (ads)函数语法
第十五类 ADS、AutoLISP加载与释放函数传回
传回:目前加载 ADS程序串行
第 10页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
15.2 15.3 15.4 15.5 15.6 15.7 15.8 15.9
(ver) (load LSP檔名[加载失败]) (arxload<应用程序名称>[错误响应])
传回:目前 AutoLISP版本字符串载入 AutoLISP档案(*.lsp)加载一个 ARX应用程序文件
17.3
(acad_strlsort串行)
作串行排序
单元五:轻松快速的掌握 AutoLISP设计技巧一、AutoLISP程序设计的四个步骤:1.第一步骤:产生写程序的动机、预期目标 2.第二步骤:构思程序流程、所需之 LISP功能函数、相关变量订定&提示讯息 3.第三步骤:利用文书软件 (如记事本)撰写 xxx.lsp程序 4.第四步骤:回到 AutoCAD下,加载 AutoLISP程序以 (load"LSP主檔名")或 (load"LSP主檔名") 5.第五步骤:执行新的 AutoLISP指令
(arxunload<应用程序名称>[错误响释放 ARX应用程序文件应]) (autoarxload<文件名称><指令定义>)载入一个关连式的 ARX檔
(autoload ADS定义的函数&指令)载入一个关连式的 AutoLISP檔 (autoxload<文件名称><指令定义>) (xload应用程序[出错处理])载入一个关连式的 ADS檔加载 ADS应用程序释放 ADS应用程序
二、透过简单范例全程演练 AutoLISP:1.第一步骤:动机、预期目标如图:希望能在输入『左下角点』、『矩形宽』、『矩形高』后,自动的将图形依所给的条件画出,如此一来,尔后画这个图就轻松愉快了!
15.10 (xunload应用程序[出错处理])
第十六类内存空间管理函数项目 16.1 16.2 16.3 16.4 16.5 16.6 16.7函数语法 (alloc数值) (expand数值) (gc) (mem) (vmon) (xdroom像素名称) (xdsize串行)传回
以节点数值设定区段大小以区段数值配置节点空间强制收回废内存显示目前的内存使用状态释放 ADS应用程序传回像素延伸数据允用得内存空间传回像素延伸数据所占用的内存空间第十七类 ARX定义的函数 2.第二步骤:构思程序相关变量订定(如下图)
项目 17.1 17.2
函数语法
传
回
(acad_colordlg颜色码旗号)显示出标准 AutoCAD颜色选择交谈框 (acad_helpdlg求助文件名主题)显示出标准 AutoCAD求助交谈框第 11页,共 27页
定
出程序名为 pbox.lsp
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
构思程序流程、相关变量:变量名称可自行设定(如 pa、 ww、hh、pb、pc、pd、mp1、mp2、mp3、mp4),掌握三个原则:
十进制角度 0度 90度 180度 270度 N度 0 1/2 2/3
弪度值 0
十进制转弪度公式
不可重复好记不会混淆适时的以分号『;』加上批注
(/ pi 2)或 (* pi 0.5) pi (* pi 1.5) (* pi (/ n 180))
(defun c:pbox();以下 pa、ww、hh值须由使用者输入 (setq pa (请求输入左下角点)) (setq ww (请求输入矩形宽度实数值)) (setq hh (请求输入矩形高度实数值));以下 pb、pc、pd值须由程序依据 pa、ww、hh求出 (setq pb (依据相对极坐标法求出 pb点坐标值)) (setq pc (依据相对极坐标法求出 pc点坐标值)) (setq pd (依据相对极坐标法求出 pd点坐标值));以下依据 pa、pb、pc、pd点画矩形 (以 pline指令画出矩形);以下 mp1、mp2、mp3、mp4值须由程序依据 pa、ww、hh;& pb、pc、pd值求出 (setq mp1 (求出 mp1点坐标值)) (setq mp3 (求出 mp3点坐标值)) (setq mp2 (求出 mp2点坐标值)) (setq mp4 (求出 mp4点坐标值));以下依据 mp1、mp2、mp3、mp4点画出二条线 (以 line指令画出 mp1到 mp3的线) (以 line指令画出 mp2到 mp4的线) ) 本程序所需的 AutoLISP功能函数及其用法
*N/180
(command"AutoCAD指令" ...)<--呼叫执行 AutoCAD指令注意:指令及其副选项皆要用双引号处理假设 pa、pb、pc、pd皆为变量,其值为点坐标正确: (command"pline" pa pb pc pd"c")错误: (command pline pa pb pc pd c)原因:指令 pline及其副选项 c皆没用双引号括住错误: (command"pline" pa pb pc pd c)原因:副选项 c (代表 close)没用双引号括住,会被误认为是 AutoLISP的变量名,但事实又没有 c这个变数错误:(command"pline""pa""pb""pc""pd""c")原因:变数 pa、pb、pc、pd不须用双引号括住注意:副选项中,若使用"",连续二个双引号,代表按[ENTER]键若想画一条 pa到 pc的 LINE&一条 pb到 pd的 LINE正确: (command"line" pa pc"") (command"line" pb pd"")错误: (command"line" pa pc) (command"line" pb pd) 其它相关接近的功能函数... (getdist[基点][提示]) 请求输入一段距离 (getint[提示]) 请求输入一整数值 (getcorner基点[提示]) 请求输入另一矩框对角点坐标 (car串行) 传回:串行中的第一个元素通常用来求 x坐标 (cadr串行) 传回:串行中的第二个元素通常用来求 y坐标 (caddr串行) 传回:串行中的第三个元素通常用来求 z坐标第 12页,共 27页
(getpoint[基点][提示])<--请求输入一个点坐标 (getreal[提示])<--请求输入一实数 (polar基点弪度距离)<--依极坐标法取得另一坐标点其中『弪度值』之转换为:
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
3.第三步骤:利用 PE2、CE或记事
本,撰写 PBOX.LSP程序并储存到 C:\LISPTOOL目录下!!! (defun c:pbox();以下 pa、ww、hh值须由使用者输入 (setq pa (getpoint"Enter Left/Low Point:")) (setq ww (getreal"Width:")) (setq hh (getreal"Height:"));以下 pb、pc、pd值须由程序依据 pa、ww、hh求出 (setq pb (polar pa 0 ww)) (setq pc (polar pb (/ pi 2) hh)) (setq pd (polar pc pi ww));以下依据 pa、pb、pc、pd点画矩形 (command"pline" pa pb pc pd"c");以下 mp1、mp2、mp3、mp4值须由程序依据 pa、ww、hh;& pb、pc、pd值求出 (setq mp1 (polar pa 0 (/ ww 2))) (setq mp2 (polar pb (/ pi 2) (/ hh 2))) (setq mp3 (polar pd 0 (/ ww 2))) (setq mp4 (polar pa (/ pi 2) (/ hh 2)));以下依据 mp1、mp2、mp3、mp4点画出二条线 (command"line" mp1 mp3"") (command"line" mp2 mp4"") ) 4.第四步骤:回到 AutoCAD下,加载 AutoLISP程序若您的 AutoCAD『环境设定』中『支持文件搜寻路径』有加上 c:\lisptool,则您可轻松载入 pbox.lsp程序指令:(load"pbox")传回:c:pbox或指令:(load"pbox")传回:c:pbox或指令:(load"pbox.lsp")传回:c:pbox若您的 AutoCAD『环境设定』中『支持文件搜寻路径』并未加上 c:\lisptool,则您载入 pbox.lsp程序时,须包含程序所在路径:错误的加载:指令:(load"pbox")
会出现:无法开启「pbox.lsp」做输入错误:加载失败 (LOAD"pbox") *取消正确的加载方式:指令:(load"c:/lisptool/pbox")传回:c:pbox或:指令:(load"c:\\lisptool\\pbox")传回:c:pbox 5.第五步骤:执行新的 AutoLISP指令指令:pbox<--成功加载后,直接键入 pbox指令 Enter Left/Low Point:<--请给一左下角点 Width:<--给一实数当宽度,例如 100 Hieght:<--给一实数当高度,例如 50指令:nil指令
三、PBOX.LSP程序产生的问题&改良1.原程序虽是成功的加载执行了,但却有以下几点小问题:问题 1:给完左下角点后,『Width:』及『Height:』提示却在同一行出现,应该一个提示各别一行才好??? ANS:很简单,只要做如下的改变,加入『\n』即可!!! (setq ww (getreal"Width:")) (setq ww (getreal"\nWidth:")) (setq hh (getreal"Height:")) (setq hh (getreal"\nHeight:"))问题 2:希望给宽度及高度时,也能直接在屏幕上拉一段距离代替??? ANS:很简单,只要做以下的函数变动即可!!!将 (setq ww (getreal"\nWidth:"))改成 (setq ww (getdist pa"\nWidth:")) pa为参考基准点将 (setq hh (getreal"\nHeight:"))改成 (setq hh (getdist pa"\nHeight:")) pa为参考基准点问题 3:给完宽度及高度值后,开始画出所要的图形,可是指令操作过程却也跟着在『指令:』下一一配合出现着,不但影响速度,也没有实质的意义,如何改善? ANS:很简单,只要在程序一开始加入如下一行即可改善: (setvar"cmdecho" 0) 设定变量 cmdecho=0关闭指令响应
第 13页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
问题 4:画完所要的图形过
程中,画面出现了小十字点,还得用 redraw指令清除,该如何使其不出现,但又不影响正常绘图设定呢??? (R14环境 blipmode内定值为 0) ANS:很简单,只要在程序一开始加入 (setvar"blipmode" 0)即可有效压抑小十字虚点出现!但须在程序结束前恢复设定 (setvar"blipmode" 1),才不会影响正常绘图设定问题 5:全部过程执行完后,在『指令:』后却出现了空响应 nil,如何消除呢???指令:pbox Enter Left/Low Point: Width: Hieght:指令:nil 就是这一行指令 ANS:很简单,只要在程序结束前,加入一行 (prin1)即可问题 6:程序确认无误后,想将所有变量均处理成『区域变量』,以免占据内存 ANS:很简单,只要做如下的改变即可将 (defun c:pbox()改成 (defun c:pbox(/ pa pb pc pd ww hh mp1 mp2 mp3 mp4)问题 7:希望在 (load"pbox")程序的响应讯息能有更多样的变化 ANS:很简单,原回应是 c:pbox,请在程序结束后,再加入二列: (prompt"**********<< C:PBOX>> **********") (prin1) 2.改良后完整 PBOX.LSP程序的全貌: (defun c:pbox(/ pa pb pc pd ww hh mp1 mp2 mp3 mp4) (setvar"cmdecho" 0) (setvar"blipmode" 0);以下 pa、ww、hh值须由使用者输入 (setq pa (getpoint"Enter Left/Low Point:")) (setq ww (getdist pa"\nWidth:")) (setq hh (getdist pa"\nHeight:"));以下 pb、pc、pd值须由程序依据 pa、ww、hh求出 (setq pb (polar pa 0 ww)) (setq pc (polar pb (/ pi 2) hh))
(setq pd (polar pc pi ww));以下依据 pa、pb、pc、pd点画矩形 (指令"pline" pa pb pc pd"c");以下 mp1、mp2、mp3、mp4值须由程序依据 pa、ww、hh;& pb、pc、pd值求出 (setq mp1 (polar pa 0 (/ ww 2))) (setq mp2 (polar pb (/ pi 2) (/ hh 2))) (setq mp3 (polar pd 0 (/ ww 2))) (setq mp4 (polar pa (/ pi 2) (/ hh 2)));以下依据 mp1、mp2、mp3、mp4点画出二条线 (指令"line" mp1 mp3"") (指令"line" mp2 mp4"") (prin1) ) (prompt"**********<< C:PBOX>> **********") (prin1)
四、本章结语:
经由简单的 PBOX.LSP程序设计全程演练,从『产生动机、预期目标』 『构思程序流程、相关变量订定』 『撰写程序』 『加载程序』 『执行 PBOX指令』 『改良 PBOX.LSP』相信您已能更了解 AutoLISP是怎么回事了,短短的十几行,能做的事却不少,一路循序渐进练习下来,您应该觉得一点儿也不吃力、『游刃有余』才对,果真如此,那恭喜您,『好戏还在后头』,还有体力的话,就继续『征服下一章』吧!!!若您仍觉得有点『迷迷糊糊』,那就休息一下,配合复习第二章『学好 AutoLISP的关键、基本结构与语法』再好好的把第四章『看』&『做』个明白,相信有心成为 AutoCAD高手的您,一定不会那么容易就『被十几行打败』的!!!
单元六:像素数据的取得与活用技巧(一)
第 14页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
一.像素数据串行的重要性: 您可知您
所绘制的每一个 AutoCAD元体 (如 LINE、CIRCLE、ARC、
CIRCLE三点(3P)/二点(2P)/相切,相切,半径(T)/<中心点>: 60,15直径(D)/<半径>: 12.5 在 TXT层写几个字 AutoCAD指令: DTEXT对正(J)/字型(S)/<起点>: (选取文字的位置点)高度<2.5000>: 8旋转角度<0>:0文字: AutoCAD文字: (按[Enter]结束)图示:
TEXT、 BLOCK、 POLYLINE、 DIMENSION...)均有其专属的数据串行!!! 没错以 LIST指令即可查询出来,显示于屏幕上 但是该如何透过 AutoLISP功能去选取、取得、修改、更新数据呢???该
如何去有效活用呢??? 别急就是本单元的学习重点!!! 请注意本章节非常重要,务必要求透彻了解!!!
二、重要像素数据应用相关的功能函数介绍:
(entsel[提示])请求选取一个像素,响应包含像素名称及选点坐标的串行 (car串行)传回:串行中的第一个元素,通常用来求 x坐标 (cadr串行)传回:串行中的第二个元素,通常用来求 y坐标 (caddr串行)传回:串行中的第三个元素,通常用来求 z坐标 (cdr串行)传回:除去第一个元素后的串行 (entlast):取出图形数据中的最后一个像素 (entget像素名称[应用程序串行]):取得像素名称的数据联合串行 (assoc关键元素联合串行):依关键元素找寻联合串行中关系数据 (cons新元素串行)传回:将新元素结合到串行,常用于产生『点对串行』 (subst新项旧项串行)传回:替换新旧串行后的串行 (entmod像素串行)依更新的数据串行更新屏幕上元体 (list元素元素…)传回:将元素结合成一串行
2.在 AutoCAD的 Command:下练习取得像素数据串行 练习函数 entsel、car、cdr、entget指令: (setq en1 (entsel))选取对象: (选取圆)传回一串行: (<像素名称: 2940518> (67.604 24.5166 0.0))其中<像素名称: 2940518><==像素名称 (67.604 24.5166 0.0)<==选点坐标指令: (car en1)传回:<像素名称: 2940518><==串行的第一个元素指令: (cadr en1)传回: (67.604 24.5166 0.0)<==串行的第二个元素指令: (setq en1_data (entget (car en1)))传回『圆的联合数据串行』: ((-1 .<像素名称: 2940518>) (0 ."CIRCLE") (5 ."23") (100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbCircle") (10 60.0 15.0 0.0) (40 . 12.5) (210 0.0 0.0 1.0))其中各子串行的第一个元素均为『群码』,各代表不同对应资料指令: (setq en2 (entsel))
三、像素数据联合串行取得技巧与群码分析:1.基础准备动作:请开一张新图,并建立二个新层 STR、TXT,颜色分别为红色 (red)、绿色 (green)
首先在 STR层画一条线
指令: LINE起点: 15,10下一点: 50,40下一点: (按[Enter]结束)
在 STR层画一个圆
指令: CIRCLE
第 15页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
选取对象: (碰选线)传回一串行: (<像素名称: 29405
00> (30.5626 23.5743 0.0))指令: (setq en2_data (entget (car en2)))传回『线的联合数据串行』: ((-1 .<像素名称: 2940500>) (0 ."LINE") (5 ."20") (100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbLine") (10 15.0 10.0 0.0) (11 50.0 40.0 0.0) (210 0.0 0.0 1.0))指令:(setq en3 (entsel))选取对象: (碰选文字)传回一串行: (<像素名称: 2940520> (45.7833 50.3614 0.0))指令: (setq en3_data (entget (car en3)))传回『文字的联合数据串行』: ((-1 .<像素名称: 2940520>) (0 ."TEXT") (5 ."24") (100 ."AcDbEntity") (67 .0) (8 ."TXT") (100 ."AcDbText") (10 10.0 50.0 0.0) (40 . 8.0) (1 ."AutoCAD") (50 . 0.0) (41 . 1.0) (51 . 0.0) (7 ."STANDARD") (71 . 0) (72 . 0) (11 0.0 0.0 0.0)(210 0.0 0.0 1.0) (100 ."AcDbText") (73 . 0)) 3.联合数据串行中各子串行群码分析说明:您可以在指令:下键入 !en1_data或 !en2_data或 !en3_data分别查看圆、线、文字的联合数据串行,您将会发现=>不同的元体类别,其联合数据串行也不一样圆的联合数据串行 en1_data (-1 .<像素名称: 2940518>) (0 ."CIRCLE") (5 ."23") (100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbCircle") (10 60.0 15.0 0.0)群码-1对应『像素名称』群码 0对应『像素类别』群码 5对应『处理码』群码 100对应『子类别』群码 67对应『模型空间』群码 8对应『图层名称』群码 100对应『子类别』群码 10对应『圆心坐标』
(40 . 12.5) (210 0.0 0.0 1.0)线的联合数据串行 en2_data (-1 .<像素名称: 2940500>) (0 ."LINE") (5 ."20") (100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbLine") (10 15.0 10.0 0.0) (11 50.0 40.0 0.0) (210 0.0 0.0 1.0)文字的联合数据串行 en3_data (-1 .<像素名称: 2940520>) (0 ."TEXT") (5 ."24") (100 ."AcDbEntity") (67 . 0) (8 ."TXT") (100 ."AcDbText") (10 10.0 50.0 0.0) (40 . 8) (1 ."AutoCAD") (50 . 0.0) (41 . 1.0)第 16页,共 27页
群码 40对应『半径值』群码 210对应『像素挤出方向』
群码-1对应『像素名称』群码 0对应『像素类别』群码 5对应『处理码』群码 100对应『子类别』群码 67对应『模型空间』群码 8对应『图层名称』群码 100对应『子类别』群码 10对应『线起始点坐标』群码 11对应『线终止点坐标群码 210对应『像素挤出方向』
群码-1对应『像素名称』群码 0对应『像素类别』群码 5对应『处理码』群码 100对应『子类别』群码 67对应『模型空间』群码 8对应『图层名称』群码 100对应『子类别』群码 10对应『插入点』群码 40对应『字高』群码 1对应『文字内容』群码 50对应『旋转角度』群码 41对应『宽度比例系数』
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
(51 . 0.0) (7 ."STANDARD") (71 . 0) (72 . 0) (11 0.0 0.0 0.0) (210 0.0 0.0 1.0) (100 ."AcDbText") (73 . 0)
群码 51对应『倾斜角』群码 7对应『字型名称』群码 71对应『镜设方
向』群码 72对应『水平对齐设定』群码 11对应『对齐点』群码 210对应『像素挤出方向』群码 100对应『子类别』群码 73对应『水平对齐设定』
((-1 .<像素名称: 2940518>) (0 ."CIRCLE") (5 ."23")(100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbCircle") (10 60.0 15.0 0.0) (40 . 12.5) (210 0.0 0.0 1.0))指令: (setq oldr (assoc 40 en1_data))传回:(40 . 12.5)<==群码 40为索引值的子串行指令:(setq newr (cons 40 23.8))传回:(40 . 23.8)指令:(setq en1_data (subst newr oldr en1_data))回应: ((-1 .<像素名称: 2940518>) (0 ."CIRCLE") (5 ."23")(100 ."AcDbEntity") (67 . 0) (8 ."STR") (100 ."AcDbCircle") (10 60.0 15.0 0.0) (40 . 23.8) (210 0.0 0.0 1.0))数据串行已被修改成功了,但是画面上像素并未更新???指令: (entmod en1_data)<==大功告成,画面上的圆也更新了!!!
4.由以上可看出,元体数据串行有些『群码』是共通的 (如 -1、0、8、210)有些『群码』是因元体而异的(如 10、40),有些『群码』是某些元体特有的(如 en3_data数据串行就比 en1_data& en2_data数据串行来的多)注意 1:往后练习撰写 AutoLISP程序中,若对各元体与群码的对应有疑问或不清楚时,请随时查看『附录 C』有关详细的群码表分析!!!注意 2:子串行中间有一点『 』隔开二元素,我们称为『点对串行』,点对串行要特别注意的是『第二个元素取得,要用 cdr函数』,而非 cadr函数!若要产生新的『点对串行』,可用 cons函数完成.如: (cons 1“ABC”)回应 (1 .“ABC”)
单元七:像素数据的取得与活用技巧(二)五、范例练习:范例一:请撰写一个 CHGRAD.LSP,用来修改圆半径,此程序的执行过程要求如下: 指令: CHGRAD 选取已知圆:碰选画面上已存在的圆 自动显示该旧圆半径值于指令区 新半径:要求输入一半径值 new_rr程序内容解答:
四、像素数据修改与更新技巧:1.像素数据串行修改&更新四步骤:步骤一:用 entget函数取得元体数据串行,如上例中 en1_data、en2_data、 en3_data步骤二:用 assoc函数依『群码值』找寻取得欲修改的旧『子串行』,新的子串行可以用 cons函数去产生步骤三:用 subst函数将数据串行中的新、旧子串行替换步骤四:用 entmod函数更新的数据串行,同时自动更新屏幕上像素 2.在 AutoCAD的『指令:』下做基本像素数据修改&更新练习:请将上例中,圆的半径修改为 23.8过程如下:指令:!en1_data传回:
(defun c:chgrad() (setvar"cmdecho" 0);指令执行过程不响应;;;;以下为 INPUT像素选取 (setq en (entsel"选取已知圆:"));要求碰选一个圆;;;;以下为像素数据&半径数据取得 (setq en_data (entget (car en)));取得元体资料串行 (setq old_rad_list (assoc 40 en_data));取得半径子串行第 17页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
(setq
old_rr (cdr rad_list))
;取得旧有半径
自动的在该线的中点画出一个半径值为 MR的圆
(princ“\n旧半径=”)(princ old_rr);显示该旧圆半径值于指令区;;;;以下为新半径输入&像素数据新旧半径更替 (setq cenpt (cdr (assoc 10 en_data)));一口气取得圆之圆心 (setq new_rr (getdist cenpt"New Radius:"));要求输入一半径值 (setq new_rad_list (cons 40 new_rr));产生新半径子串行 (setq en_data (subst new_rad_list old_rad_list en_data));新旧交替 (entmod en_data);依新像素数据自动更新圆半径 (prin1) ) (prompt"***************<< C:CHGRAD>> *****************") (prin1)程序执行:(请先在画面上任意的画一些圆)指令: (load"chgrad")回应: ***************<< C:CHGRAD>> *****************指令: CHGRAD选取已知圆: (碰选画面上已有的圆)新半径:20 (输入一半径值)
该如何设计 MCIR.LSP呢???解题关键:先取得线的二端点坐标 pt1(px1 py1)& pt2(px2 py2),那二点的中点坐标 mpt(mx my)就用数学几何公式求得 mx= (px1+ px2)/2 my= (py1+ py2)/2程序内容解答: (defun c:mcir() (setvar"cmdecho" 0);指令执行过程不响应 (setq en (entsel"Select a LINE:"));要求碰选一条线 (setq en_data (entget (car en)));取得元体资料串行;********************求得 pt1& px1、py1 ********************* (setq pts (assoc 10 en_data));取得群码 10的子串行 (setq pt1 (cdr pts));取得起点 pt1坐标 (setq px1 (car pt1));取得 pt1坐标的 x值 (setq py1 (cadr pt1));取得 pt1坐标的 y值;********************求得 pt2& px2、py2 *********************** (setq pte (assoc 11 en_data));取得群码 11的子串行 (setq pt2 (cdr pte));取得终点 pt2坐标 (setq px2 (car pt2));取得 pt2坐标的 x值 (setq py2 (cadr pt2));取得 pt2坐标的 y值;*****************求得 mx& my并结合成 mpt **************** (setq mx (/ (+ px1 px2) 2));求得 mx值 (setq my (/ (+ py1 py2) 2));求得 my值 (setq mpt (list mx my));结合 mx& my成 mpt点;******************** Input<mr>& Finish ************************ (setq mr (getdist mpt"Circle Radius:"));要求输入半径值第 18页,共 27页
范例二:请撰写一个 MCIR.LSP,当碰选画面上的 LINE时,会在该线的中点 (Midpoint)产生一个圆,此程序的执行过程要求如下: 指令: MCIR Select a LINE:碰选画面上已有的线
Circle Radius:要求输入一半径值 MR (可给整数、实数或拉一段距离)
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
(command"circle" mpt mr);完成中点画圆 (prin1) ) (prompt"***************<< C:MCIR>> *****************") (prin1)程序执行:(请先在画面上任意的画一些线)指令: (load"mcir")回应: ***************<< C:MCIR>> *****************指令: MCIR Select a LINE: (碰选画面上已有的线) Circle Radius:20 (输入半径 20)
指令: cpoly5 Select CIRCLE:碰选画面上已有的圆 自动产生一个内接正五边形,OK!
该如何
设计 CPOLY5.LSP呢???解题关键: 先取得圆的圆心点坐标 cenpt&半径 rr 模拟 polygon完成内接正五边形的过程:
指令:POLYGON边数<4>: 5注意: 1.变数值查询:您若想进一步查询执行后变量值,没问题!!!请搭配 a惊叹号『!』+『变量名』输入在『指令:』后如!en、!en_data、!pts、!pt1、!px1、!py1、!pte、!pt2、!px2、!py 2、!mx、!my、!mpt、!mr 2.以上程序中所用到的变量,读者皆可自行命名,以方便、好记、不会混淆为原则 3.若不加上最后两行 (prompt"***************<< C:MCIR>> *****************") (prin1)则程序在加载后,将只响应 c:mcir 4.建议读者们养成加入最后两行的习惯,以免未来程序越来越大,加载程序后,根本无从知道该如何执行此 LISP程序,因为程序内可能有好几个 C:XX的指令函数,也可能有很多子程序!!!范例三:请撰写一个 CPOLY5.LSP,碰选 CIRCLE后,自动产生一个圆内接正五边形,此程序的执行过程要求如下:边缘(E)/<多边形的中心点>: (选一点为正多边形中心)内接或外切于圆 (内接(I)/外切(C))<I>:I圆的半径: (给一个半径值)程序内容解答: (defun c:cpoly5() (setvar"cmdecho" 0);指令执行过程不响应 (setq en (entsel"Select CIRCLE:"));要求碰选一个圆 (setq en_data (entget (car en)));取得元体资料串行 (setq cenpt (cdr (assoc 10 en_data)));求得圆心 cenpt (setq rr (cdr (assoc 40 en_data)));求得半径 rr (command"polygon" 5 cenpt"i" rr);完成圆内接正五边形 (prin1) ) (prompt"***************<< C:CPOLY5>> *****************") (prin1)程序执行:(请先在画面上任意的画一些圆)
第 19页,共 27页
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
指令:(load"cpoly5")回应 ***************<< C:CPOLY5>> *****************指令: CPOLY5 Select CIRCLE: (碰选画面上已有的圆) OK!完成一个内接正五边形
该如何设计 CIRSCA.LSP呢???解题关键: 用 entget函数取得圆的元体资料串行 cir_data 用 assoc函数取得群码 40的半径『子串行』rad_list,并以 cdr取
得半径值 old_r,再依此值作放大 2倍或缩小一半新的半径子串行可以用 cons函数结合群码 40&新半径值 用 subst函数将数据串行中的新、旧子串行替换 用 entmod函数依更新的数据串行更新屏幕上圆
程序内容解答: (defun c:cira() (setvar"cmdecho" 0) (setq cir (entsel"Select CIRCLE to<Scale 0.5>:")) (setq cir_data (entget (car cir)));取得元体资料串行 (setq old_rad_list (assoc 40 cir_data));取得原半径子串行 (setq old_r r(cdr rad_list));求得半径 old_r (setq new_rr (* old_rr 0.5));求得新半径 new_r (setq new_rad_list (cons 40 new_rr));产生新半径子串行 (setq cir_data (subst new_rad_list old_rad_list cir_data)) (entmod cir_data) (prin1) ) (defun c:cirb() (setvar"cmdecho" 0) (setq cir (entsel"Select CIRCLE to<Scale 2>:")) (setq cir_data (entget (car cir)));取得
元体资料串行 (setq old_rad_list (assoc 40 cir_data));取得原半径子串行 (setq old_r r(cdr rad_list));求得半径 old_r (setq new_rr (* old_rr 2));求得新半径 new_r (setq new_rad_list (cons 40 new_r));产生新半径子串行 (setq cir_data (subst new_rad_list old_rad_list cir_data)) (entmod cir_data);画面上元体更新 (prin1)第 20页,共 27页
范例四:请撰写一个 CIRSCA.LSP,其内有二个可执行函数: CIRA碰选 CIRCLE后,原 CIRCLE大小自动缩为原来的 1/2 CIRB碰选 CIRCLE后,原 CIRCLE大小自动放大为原来的 2倍
此程序的执行过程要求如下:指令:cira Select CIRCLE to<Scale 0.5>: (碰选画面上已有的圆)自动产生 CIRCLE大小自动缩为原来的 1/2指令:cirb Select CIRCLE to<Scale 2>: (碰选画面上已有的圆)自动产生 CIRCLE大小自动放大为原来的 2倍
非常简明而实用的AutoLISP教程,你信不信,反正我信了(亲,好的话请评价哈)。
) (prompt"*****<< C:CIRA>> *****<< C:CIRB>>********") (prin1)程序执行:(请先在画面上任意的画一些圆)指令:(load"cirsca")回应 *****<< C:CIRA>> *****<< C:CIRB>>********指令: cira Select CIRCLE to<Scale 0.5>: (碰选画面上已有的圆) OK!完成一个缩小为 1/2倍的圆
特殊解法(配合函数 OSNAP& MID对象锁点功能) 而且希望问半径时,能以类似标准 circle指令的半径拖动模式出现?解答:改写范例二的 MCIR.LSP,让程序更精简有力???新程序剩下 15行,省
了 6行 (defun c:mcir1() (setvar"cmdecho" 0) (setq en (entsel"Select a LINE:")) (setq en_data (entget (car en))) (setq pt1 (cdr (assoc 10 en_data)));直接取得第一点 (setq pt2 (cdr (assoc 11 en_data)));直接取得第二点 (setq mx (/ (+ (car pt1) (car pt2)) 2));求得中点 X坐标 (setq my (/ (+ (cadr pt1) (cadr pt2)) 2));求得中点 Y坐标 (setq mpt (list mx my)) (setq mr (getdist mpt"Circle Radius:"));要求输入半径值 (command"circle" mpt mr);完成中点画圆 (prin1) ) (prompt"***************<< C:MCIR1>> *****************") (prin1) 特殊解法(配合函数 OSNAP& MID对象锁点功能)新程序剩下 11行,省了 10行 (defun c:mcir2() (setvar"cmdecho" 0) (setq en (entsel"Select a LINE:")) (setq pts(cadr en));选取时点选坐标 (setq mpt (osnap pts“mid”));直接取得中点 (setq mr (getdist mpt"Circle Radius:"));要求输入半径值 (command"circle" mpt mr);完成中点画圆
指令:cirb Select CIRCLE to<Scale 2>:碰选画面上已有的圆 OK!完成一个放大为 2倍的圆
六、测验练习&解答,举一反三:题目: 改写范例二的 MCIR.LSP,让程序更精简有力??? (原程序有 21行)
(prin1) ) (prompt"***************<< C:MCIR2>> *****************") (prin1)
第 21页,共 27页