找回密码
 立即注册

QQ登录

只需一步,快速开始

扫一扫,访问微社区

查看: 3019|回复: 18

[每日一码] lisp+c#混合编程之--超简单的输入法切换(源码)

[复制链接]

已领礼包: 28个

财富等级: 恭喜发财

发表于 2021-1-27 23:33:53 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
本帖最后由 print1985 于 2022-5-17 10:33 编辑
  1. (vl-load-com);加载VL函数

  2. ;以下为自动加载dll代码,修改为你的AganInp.dll路径(注意路径为双斜杠)
  3. (vl-cmdf "netload" "D:\\Program Files\\Autodesk\\AutoCAD 2014\\Support\\AganInp.dll")

  4. ;反应器,加载lisp后即运行
  5. (vlr-command-reactor nil '((:vlr-commandEnded . GL:changeen)     ;command命令完成后切换为英文
  6.                            (:vlr-commandCancelled . GL:changeen)  ;command命令取消后切换为英文
  7.                            (:vlr-unknownCommand . GL:changeen)    ;command输入未知命令后切换为英文
  8. ))

  9. (defun GL:changeen(a b)
  10. (GC:changeen T) ;C#切换输入法为英文
  11. (princ)
  12. )
  1. using Autodesk.AutoCAD.Runtime;
  2. using Autodesk.AutoCAD.EditorInput;
  3. using Autodesk.AutoCAD.ApplicationServices;
  4. using Autodesk.AutoCAD.DatabaseServices;
  5. using System;
  6. using System.Runtime.InteropServices;

  7. namespace inputting
  8. {
  9.     public class inputting
  10.     {
  11.         [DllImport("user32.dll")]
  12.         public static extern IntPtr FindWindow(string ClassName, string WindowName);//窗口句柄
  13.         [DllImport("user32.dll")]
  14.         public static extern int GetWindowThreadProcessId(IntPtr hwnd, out int ID);//线程
  15.         [DllImport("user32.dll")]
  16.         public static extern int GetKeyboardLayout(int threadid);//键盘布局(输入法)

  17.         //[DllImport("user32.dll")]
  18.         //public static extern void keybd_event(byte bVk, byte bScan, int dwFlags, int dwExtraInfo);//模拟按键用

  19.         [LispFunction("GC:changeen")] //lisp调用函数名字
  20.         public static ResultBuffer qhenus(ResultBuffer rb)
  21.         {
  22.             if (rb == null) return null;
  23.             TypedValue[] values = rb.AsArray();//返回值为数组,相当于lisp里面的表list

  24.             Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
  25.             IntPtr cadhwnd = FindWindow(null, null);//窗口句柄
  26.             int cadID = 0;
  27.             int threadid = 0;
  28.             threadid = GetWindowThreadProcessId(cadhwnd, out cadID);
  29.             int num = GetKeyboardLayout(threadid);//取得一个句柄,描述指定应用程序的键盘布局,经比较中文输入法都小于0
  30.             if (cadhwnd != IntPtr.Zero)
  31.             {
  32.                 if (num < 0)
  33.                 {
  34.                     //API切换输入法为英文
  35.                     System.Windows.Forms.InputLanguage.CurrentInputLanguage =
  36.                     System.Windows.Forms.InputLanguage.FromCulture(System.Globalization.CultureInfo.GetCultureInfo("en-US"));

  37.                     /* 也可用模拟按键切换 ctrl+空格
  38.                     //模拟按下ctrl键
  39.                     keybd_event(0x11, 0, 0, 0);
  40.                     //模拟按下空格键
  41.                     keybd_event(0x20, 0, 0, 0);
  42.                     //模拟松开ctrl键
  43.                     keybd_event(0x11, 0, 2, 0);
  44.                     //模拟松开空格键
  45.                     keybd_event(0x20, 0, 2, 0);
  46.                     ed.WriteMessage("已切换");
  47.                     */
  48.                 }
  49.             }
  50.             else
  51.             {
  52.                 ed.WriteMessage("未找到CAD窗口,输入法自动切换失败");
  53.             }
  54.             return null;
  55.         }
  56.     }
  57. }
自动切换输入法有很多种,我也凑热闹弄了个超简单的输入法切换给大家玩,源码源码
功能:在CAD命令结束时自动切换为英文输入法,妈妈再也不用担心忘记切换输入法了,soeasy!

我的测试环境:win7 64位 CAD2020、CAD2014
个人能力有限,更多功能大家共同开发,谢谢大家!

新版本请移步明经(晓东因为帖子关键词限制--也不提示是哪些关键词的问题,修改了几次也发布不了,只好放弃了)
http://bbs.mjtd.com/thread-183157-1-1.html

评分

参与人数 1D豆 +5 收起 理由
Lisphk + 5 很给力!经验;技术要点;资料分享奖!

查看全部评分

论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

已领礼包: 28个

财富等级: 恭喜发财

 楼主| 发表于 2021-1-30 23:31:53 | 显示全部楼层

谢谢你  给你点个赞
但是你自己也看见了,3行lisp函数,C#用了大几十条代码,还要调试,各种情况还不一定能正常,费力不讨好。
我觉得这个帖子应该让更多学习lisp的人看见,看见lisp和C#各自的长短,减小自己的学习量,编出更好的程序,节省画图时间。
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 0 反对 1

使用道具 举报

已领礼包: 675个

财富等级: 财运亨通

发表于 2021-1-28 08:40:19 | 显示全部楼层
可惜C#有版本限制
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 28个

财富等级: 恭喜发财

 楼主| 发表于 2021-1-28 13:11:42 | 显示全部楼层
能用就行了,又不是不支持,c#能实现更多的功能,为什么不用呢?
纯lisp能实现的功能比较有限,比如动态、对话框、按键等涉及到系统底层的一些东西。
桌子公司不会再为lisp提供更多的支持,如果哪一天像VBA一样就杯具了,现在.NET才是王道。
个人觉得不要有抱残守缺的思想,拿来主义也不一定是错,C#的代码一搜一大把,各种功能花样玩耍。当然C#的入门要难一些,我也还不算完全入门,只能借用C#的一些功能,结合相对简练的lisp实现一些小功能(个人觉得很多功能lisp更简洁一些)。
学C#还有另外的好处,可以非常方便的做出Windows程序甚至手机端的程序,做一些小型专业程序不是事。
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 1094个

财富等级: 财源广进

发表于 2021-1-30 07:43:06 | 显示全部楼层
lisp+c#混合编程。各取所长,给个大赞!
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 1268个

财富等级: 财源广进

发表于 2021-1-30 14:25:21 | 显示全部楼层
直接在 C# 都完成不是更省事?
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 28个

财富等级: 恭喜发财

 楼主| 发表于 2021-1-30 18:57:23 | 显示全部楼层
st788796 发表于 2021-1-30 14:25
直接在 C# 都完成不是更省事?

那你试试看省不省事
一句lisp代码,C#要N多代码才能达到目的
比如(princ " 123")你用C#在命令行打出来你算写出第一个C#程序了
不要看lisp里面反应器的这几条简单代码(1分钟的事),在C#里面也要弄一阵子才行,其中还涉及到开启CAD自动运行、新建文件和打开文件事件的自动加载反应器、卸载反应器等等一系列问题(你能一分钟搞定你是大神),而这些东西在lisp里面都不用考虑。
各取所需,各有特长
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 1268个

财富等级: 财源广进

发表于 2021-1-30 23:14:43 | 显示全部楼层
print1985 发表于 2021-1-30 18:57
那你试试看省不省事
一句lisp代码,C#要N多代码才能达到目的
比如(princ " 123")你用C#在命令行打出来 ...

  1. using Autodesk.AutoCAD.Runtime;
  2. using Autodesk.AutoCAD.ApplicationServices;
  3. using System;
  4. using System.Globalization;
  5. using System.Runtime.InteropServices;
  6. using System.Windows.Forms;
  7. using Autodesk.AutoCAD.DatabaseServices;
  8. using Application = Autodesk.AutoCAD.ApplicationServices.Core.Application;


  9. namespace inputting
  10. {
  11.     public class MyPlus : IExtensionApplication
  12.     {
  13.         [DllImport("user32.dll")]
  14.         public static extern IntPtr FindWindow(string className, string windowName); //窗口句柄

  15.         [DllImport("user32.dll")]
  16.         public static extern int GetWindowThreadProcessId(IntPtr hwnd, out int ID); //线程

  17.         [DllImport("user32")]
  18.         public static extern int LoadKeyboardLayout(string pwszKLID, int flags);

  19.         [DllImport("user32.dll")]
  20.         public static extern uint GetKeyboardLayout(int threadid); //键盘布局(输入法)

  21.         [DllImport("user32")]
  22.         private static extern uint ActivateKeyboardLayout(uint hkl, uint Flags);



  23.         public void Initialize()
  24.         {
  25.             start();
  26.         }

  27.         public void Terminate()
  28.         {

  29.         }

  30.         [LispFunction("qc:changen")]
  31.         public object qhenus(ResultBuffer rb)
  32.         {
  33.             if (rb == null)
  34.             {
  35.                 end();
  36.             }
  37.             else
  38.             {
  39.                 start();
  40.             }
  41.             return true;
  42.         }



  43.         #region MyRegion

  44.         private void start()
  45.         {
  46.             Application.DocumentManager.MdiActiveDocument.CommandWillStart += MdiActiveDocument_CommandWillStart;
  47.             Application.DocumentManager.MdiActiveDocument.CommandCancelled += MdiActiveDocument_CommandWillStart;
  48.             Application.DocumentManager.MdiActiveDocument.CommandEnded += MdiActiveDocument_CommandWillStart;
  49.             Application.DocumentManager.MdiActiveDocument.UnknownCommand += MdiActiveDocument_UnknownCommand; ;

  50.         }

  51.         private void end()
  52.         {
  53.             Application.DocumentManager.MdiActiveDocument.CommandWillStart -= MdiActiveDocument_CommandWillStart;
  54.             Application.DocumentManager.MdiActiveDocument.CommandCancelled -= MdiActiveDocument_CommandWillStart;
  55.             Application.DocumentManager.MdiActiveDocument.CommandEnded -= MdiActiveDocument_CommandWillStart;
  56.             Application.DocumentManager.MdiActiveDocument.UnknownCommand -= MdiActiveDocument_UnknownCommand; ;
  57.         }

  58.         private void MdiActiveDocument_UnknownCommand(object sender, UnknownCommandEventArgs e)
  59.         {
  60.             Qhenus();
  61.         }

  62.         private void MdiActiveDocument_CommandWillStart(object sender, CommandEventArgs e)
  63.         {
  64.             Qhenus();
  65.         }

  66.         private void Qhenus()
  67.         {
  68.             var ed = Application.DocumentManager.MdiActiveDocument.Editor;
  69.             var cadhwnd = FindWindow(null, null); //窗口句柄

  70.             int cadId;
  71.             var threadid = GetWindowThreadProcessId(cadhwnd, out cadId);
  72.             var num = GetKeyboardLayout(threadid);

  73.             LoadKeyboardLayout("00000409", 1);

  74.             ActivateKeyboardLayout(num, 0);

  75.             if (cadhwnd != IntPtr.Zero)
  76.             {
  77.                 var typeOfLanguage = new CultureInfo("en-US");
  78.                 InputLanguage.CurrentInputLanguage = InputLanguage.FromCulture(typeOfLanguage);
  79.             }
  80.             else
  81.             {
  82.                 ed.WriteMessage("未找到CAD窗口,输入法自动切换失败");
  83.             }

  84.         }

  85.         #endregion

  86.     }
  87. }


论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 19个

财富等级: 恭喜发财

发表于 2021-1-30 23:27:44 | 显示全部楼层
print1985 发表于 2021-1-28 13:11
能用就行了,又不是不支持,c#能实现更多的功能,为什么不用呢?
纯lisp能实现的功能比较有限,比如动态、 ...

我认为,什么都没了,AUTOLISP也不会没,LISP是天然和ACAD融合在一起的,综合上看,也是最方便定制的
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 8611个

财富等级: 富甲天下

发表于 2021-1-30 23:34:45 | 显示全部楼层
看惯了alisp的语句,现在看别的语言都觉得复杂,还是lisp+API的方式用着最舒服
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 19个

财富等级: 恭喜发财

发表于 2021-1-30 23:38:12 | 显示全部楼层
liuyj 发表于 2021-1-30 23:34
看惯了alisp的语句,现在看别的语言都觉得复杂,还是lisp+API的方式用着最舒服

对,LISP+API是王道,各干该干的事
C++,C#定制LISP不方便做的事情到函数,
最后都通过LISP去完成和ACAD的交互

点评

是的 lisp干很多事情反而更方便 更省事 C++ C#等 干lisp不能干的就行了 晓东的函数库不正式如此吗,感谢晓东  详情 回复 发表于 2021-1-30 23:49
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 28个

财富等级: 恭喜发财

 楼主| 发表于 2021-1-30 23:40:07 | 显示全部楼层
新建图纸、打开图纸、取消新建等事件没考虑?
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 28个

财富等级: 恭喜发财

 楼主| 发表于 2021-1-30 23:49:25 | 显示全部楼层
Lisphk 发表于 2021-1-30 23:38
对,LISP+API是王道,各干该干的事
C++,C#定制LISP不方便做的事情到函数,
最后都通过LISP去完成和ACAD ...

是的 lisp干很多事情反而更方便 更省事
C++ C#等 干lisp不能干的就行了
晓东的函数库不正式如此吗,感谢晓东
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 12个

财富等级: 恭喜发财

发表于 2021-2-1 12:22:55 | 显示全部楼层
很好用,感谢分享
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

已领礼包: 1310个

财富等级: 财源广进

发表于 2021-4-2 00:08:43 | 显示全部楼层
感谢分享,学习了
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|申请友链|Archiver|手机版|小黑屋|辽公网安备|晓东CAD家园 ( 辽ICP备15016793号 )

GMT+8, 2024-5-4 17:40 , Processed in 0.194266 second(s), 57 queries , Gzip On.

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表