找回密码
 立即注册

QQ登录

只需一步,快速开始

扫一扫,访问微社区

查看: 621|回复: 4

[教学]:如何在程序中使用相对引用你的软件安装目录来调用你的程序?

[复制链接]

已领礼包: 1个

财富等级: 恭喜发财

发表于 2004-6-3 21:26:12 | 显示全部楼层 |阅读模式

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

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

×
我们知道在进行CAD二次开发中LISP语言中,对程序的定位是有很大困难的。现在大部分程序都是通过向CAD支持目录中添加自己的程序目录来实现。而在程序内部调用时均不指定目录,只有文件名,这在块的引用,程序的调入,幻灯片的显示都存在很多问题,当ACAD目录中有与你调用相同的文件时,它可能会调用并不是你想要的文件。
我在使用过程中使用了天正的方法。即在程序安装时将安装目录信息保存在注册表中。而在CAD启动过程中装载程序时将注册表中的目录信息读入目录变量。而在所有对文件的调入、块文件的插入等都在文件名前加入目录信息。这样所有的文件都能顺利载入啦。
实现方法有两种:
第一种:使用其他高级语言编程单独实现。
我用的是VC,思路:
先用GetModuleFileName来获取文件当前目录。
然后再用
RegCreateKeyEx
RegSetValueEx
RegCloseKey

来将其写入注册表中你需要的位置上
[php]
// setdir.cpp : Defines the entry point for the application.
//

#include "stdafx.h"
#include <string.h>

int APIENTRY WinMain(HINSTANCE hInstance,
                     HINSTANCE hPrevInstance,
                     LPSTR     lpCmdLine,
                     int       nCmdShow)
{
        // TODO: Place code here.
        //获取当前目录。
        TCHAR exeFullPath[MAX_PATH];
        long ret0=::GetModuleFileName(NULL,exeFullPath,MAX_PATH);
        if(ret0==ERROR_SUCCESS)
        {MessageBox (NULL, TEXT ("目录太长,无法获取当前目录!"), TEXT ("错误"), 0);
        return 0;
        }
        char *p;
        //分离路径和文件名。
        p = exeFullPath;
        while(strchr(p,'\\')) {
                p = strchr(p,'\\');
                p++;
        }
        *p = '\0';
       
        //创建[蜜蜂软件]主健
        HKEY hOpenedKey;
        LPCTSTR data_Set="Software\\蜜蜂软体\\";
        DWORD dwDisposition;
        //DWORD dwLastError;
        BOOL bRet =::RegCreateKeyEx(HKEY_LOCAL_MACHINE,
                data_Set, //lpszSubKey
                0,
                "RegApp", //(char *) lpszClass,
                REG_OPTION_NON_VOLATILE,
                KEY_ALL_ACCESS,
                NULL,
                &hOpenedKey,
                &dwDisposition
                );
        if(bRet!=ERROR_SUCCESS) //如果无法打开hKEY,则终止程序的执行
        {
                MessageBox (NULL, TEXT ("无法打开有关的hKEY!"), TEXT ("错误"), 0);
                return 0;
        }
   
        long ret2=::RegSetValueEx(
                hOpenedKey,
                "NetBee_Dir",
                NULL,
                REG_SZ,
                (LPBYTE)exeFullPath,
                ret0
                );
       
        if(ret2!=ERROR_SUCCESS)
        {
                MessageBox (NULL, TEXT ("无法修改有关注册表信息!"), TEXT ("错误"), 0);
                return 0;
        }
        ::RegCloseKey( hOpenedKey );
        return 0;
}
[/php]
大家用VC编译后将其放在你的程序目录中,并设置为在安装后自动运行即可。
=================================

第二种:不用编程,而是在inno setup安装制作软件中使用[Registry]段直接进行注册表的添加
[Registry]
Root: HKLM;Subkey: "Software\蜜蜂软体";Flags: createvalueifdoesntexist
Root: HKLM;Subkey: "Software\蜜蜂软体";ValueType: string; ValueName: "NetBee_Dir"; ValueData: "{app}"
………
这里还可添加其他你需要的子项

说明:
目录常量
{app}
用户在安装向导中的选择目标位置页中选定的应用程序目录。
例如: 如果你在项目中指定了 {app}\MYPROG.EXE,用户选择了“C:\MYPROG”作为应用程序目录,安装程序将该文件安装到“C:\MYPROG\MYPROG.EXE”。
----------------------------------------
然后在你的加载菜单程序*.MNL中添加如下语句:

  1. (DEFUN Netbee_load (file)
  2.   (IF (= (LOAD (STRCAT Netbee_Lisp_Dir file) "BAD") "BAD")
  3.     (ALERT (STRCAT "警告:\n文件装载失败:\n" file))
  4.   ) ;_ end of if
  5. ) ;_ end of defun
  6. (setq Netbee_Dir
  7.        (vl-registry-read
  8.          "HKEY_LOCAL_MACHINE\\Software\\蜜蜂软体"
  9.          "Netbee_Dir"
  10.        )
  11. )
  12. (IF (NOT Netbee_Dir)
  13.   (progn(PROMPT "\n [基础绘图系统]装载失败!")
  14.                   (EXIT))
  15.   (Progn
  16.     (setq NetBee_Lisp_Dir (strcat Netbee_Dir "lisp\")
  17.           NetBee_Sys_Dir(strcat Netbee_Dir "Sys\")
  18.           Netbee_Block (STRCAT Netbee_Dir "BLOCK\")
  19.     )
  20.     )
  21. ) ;_ end of if

对于所有的LISP文件调用均用Netbee_load函数
(Netbee_load "netbeelib")
而块的插入均使用Netbee_Block变量加文件名的方式。
这样你的程序在调用中再也不会出错啦。

=============
有些网友对VC不了解,那么下载下面的附件,用VC打开后将其中关于子键及目录名改为你想要的,然后按Release方式编译即可。不要用DEBUG方式编译,不然文件会很大的。
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
发表于 2004-6-5 08:09:30 | 显示全部楼层
呵呵,第一种方法好是好,但我不懂VC,要是采用读INI文件来确定注册表子键名及注册项名就好啦,这样我只要改INI文件里的选项就行啦。
所以,我用第二种方法。

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

使用道具 举报

已领礼包: 593个

财富等级: 财运亨通

发表于 2004-6-5 08:18:32 | 显示全部楼层
既然引用路径,首要条件是你的文件路径在 Support 下,其次自己的菜单加载后,会在当前配置的 Menu 项下生成 Gropx 组,这个里面就包含路径,这样用 Vlisp 完全可以读出来,不用写注册表。菜单加载命令 Menuload 相信菜鸟也很容易学会。
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

发表于 2004-6-5 08:28:47 | 显示全部楼层
最初由 eachy 发布
[B]既然引用路径..... [/B]

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

使用道具 举报

已领礼包: 593个

财富等级: 财运亨通

发表于 2004-6-5 08:55:34 | 显示全部楼层
最初由 beesoft 发布
[B]
哪如何用LISP方法读出当前配置的 Menu 项下生成 Gropx 组呢? [/B]

先取得Menugroup加载的数量,下例是读出其中一个菜单,根据加载菜单的数量做个循环就可以读出全部

  1. (setq acpro (vla-get-activeprofile
  2.               (vla-get-profiles
  3.                 (vla-get-Preferences (vlax-get-acad-object))
  4.               )
  5.             )
  6. )
  7. (vl-registry-read
  8.   (strcat "HKEY_CURRENT_USER\"
  9.           (vlax-product-key)
  10.           "\\Profiles\"
  11.           acpro
  12.           "\\Menus"
  13.   )
  14.   "Group1"  
  15. )
论坛插件加载方法
发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;
如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子标题加上【已解决】;
如何回报帮助你解决问题的坛友,一个好办法就是给对方加【D豆】,加分不会扣除自己的积分,做一个热心并受欢迎的人!
回复 支持 反对

使用道具 举报

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

本版积分规则

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

GMT+8, 2025-9-27 05:30 , Processed in 0.382891 second(s), 40 queries , Gzip On.

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

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