打包:InstallShield,由windows提供, 安裝包開發的製做工具 。html
1.新建工程:File---->New---->Windows Installer----> Installscript MSI Projectredis
2.配置工程:把界面切到 Project Assistant,跟着底部的進度條一步一步完成。shell
(1) Application Information:公司名稱,軟件名稱,版本號,公司網址(必填),更新是否自動通知用戶,圖標windows
(2)Installation Requirement:操做系統和所需的軟件等api
(3) Installation Architecture: 用戶能夠自由選擇安裝某些功能。(可參考下面第三個網址)app
若是爲Yes,在此處設置好之後, 把界面切到 Installation Designer ----> Organization ----> Features 從新修改一遍名稱。async
(4) Application Files : 安裝路徑,默認路徑爲C:\Program Files (x86)\公司名稱\項目名稱,現改成C:\Program Files (x86)\項目名稱ide
(5) Application Shortcuts :快捷方式工具
左側: More Options下Create an uninstallation shortcut:卸載快捷方式。oop
右側勾選按鈕分別爲: a.開始菜單快捷方式。 b. 桌面快捷方式 。c. 替換快捷方式的圖標 。d.
將文件擴展名與快捷方式的目標關聯
而後,把界面切到 Installation Designer ----> System Configuration ---->Shortcuts就能夠看到添加的快捷方式.exe
(6) Application Registry :註冊表寫key和value
(7) Installation Location : 安裝包的語言
而後,把界面切到 Installation Designer ----> Installation Information ----> General Information 能夠看到勾選的語言, 右鍵,選擇Make Default 能夠設置默認語言。
(8) Build Installation:打包安裝盤的設置,固然你也能夠用工具條上的Release Wizard,本身寫腳本。
3.經過工具製做的安裝包也許不能實現全部的要求,接下來就要經過腳原本彌補不足的地方。先回到Installation Designer界面。
(1)軟件許可協議: Behavior and Logic ----> Support Files/Billboards ----> Support Files ----> Language Independent (在此設置後,全部語言都有效),Files部分, 右鍵 Insert Files打開事先寫好的許可協議( txt,rtf 格式)。
(2)安裝腳本:Behavior and Logic ----> Installscript ---->Files ---->Setup.Rul
//////////////////////////////////////////////////////////////////////////////// // // File Name: Setup.rul // // Description: InstallShield script // // Comments: This script was generated based on the selections you made in // the Project Wizard. Refer to the help topic entitled "Modify // the script that the Project Wizard generates" for information // on possible next steps. // //////////////////////////////////////////////////////////////////////////////// // Include header files #include "ifx.h" #include "AppOperate.rul" ////////////////////// string defines //////////////////////////////// #define LICENSE_PATH "License.txt" // 自定義許可文件 #define SRC_BIN_FOLDER "Bin" // 數據源Bin目錄 #define DES_BIN_FOLDER "Bin" // Bin #define SRC_DIST_FOLDER "Dist" // 數據源Dist目錄 #define DES_DIST_FOLDER "dist" // dist #define DES_PRJ_FOLDER "Project" // Project #define DES_MENU_FOLDER "Menu" // Menu #define LANUCH_FOLDER "dist" // dist #define LANUCH_INI "config.ini" // 程序啓動配置文件 #define LANUCH_APPNAME "LiveUpdate.exe" // 應用程序啓動名稱 #define PRODOUCT_NAME "XX客戶端" // 應用軟件名稱 #define PROFILES_NAME "HHWYGISELECDATAEDIT" // AutoCAD配置模板名稱 #define REGISTER_DLLDIR "Bin\\Arx\\reg.bat" // 主要註冊的dll路徑 #define VC_REDIST_DIR "Support\\Drivers\\vcredist" // 運行時的分發包目錄 //#define ACCESSDRIVER_X64_DIR "Support\\Drivers\\AceRedist.msi" // 運行時的分發包目錄 #define VC_REDIST_11 "{1D8E6291-B0D5-35EC-8441-6616F567A0F7}" // VC11.0運行時 //#define VCREDIST_x86_2005 "vcredist_x86_2005.exe" // vc //#define VCREDIST_x64_2005 "vcredist_x64_2005.exe" // vc //#define VCREDIST_x86_2008 "vcredist_x86_2008.exe" // vc //#define VCREDIST_x64_2008 "vcredist_x64_2008.exe" // vc //#define VCREDIST_x86_2010 "vcredist_x86_2010.exe" // vc //#define VCREDIST_x64_2010 "vcredist_x64_2010.exe" // vc #define VCREDIST_x86_2016 "vcredist_x86_2016.exe" // vc #define VCREDIST_x64_2016 "vcredist_x64_2016.exe" // vc //////////////////// installation declarations /////////////////// // ----- DLL function prototypes ----- // your DLL function prototypes // ---- script function prototypes ----- // your script function prototypes prototype BOOL InitVcredist(STRING); prototype BOOL InitCADVerInfo(); prototype string GetUpperDir(string); prototype BOOL IsInstallCADVersion(STRING,STRING,STRING); // OutVer.InVer.CurVer prototype BOOL GetCADVerInfo(STRING, BYREF STRING, BYREF STRING,BYREF STRING,BYREF STRING); // OutVer.InVer.CurVer prototype BOOL SearchRoamableRootFolder(STRING, STRING,BYREF STRING); // InVer.CurVer.RoamableRootFolder prototype BOOL InitSelectVerionInstallPara(STRING); // OutVer prototype BOOL SearchCADPath(STRING,STRING,BYREF STRING,BYREF STRING); //InVer.CurVer.ACADPath.ACADSearchPath prototype BOOL CreateUninstShortCut(); //uninstll shortCut prototype BOOL LaunchAppAcad(); //Start App prototype ModifyFileData(STRING,STRING ,STRING ); prototype RecursionModifyFileData(OBJECT,STRING ,STRING ); prototype BOOL WriteReg(); prototype BOOL InstallDogDirver(); prototype BOOL SetupFolders(); prototype BOOL CopyVersionFiles(); prototype BOOL RegisterDll(); prototype BOOL SetCompatModel(STRING,STRING); //Set App 兼容模式 prototype BOOL UninstallFiles(); prototype BOOL WindowsUnstallInfo(STRING); //卸載信息 prototype BOOL InstallSoftSilent(STRING,STRING); //靜默式安裝某個程序 //Use to Uninstall OldVersion prototype BOOL UninstallOldVersion(STRING); prototype BOOL CheckOldVersion(STRING,BYREF STRING); // your global variables typedef CADVERSIONINFO //Define CAD Version Info begin LIST listOutVerID; //CAD Outside Verion Name AutoCAD 2007 LIST listInVerID; //CAD Inside Verion Name R17.0 LIST listCurVerID; //CAD Current Version Name ACAD-201:804 LIST listCustomID; //CAD Custom Version name 2009 LIST listShortID; //CAD Short Version name 09 end; STRING g_ACADPath; STRING g_ACADSearchPath; STRING g_szRoamableRootFolder; BOOL g_bLANUCHAPP; STRING g_szCurVcredist; //當前系統和CAD對應的 vcredist STRING g_szSelOutVersion; //用戶選擇的外部版本,例如 AutoCAD 2007,做爲檢索標示 STRING g_szInVersion; //全局內部版本代號 例如 R17.0 STRING g_szCurVersion; //全局當前版本代號 例如 ACAD-201:804 STRING g_szCustomID; //全局小版本代號 例如 2009 STRING g_szShortID; //全局短版本號 例如 09 CADVERSIONINFO g_CADVerInfo; //CAD Base Version info //------------------------------------------- ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: CADVerCheckDialog // EVENT: Check Mem CAD Verion Info In order to privide User to Select // Author: /////////////////////////////////////////////////////////////////////////////// #define RES_DIALOG_ID 13333 // ID of dialog itself #define RES_VERSIONLIST_ID 1303 // ID of VersionList #define RES_PBUT_NEXT 1 // ID of Next button #define RES_PBUT_CANCEL 9 // ID of Cancel button #define RES_PBUT_BACK 12 // ID of Back button prototype CADVerCheckDialog(STRING, STRING); function CADVerCheckDialog(szTitle, szMsg) STRING szDlg, szDialogName, szDLLName, szDialog; STRING szTempOutVer,szTempInVer,szTempCurVer,szTempCustom; STRING szTemp,szTemp2; number nId, nSdDialog, hInstance, hwndParent, nResult; HWND hwndDlg; LIST listVerID,listSupportVerID; BOOL bDone; INT iCount,i; begin // Specify a name to identify the custom dialog in this installation. szDlg = "NewDialog"; nSdDialog = RES_DIALOG_ID; g_szSelOutVersion=""; // record data produced by this dialog if( MODE = SILENTMODE ) then return nId; endif; // ensure general initialization is complete if( !bSdInit ) then SdInit(); endif; szDialogName = "NewDialog"; hInstance = 0; szDLLName = ""; szDialog = ""; hwndParent = 0; nResult = DefineDialog (szDialogName, hInstance, szDLLName, nSdDialog, szDialog, hwndParent, HWND_INSTALL, DLG_MSG_STANDARD|DLG_CENTERED); listVerID = ListCreate (STRINGLIST); listSupportVerID = ListCreate(STRINGLIST); if ( nResult = DLG_ERR) then bDone = TRUE; return -1; endif; //Initialize CAD Install Version iCount = ListCount(g_CADVerInfo.listOutVerID); if( iCount<=0 ) then bDone =TRUE; return -1; endif; // Initialize CAD Install Verion in the for loop. for i = 0 to (iCount-1) ListSetIndex(g_CADVerInfo.listOutVerID,i); ListSetIndex(g_CADVerInfo.listInVerID,i); ListSetIndex(g_CADVerInfo.listCurVerID,i); ListSetIndex(g_CADVerInfo.listCustomID,i); ListCurrentString (g_CADVerInfo.listOutVerID,szTempOutVer); ListCurrentString (g_CADVerInfo.listInVerID,szTempInVer); ListCurrentString (g_CADVerInfo.listCurVerID,szTempCurVer); ListCurrentString (g_CADVerInfo.listCustomID,szTempCustom); //檢查安裝盤版本 szTemp = SRCDIR^SRC_BIN_FOLDER^DES_BIN_FOLDER+szTempCustom; if (ExistsDir (szTemp) = EXISTS) then ListAddString(listSupportVerID,szTempOutVer,AFTER); if(IsInstallCADVersion(szTempOutVer,szTempInVer,szTempCurVer)) then ListAddString(listVerID,szTempOutVer,AFTER); endif; endif; endfor; //Get CAD Install Check Count if <=0 return iCount = ListCount(listVerID); if(iCount<=0) then iCount = ListCount(listSupportVerID); szTemp = "\n"; if(iCount>0) then for i = 0 to (iCount-1) ListSetIndex(listSupportVerID,i); ListCurrentString (listSupportVerID,szTemp2); szTemp = szTemp + "\n"+szTemp2; endfor; MessageBox ("當前軟件支持安裝"+szTemp+"版本,\n請選擇安裝一個版本後,再執行軟件安裝操做!", SEVERE); else //嚴重問題發生 MessageBox ("軟件安裝信息缺失,請儘快聯繫軟件提供商!", SEVERE); endif; //MessageBox ("請檢查系統是否已經安裝AutoCAD 2007 以上版本,\n而後再執行軟件安裝操做!", SEVERE); bDone = TRUE; return -1; else endif; // Initialize the indicator used to control the while loop. bDone = FALSE; // Loop until done. while (!bDone) // Display the dialog and return the next dialog event. nId = WaitOnDialog( szDlg ); // Respond to the event. . switch(nId) case DLG_INIT: nResult = CtrlSetList (szDialogName, RES_VERSIONLIST_ID,listVerID); case RES_PBUT_NEXT: // The user clicked the Next button. bDone = TRUE; case RES_PBUT_BACK: // The user clicked the Back button. bDone = TRUE; case RES_PBUT_CANCEL: // The user clicked the Cancel button. Do (EXIT); case DLG_CLOSE: SdCloseDlg( hwndDlg, nId, bDone ); endswitch; endwhile; if(bDone) then nResult = CtrlGetCurSel (szDialogName, RES_VERSIONLIST_ID, szTempCurVer); if(nResult=0) then g_szSelOutVersion = szTempCurVer; endif; endif; // Cleanup Dialog EndDialog( szDlg ); ReleaseDialog( szDlg ); SdUnInit(); // record data produced by this dialog if( MODE = RECORDMODE ) then endif; return nId; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: OnFirstUIBefore // // EVENT: FirstUIBefore event is sent when installation is run for the first // time on given machine. In the handler installation usually displays // UI allowing end user to specify installation parameters. After this // function returns, FeatureTransferData is called to perform file // transfer. // /////////////////////////////////////////////////////////////////////////////// function OnFirstUIBefore() number nResult,nSetupType; STRING szTitle,szMsg,szDir,szPicName; begin SHELL_OBJECT_FOLDER = @PRODUCT_NAME; szDir = INSTALLDIR; //檢查早期的2009版本之前的安裝包信息 //UninstallOldVersion("{9D23756A-FF9F-4AB9-85E5-4C1D22D7D53E}"); Dlg_Start: Dlg_SdWelcome: //設置對話框左邊的圖形: SdInit(); szPicName = SUPPORTDIR^"LeftView.BMP"; DialogSetInfo(DLG_INFO_ALTIMAGE,szPicName,TRUE); szTitle = ""; szMsg = ""; nResult = SdWelcome( szTitle, szMsg ); if (nResult = BACK) goto Dlg_Start; Dlg_License2: //設置對話框左邊的圖形: SdInit(); szPicName = SUPPORTDIR^"LeftView.BMP"; DialogSetInfo(DLG_INFO_ALTIMAGE,szPicName,TRUE); // Display the SdLicense2 dialog. szTitle = ""; szMsg = ""; if (SdLicense2 (szTitle, "", "", LICENSE_PATH, FALSE) = BACK) goto Dlg_SdWelcome; Dlg_CADVerCheckDialog: szTitle = ""; szMsg = ""; nResult = CADVerCheckDialog( szTitle, szMsg ); if (nResult = BACK) goto Dlg_License2; if(nResult = -1)then abort; endif; Dlg_SdAskDestPath: //設置對話框上面的圖形: SdInit(); szPicName = SUPPORTDIR^"LeftView.BMP"; DialogSetInfo(DLG_INFO_ALTIMAGE,szPicName,TRUE); szTitle = ""; szMsg = ""; nResult = SdAskDestPath( szTitle, szMsg, szDir, 0 ); if (nResult = BACK) goto Dlg_License2; //檢測路徑是否合法 if (Is(VALID_PATH,szDir) == FALSE) then MessageBox("請檢查路徑是否合法!",INFORMATION); goto Dlg_SdAskDestPath; endif; if (SYSINFO.bIsWow64) then szMsg = GetUpperDir(szDir); if (szMsg == PROGRAMFILES64 || szDir == PROGRAMFILES64) then MessageBox("非64位軟件不能安裝到此路徑,請從新選擇.",INFORMATION); goto Dlg_SdAskDestPath; endif; endif; INSTALLDIR = szDir; Enable(STATUSEX); //初始化安裝版本安裝環境,路徑、版本信息等 if(!InitSelectVerionInstallPara(g_szSelOutVersion)) then abort; endif; return 0; end; //--------------------------------------------------------------------------- // // GetUpperDir(STRING) // 獲取當前目錄的上一級目錄 // 如 srcDir : C:\Program Files\TestDir // 返回 C:\Program Files\ //--------------------------------------------------------------------------- function string GetUpperDir(srcDir) NUMBER upperstrlen; string returnDir,tempDir; begin returnDir = ""; tempDir = srcDir; while (StrFind(tempDir,"\\")>-1) StrSub(tempDir,tempDir,StrFind(tempDir,"\\")+1,StrLength(tempDir)-StrFind(tempDir,"\\")); endwhile; upperstrlen = StrLength(tempDir); StrSub(returnDir,srcDir,0,StrLength(srcDir)-upperstrlen-1); returnDir = returnDir + "\\"; return returnDir; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: InitCADVerInfo() // // EVENT: 初始化CAD的基礎版本信息數據 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL InitCADVerInfo() begin g_CADVerInfo.listOutVerID = ListCreate (STRINGLIST); //CAD Outside Verion Name AutoCAD 2007 g_CADVerInfo.listInVerID = ListCreate (STRINGLIST); //CAD Inside Verion Name R17.0 g_CADVerInfo.listCurVerID = ListCreate (STRINGLIST); //CAD Curtent Verion Name ACAD-201:804 g_CADVerInfo.listCustomID = ListCreate (STRINGLIST); //CAD Custom Version name 2009 g_CADVerInfo.listShortID = ListCreate (STRINGLIST); //CAD Short Version name 09 if (SYSINFO.bIsWow64) then /* //!AutoCAD 2009x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2009", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R17.2", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-7001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2009-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "09", AFTER); //!AutoCAD 2010x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2010", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.0", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-8001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2010-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "10", AFTER); //!AutoCAD 2011x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2011", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-9001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2011-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "11", AFTER); //!AutoCAD 2012x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2012", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.2", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-A001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2012-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "12", AFTER); //!AutoCAD 2013x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2013", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R19.0", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-B001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2013-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "13", AFTER); //!AutoCAD 2014x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2014", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R19.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-D001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2014-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "14", AFTER); */ //!AutoCAD MAP 3D 2016x64 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD Map 3D 2016", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R20.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-F002:409", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2016-x64", AFTER); ListAddString (g_CADVerInfo.listShortID, "16", AFTER); /* else //!AutoCAD 2007 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2007", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R17.0", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-5001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2007", AFTER); ListAddString (g_CADVerInfo.listShortID, "07", AFTER); //!AutoCAD 2008 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2008", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R17.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-6001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2008", AFTER); ListAddString (g_CADVerInfo.listShortID, "08", AFTER); //!AutoCAD 2009 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2009", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R17.2", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-7001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2009", AFTER); ListAddString (g_CADVerInfo.listShortID, "09", AFTER); //!AutoCAD 2010 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2010", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.0", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-8001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2010", AFTER); ListAddString (g_CADVerInfo.listShortID, "10", AFTER); //!AutoCAD 2011 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2011", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-9001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2011", AFTER); ListAddString (g_CADVerInfo.listShortID, "11", AFTER); //!AutoCAD 2012 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2012", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R18.2", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-A001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2012", AFTER); ListAddString (g_CADVerInfo.listShortID, "12", AFTER); //!AutoCAD 2013 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2013", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R19.0", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-B001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2013", AFTER); ListAddString (g_CADVerInfo.listShortID, "13", AFTER); //!AutoCAD 2014 ListAddString (g_CADVerInfo.listOutVerID, "AutoCAD 2014", AFTER); ListAddString (g_CADVerInfo.listInVerID , "R19.1", AFTER); ListAddString (g_CADVerInfo.listCurVerID, "ACAD-D001:804", AFTER); ListAddString (g_CADVerInfo.listCustomID, "2014", AFTER); ListAddString (g_CADVerInfo.listShortID, "14", AFTER); */ endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: InitCADVerInfo // // EVENT: 是否已經包含CAD指定版本註冊信息 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL IsInstallCADVersion( szOutVer, szInVer, szCurVer) STRING szKey,szNumName,szNumValue; //szKey表示鍵,szNumName表示字符,svNumValue表示數值 number nvType,nvSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; if(RegDBSetDefaultRoot(HKEY_LOCAL_MACHINE) <0) then return FALSE; endif; nvType = REGDB_STRING; szKey = "SOFTWARE\\Autodesk\\AutoCAD\\"+szInVer+"\\"+szCurVer; szNumName ="AcadLocation"; if (RegDBKeyExist (szKey) < 0) then return FALSE; else if (RegDBGetKeyValueEx (szKey, szNumName, nvType, szNumValue, nvSize) < 0) then return FALSE; endif; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: CreateUninstShortCut() // // EVENT: 建立刪除快捷方式 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL CreateUninstShortCut() string szmsg1,szmsg2,szfilename; INT nresult; begin //建立刪除快捷方式 /UNINSTALL szfilename = UNINSTALL_STRING +" /removeonly"; nresult = StrFind(szfilename,".exe"); if nresult >=0 then StrSub(szmsg1,szfilename,0,nresult + 4); StrSub(szmsg2,szfilename,nresult + 4,200); LongPathToQuote(szmsg1, FALSE ); LongPathToQuote(szmsg2, FALSE ); szfilename = "\"" + szmsg1 + "\"" +szmsg2; endif; if(AddFolderIcon(FOLDER_PROGRAMS^PRODOUCT_NAME,"卸載"+PRODOUCT_NAME,szfilename,WINDIR,"",0,"",REPLACE)!=0) then return FALSE; endif; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: LaunchAppAcad() // // EVENT: 啓動應用程序 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL LaunchAppAcad() string AppTarget,szDocFile; begin AppTarget=TARGETDIR^LANUCH_FOLDER; if(FindFile(AppTarget, LANUCH_APPNAME, szDocFile)=0) then if (LaunchApp (AppTarget^LANUCH_APPNAME, "") < 0) then //MessageBox ("Unable to launch "+serviceTarget+".", SEVERE); endif; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: GetCADVerInfo(szOutVer, szInVer, szCurVer,szCustomID,szShortID) // 【IN】szOutVer 【out】 szInVer 【out】szCurVer // EVENT: 獲得CAD版本信息配置數據 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL GetCADVerInfo(szOutVer, szInVer, szCurVer,szCustomID,szShortID) STRING szTempOutVer,szTempInVer,szTempCurVer,szTempCustomID,szTempShortID; INT iCount,i; BOOL bRet; begin szInVer = ""; szCurVer =""; bRet = FALSE; iCount = ListCount(g_CADVerInfo.listOutVerID); if(iCount<=0) then return FALSE; endif; for i=0 to (iCount-1) ListSetIndex(g_CADVerInfo.listOutVerID,i); ListSetIndex(g_CADVerInfo.listInVerID,i); ListSetIndex(g_CADVerInfo.listCurVerID,i); ListSetIndex(g_CADVerInfo.listCustomID,i); ListSetIndex(g_CADVerInfo.listShortID,i); ListCurrentString (g_CADVerInfo.listOutVerID,szTempOutVer); ListCurrentString (g_CADVerInfo.listInVerID,szTempInVer); ListCurrentString (g_CADVerInfo.listCurVerID,szTempCurVer); ListCurrentString (g_CADVerInfo.listCustomID,szTempCustomID); ListCurrentString (g_CADVerInfo.listShortID,szTempShortID); if( StrCompare (szOutVer, szTempOutVer) = 0) then szInVer = szTempInVer; szCurVer= szTempCurVer; szCustomID = szTempCustomID; szShortID = szTempShortID; return TRUE; endif; endfor; return FALSE; end; // 初始化vcredist到 g_szCurVcredist function BOOL InitVcredist(szOutVer) begin /* if(szOutVer == "AutoCAD 2007" || szOutVer == "AutoCAD 2008") then g_szCurVcredist = VCREDIST_x86_2005; endif; if(szOutVer == "AutoCAD 2009") then if(!SYSINFO.bIsWow64) then g_szCurVcredist = VCREDIST_x86_2005; else g_szCurVcredist = VCREDIST_x64_2005; endif; endif; if(szOutVer == "AutoCAD 2010" || szOutVer == "AutoCAD 2011") then if(!SYSINFO.bIsWow64) then g_szCurVcredist = VCREDIST_x86_2008; else g_szCurVcredist = VCREDIST_x64_2008; endif; endif; if(szOutVer == "AutoCAD 2012") then if(!SYSINFO.bIsWow64) then g_szCurVcredist = VCREDIST_x86_2010; else g_szCurVcredist = VCREDIST_x64_2010; endif; endif; */ if(szOutVer == "AutoCAD Map 3D 2016") then if(!SYSINFO.bIsWow64) then g_szCurVcredist = VCREDIST_x86_2016; else g_szCurVcredist = VCREDIST_x64_2016; endif; endif; if (g_szCurVcredist == "") then return FALSE; else return TRUE; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: InitSelectVerionInstallPara(STRING) // 【IN】szOutVer // EVENT: 初始化用戶選擇CAD版本安裝變量 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL InitSelectVerionInstallPara(szOutVer) begin //Convert OutVersion to InVersion,Current Verion if(!GetCADVerInfo(szOutVer,g_szInVersion,g_szCurVersion,g_szCustomID,g_szShortID)) then return FALSE; endif; //get search path if(!SearchCADPath(g_szInVersion,g_szCurVersion,g_ACADPath, g_ACADSearchPath)) then return FALSE; endif; //get Roamable path if(!SearchRoamableRootFolder(g_szInVersion,g_szCurVersion,g_szRoamableRootFolder)) then return FALSE; endif; //初始化vcredist if(!InitVcredist(szOutVer)) then return FALSE; endif; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: SearchCADPath // 【IN】szInVersion,【IN】szCurVersion,【out】szACADPath,【out】szACADSearchPath // EVENT: 查找CAD路徑 // ////////////////////////////////////////////////////////////////////////////// function BOOL SearchCADPath(szInVersion,szCurVersion,szACADPath,szACADSearchPath) string szKey,szNumName,svNumValue; //szKey表示鍵,szNumName表示字符,svNumValue表示數值 int nns; number nvType ,nvSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; if (RegDBSetDefaultRoot(HKEY_LOCAL_MACHINE)<0) then return FALSE; endif; nvType = REGDB_STRING; szKey = "Software\\Autodesk\\AutoCAD\\"+szInVersion+"\\"+szCurVersion; szNumName ="AcadLocation"; if (RegDBKeyExist (szKey) < 0) then return FALSE; else if (RegDBGetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then return FALSE; endif; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; szACADPath = svNumValue; szACADSearchPath = svNumValue; return TRUE; end; function RecursionModifyFileData( objNode, szOldStr,szNewStr ) STRING szValue; NUMBER nCount,i,nRet; OBJECT ObjList,subNode; begin if (IsObject(objNode)) then //修改自身屬性 set ObjList = objNode.Attributes; nCount = ObjList.length(); for i = 0 to nCount step 1 set subNode = ObjList(i); if (IsObject(subNode)) then szValue = subNode.Text; nRet = StrReplace(szValue, szOldStr, szNewStr, 0); if (nRet > ISERR_SUCCESS) then subNode.Text = szValue; endif; endif; endfor; //修改子項 if (objNode.hasChildNodes()) then set ObjList = objNode.childNodes; nCount = ObjList.length(); for i = 0 to nCount step 1 set subNode = ObjList(i); RecursionModifyFileData(subNode, szOldStr, szNewStr); endfor; endif; endif; end; function ModifyFileData(szFileName,szOldStr,szNewStr) STRING szFilePath; NUMBER nRet; OBJECT objXml,objNode; begin szFilePath = szFileName; nRet = Is(FILE_EXISTS, szFilePath); if (nRet = TRUE) then set objXml = CreateObject("MSXML.DOMDocument");//建立一個DOM對象 if (IsObject(objXml)) then objXml.async = FALSE; objXml.Load(szFilePath); set objNode = objXml.documentElement; RecursionModifyFileData(objNode, szOldStr, szNewStr); objXml.save(szFilePath); //保存 endif; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: SearchRoamableRootFolder(STRING, STRING,BYREF STRING) // 【IN】szInVer,【IN】szCurVer,【out】szRoamableRootFolder // EVENT: 獲得CAD版本的根路徑 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL SearchRoamableRootFolder(szInVer, szCurVer,szRoamableRootFolder) STRING szKey,szNumName,szNumValue; //szKey表示鍵,szNumName表示字符,svNumValue表示數值 number nvType ,nvSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; RegDBSetDefaultRoot(HKEY_CURRENT_USER); szKey = "Software\\Autodesk\\AutoCAD\\"+szInVer+"\\"+szCurVer; szNumName ="RoamableRootFolder"; if(RegDBGetKeyValueEx (szKey, szNumName, nvType, szNumValue, nvSize) < 0) then return FALSE; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; szRoamableRootFolder = szNumValue; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: SetupFolders() // // EVENT: 在桌面和程序組建立快捷方式 // /////////////////////////////////////////////////////////////////////////////// function BOOL SetupFolders() NUMBER nResult; STRING szFolderDir,svResult,szProgramFolder,szProgram,szCommandLine,szWorkingDir,szIconPath,szShortCutKey; INT nIcon,nFlag; begin Disable(LOGGING); Enable(LOGGING); szProgramFolder = FOLDER_PROGRAMS^SHELL_OBJECT_FOLDER;//創建程序組或快捷方式的位置 szProgram = INSTALLDIR^"\\dist\\LiveUpdate.exe"; //可執行文件名 //g_szParam = "/p HHWY10KV3 /nologo"; LongPathToQuote (szProgram, TRUE);//合併路徑 szCommandLine = szProgram; //生成命令行 szWorkingDir = INSTALLDIR^"\\dist";//工做路徑 szIconPath = INSTALLDIR^"\\Support\\setup.ico"; nIcon = 0; szShortCutKey = ""; nFlag = REPLACE; AddFolderIcon (szProgramFolder, PRODOUCT_NAME, szCommandLine, szWorkingDir, szIconPath, nIcon, szShortCutKey, nFlag); szProgramFolder = FOLDER_DESKTOP; LongPathToQuote(szCommandLine, TRUE); AddFolderIcon (szProgramFolder, PRODOUCT_NAME, szCommandLine, szWorkingDir, szIconPath, nIcon, szShortCutKey, nFlag); return TRUE; end; /////////////////////////////////////////////////////////////////////////////// // // FUNCTION: WriteReg() // // EVENT: 向註冊表中寫入定製好的CAD模板信息。 // /////////////////////////////////////////////////////////////////////////////// function BOOL WriteReg() string szKey,szNumName,svNumValue,szMenuName; //szKey表示鍵,szNumName表示字符,svNumValue表示數值 number nvType ,nvSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; if RegDBSetDefaultRoot(HKEY_CURRENT_USER) <0 then MessageBox("安裝失敗[設置註冊表根鍵失敗]!",INFORMATION); return FALSE; endif; szKey ="Software\\Autodesk\\AutoCAD\\"+g_szInVersion+"\\"+g_szCurVersion+"\\Profiles\\"+PROFILES_NAME+"\\General"; szNumName ="ACAD"; svNumValue=g_szRoamableRootFolder+";"+g_szRoamableRootFolder+"\support;"+g_ACADSearchPath+"\\;"+g_ACADSearchPath+"\\support;"+g_ACADSearchPath+"\\fonts;"+g_ACADSearchPath+"\\help;"+g_ACADSearchPath+"\\support\\color;"; svNumValue=svNumValue+INSTALLDIR+"\Bin\\Arx;"+INSTALLDIR+"\Font;"+INSTALLDIR+"\Menu;"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; szKey ="Software\\Autodesk\\AutoCAD\\"+g_szInVersion+"\\"+g_szCurVersion+"\\Profiles\\"+PROFILES_NAME+"\\Variables"; // 設置信任路徑 szNumName ="TRUSTEDPATHS"; svNumValue=INSTALLDIR+"\Bin\\Arx;"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; szKey ="Software\\Autodesk\\AutoCAD\\"+g_szInVersion+"\\"+g_szCurVersion+"\\Profiles\\"+PROFILES_NAME+"\\General Configuration"; szNumName ="MenuFile"; //特殊處理 if(g_szInVersion=="R17.0" || g_szInVersion=="R17.1")then szMenuName = "menu_"+g_szShortID+"_jk_t"; else szMenuName = "menu_"+g_szShortID+"_jk_r"; endif; svNumValue=INSTALLDIR+"\Menu\\"+szMenuName; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; if (RegDBSetDefaultRoot(HKEY_LOCAL_MACHINE) < 0) then MessageBox("安裝失敗[設置註冊表根鍵失敗]!",INFORMATION); return FALSE; endif; szKey ="SOFTWARE\\XX客戶端\\1.00"; szNumName ="InstallDir"; svNumValue=INSTALLDIR; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; if RegDBSetDefaultRoot(HKEY_CLASSES_ROOT) <0 then MessageBox("安裝失敗[設置註冊表根鍵失敗]!",INFORMATION); return FALSE; endif; szKey ="\\hhwypwsj"; szNumName =""; svNumValue="hhwy"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; szKey ="\\hhwypwsj"; szNumName ="URL Protocol"; svNumValue=":"+INSTALLDIR+"\Support\\HHShellRun\\HHShellRun.exe"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; szKey ="\\hhwypwsj\\DefaultIcon"; szNumName =""; svNumValue=INSTALLDIR+"\Support\\HHShellRun\\HHShellRun.exe"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; szKey ="\\hhwypwsj\\shell\\open\\command"; szNumName =""; svNumValue=INSTALLDIR+"\Support\\HHShellRun\\HHShellRun.exe %1"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey, szNumName, nvType, svNumValue,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; return TRUE; end; /////////////////////////////////////////////////////////////////////////////// // // FUNCTION: InstallDog() // // EVENT: 安裝加密狗驅動和服務 // /////////////////////////////////////////////////////////////////////////////// function BOOL InstallDogDirver() STRING szDogPath,szModel,svResult; number nvResult; begin // 安裝加密狗驅動和服務 if (!MAINTENANCE) then Delay(1); szDogPath = INSTALLDIR^"\\Support\\Drivers\\Drivers\\InstWiz3.exe"; //INSTALLDIR^"\\Support\\Drivers\\Drivers\\InstWiz3.exe"; 鎖打包 //INSTALLDIR^"\\Support\\Drivers\\hdd32NC.exe"; 鎖打包 szModel = "WINXPSP2"; //檢測當前的操做系統 GetSystemInfo(WINMINOR, nvResult,svResult); //Vista if(svResult =="6.0" ) then SetCompatModel(szDogPath,szModel); endif; //Win7 if(svResult =="6.1" ) then SetCompatModel(szDogPath,szModel); endif; // Win8/8.1 if(svResult == "6.2") then SetCompatModel(szDogPath,szModel); endif; if(LaunchAppAndWait (szDogPath ,"",LAAW_OPTION_WAIT)<0)then MessageBox("安裝加密鎖驅動出錯!請手動安裝。",SEVERE); endif; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: CopyVersionFiles() // 【RETURN】 // EVENT: 拷貝目錄數據 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL CopyVersionFiles() STRING szSrcDir,szDesDir,szBinName; begin //版本名稱目錄 szBinName = DES_BIN_FOLDER+g_szCustomID; szSrcDir = SRCDIR^SRC_BIN_FOLDER^szBinName; szDesDir = INSTALLDIR^DES_BIN_FOLDER; if (XCopyFile ( szSrcDir^ "*.*", szDesDir ^ "*.*",INCLUDE_SUBDIR) != 0) then return FALSE; endif; //dist目錄 szSrcDir = SRCDIR^SRC_DIST_FOLDER^"dist_x86"; szDesDir = INSTALLDIR^DES_DIST_FOLDER; if (SYSINFO.bIsWow64) then szSrcDir = SRCDIR^SRC_DIST_FOLDER^"dist_x64"; endif; if (XCopyFile ( szSrcDir^ "*.*", szDesDir ^ "*.*",INCLUDE_SUBDIR) != 0) then return FALSE; endif; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: RegisterDll() // 【RETURN】 // EVENT: 手工註冊必要的dll--採用靜默式注 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL RegisterDll() string szRegPath; begin szRegPath =TARGETDIR^REGISTER_DLLDIR; if (LongPathToShortPath (szRegPath) == 0) then LaunchAppAndWait (szRegPath ,"",LAAW_OPTION_HIDDEN|LAAW_OPTION_WAIT); endif; return TRUE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: SetCompatModel(STRING,STRING) // 【IN】szAppPath路徑,szModel 【RETURN】 BOOL // EVENT: 設置程序爲兼容模式 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL SetCompatModel(szAppPath,szModel) STRING szKey; number nvType,nvSize; begin if RegDBSetDefaultRoot(HKEY_CURRENT_USER) <0 then return FALSE; endif; szKey ="Software\\Microsoft\\Windows NT\\CurrentVersion\\AppCompatFlags\\Layers"; nvType = REGDB_STRING; if (RegDBSetKeyValueEx (szKey,szAppPath, nvType, szModel,nvSize) < 0) then MessageBox("安裝失敗[設置註冊表失敗]!",SEVERE); return FALSE; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: UninstallFiles() // 【RETURN】 BOOL // EVENT: 註冊必要的dll // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL UninstallFiles() begin //刪除安裝文件信息 DeleteProgramFolder(PRODOUCT_NAME); DeleteFolderIcon (FOLDER_DESKTOP,PRODOUCT_NAME); //DeleteProgramFolder ( TARGETDIR ); 動態連接時,無版本文件測試發現刪除不乾淨 DeleteDir(TARGETDIR^DES_BIN_FOLDER,ALLCONTENTS); DeleteDir(TARGETDIR^DES_BIN_FOLDER,ONLYDIR); DeleteDir(TARGETDIR^DES_PRJ_FOLDER,ALLCONTENTS); DeleteDir(TARGETDIR^DES_PRJ_FOLDER,ONLYDIR); DeleteDir(TARGETDIR^DES_MENU_FOLDER,ALLCONTENTS); DeleteDir(TARGETDIR^DES_MENU_FOLDER,ONLYDIR); //刪除安裝文件信息 DeleteDir(ProgramFilesFolder+"//InstallShield Installation Information//{"+PRODUCT_GUID +"}",ALLCONTENTS); DeleteDir(ProgramFilesFolder+"//InstallShield Installation Information//{"+PRODUCT_GUID +"}",ONLYDIR); end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: WindowsUnstallInfo( szGUID) // 【RETURN】 BOOL // EVENT: 檢查是否已經安裝過某個軟件信息, // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL WindowsUnstallInfo( szGUID) STRING UNINSTALL_REG; STRING szNumName,szUnInstallString; NUMBER nType,nSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; RegDBSetDefaultRoot(HKEY_LOCAL_MACHINE); UNINSTALL_REG = "\\SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\"+szGUID; nType = REGDB_STRING; RegDBGetKeyValueEx(UNINSTALL_REG,szNumName,nType,szUnInstallString,nSize); //獲取卸載腳本 if(RegDBKeyExist(UNINSTALL_REG)>0) then return TRUE; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; return FALSE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: InstallSoftSilent( szAppDir, szAppName) // 【RETURN】 BOOL // EVENT: 檢查是否已經安裝過某個軟件信息, // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL InstallSoftSilent( szAppDir, szAppName) STRING szResult,szTemp; INT nResult; begin //先查找文件,若是查找不到,須要進行提示 if (FindFile(szAppDir,szAppName,szResult) < 0) then return FALSE; else Delay(1); szTemp =szAppDir^szAppName; //須要轉換爲短路徑 if (LongPathToShortPath (szTemp) == 0) then nResult=LaunchAppAndWait(szTemp," /qd ",LAAW_OPTION_WAIT|LAAW_OPTION_HIDDEN); return TRUE; endif; return FALSE; endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: UninstallOldVersion(STRING); // 【RETURN】 // EVENT: 檢查刪除就版本信息 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL UninstallOldVersion(szOldGuid) STRING szUninstallString; BOOL bFind; INT nResult; begin while(CheckOldVersion(szOldGuid,szUninstallString)) if(AskYesNo("檢測到已存在此軟件,是否卸載後安裝新版本?",NO)=YES)then //SdShowMsg("正在卸載程序,請稍等 ...",TRUE); Delay(1); nResult = LaunchAppAndWait("",szUninstallString,LAAW_OPTION_WAIT); //刷新註冊表 nResult = LaunchAppAndWait("","cmd /c gp /force /wait:0 ",LAAW_OPTION_WAIT|LAAW_OPTION_HIDDEN); else abort; endif; endwhile; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: CheckOldVersion(szGUID,szUnInstallString) // 【RETURN】 // EVENT: 檢查舊版本安裝信息 // Author: ////////////////////////////////////////////////////////////////////////////// function BOOL CheckOldVersion(szGUID,szUnInstallString) STRING UNINSTALL_REG; STRING szNumName; NUMBER nType,nSize; begin if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS | REGDB_OPTION_WOW64_64KEY; endif; RegDBSetDefaultRoot(HKEY_LOCAL_MACHINE); UNINSTALL_REG = "\\SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\InstallShield_"+szGUID; nType = REGDB_STRING; szNumName = "UninstallString"; RegDBGetKeyValueEx(UNINSTALL_REG,szNumName,nType,szUnInstallString,nSize); //獲取卸載腳本 if(RegDBKeyExist(UNINSTALL_REG)>0) then return TRUE; endif; if (SYSINFO.bIsWow64) then REGDB_OPTIONS = REGDB_OPTIONS & ~REGDB_OPTION_WOW64_64KEY; endif; return FALSE; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: OnBegin // // EVENT: Begin event is always sent as the first event during installation. // ////////////////////////////////////////////////////////////////////////////// function OnBegin() STRING szMsg; begin InitCADVerInfo(); end; /////////////////////////////////////////////////////////////////////////////// // // FUNCTION: OnEnd // // EVENT: End event is the last event. It is not sent if the installation // has been aborted. In this case Abort event is sent // /////////////////////////////////////////////////////////////////////////////// function OnEnd() STRING szDogPath; begin if(g_bLANUCHAPP=TRUE)then LaunchAppAcad(); endif; end; ////////////////////////////////////////////////////////////////////////////// // // FUNCTION: OnInstallFilesActionAfter // // EVENT: InstallFilesActionAfter event is sent just after the // standard MSI action InstallFiles is executed. // /////////////////////////////////////////////////////////////////////////////// function OnInstallFilesActionAfter() string szPicName; begin SetupFolders(); SdInit(); szPicName = SUPPORTDIR^"LeftView.BMP"; DialogSetInfo(DLG_INFO_ALTIMAGE,szPicName,TRUE); end; //--------------------------------------------------------------------------- // OnMoved // // The OnMoved event is called just before the InstallShield action // 'GeneratedMSIScript' is executed. //--------------------------------------------------------------------------- function OnMoved() string szINI,szPathValue; begin if (!MAINTENANCE) then //拷貝安裝版本文 if(!CopyVersionFiles())then MessageBox ("複製數據文件信息出錯!", SEVERE); abort; endif; //修改啓動文件Ini信息 szINI = INSTALLDIR^LANUCH_INI; szPathValue = "SOFTWARE\\Autodesk\\AutoCAD\\"+g_szInVersion+"\\"+g_szCurVersion; if(WriteProfString (szINI, "ExeInfo", "RegPath",szPathValue)!=0) then MessageBox ("安裝啓動版本信息出錯!", SEVERE); abort; endif; //修改版本信息 if(WriteProfString (szINI, "ExeInfo", "Version",g_szCustomID)!=0) then MessageBox ("安裝版本信息出錯!", SEVERE); abort; endif; endif; end; //--------------------------------------------------------------------------- // OnMaintUIAfter // // The OnMaintUIAfter event called by the framework after the file transfer // of the setup when the setup is running in maintenance mode. By default // this event displays UI that informs the end user that the maintenance setup // has been completed successfully. //--------------------------------------------------------------------------- function OnMaintUIAfter() STRING szTitle, szMsg1, szMsg2, szOpt1, szOpt2,szMsg; NUMBER bOpt1, bOpt2; begin Disable(STATUSEX); if( REMOVEALLMODE ) then szTitle = SdLoadString(IFX_SDFINISH_REMOVE_TITLE); szMsg1 = SdLoadString(IFX_SDFINISH_REMOVE_MSG1); else szTitle = SdLoadString(IFX_SDFINISH_MAINT_TITLE); szMsg1 = SdLoadString(IFX_SDFINISH_MAINT_MSG1); endif; bOpt1 = FALSE; bOpt2 = FALSE; if ( BATCH_INSTALL ) then SdFinishReboot ( szTitle , szMsg1 , SYS_BOOTMACHINE , szMsg2 , 0 ); else SdFinish ( szTitle , szMsg1 , szMsg2 , szOpt1 , szOpt2 , bOpt1 , bOpt2 ); endif; UninstallFiles(); end; //--------------------------------------------------------------------------- // OnFirstUIAfter // // The OnFirstUIAfter event called by the framework after the file transfer // of the setup when the setup is running in first install mode. By default // this event displays UI that informs the end user that the setup has been // completed successfully. //--------------------------------------------------------------------------- function OnFirstUIAfter() STRING szTitle, szMsg1, szMsg2, szOpt1, szOpt2,szOption1,szOption2,szDocFile; NUMBER bOpt1, bOpt2; begin //註冊表 if(!WriteReg()) then abort; endif; //註冊dll RegisterDll(); //卸載快捷方式 CreateUninstShortCut(); //安裝vcredist_x86_2008 版本9.0.30729 if(!WindowsUnstallInfo(VC_REDIST_11)) then InstallSoftSilent(INSTALLDIR^VC_REDIST_DIR,g_szCurVcredist); endif; //裝狗驅動 InstallDogDirver(); if (SYSINFO.bIsWow64) then LaunchAppAndWait ("msiexec.exe", "/i \""+INSTALLDIR^"Support\\Drivers\\AceRedist.msi\" /qb", LAAW_OPTION_WAIT); endif; Disable(STATUSEX); ShowObjWizardPages(NEXT); bOpt1 = TRUE; bOpt2 = TRUE; szMsg1 = SdLoadString(IFX_SDFINISH_MSG1); szTitle=""; szMsg1=""; szMsg2=""; szOption1="當即啓動應用程序"; szOption2=""; SdFinishEx(szTitle, szMsg1, szMsg2, szOption1, szOption2, bOpt1, bOpt2); g_bLANUCHAPP = bOpt1; end; //--------------------------------------------------------------------------- // OnMaintUIBefore // // The OnMaintUIBefore event is called by the framework when the setup is // running in maintenance mode. By default this event displays UI that // allows the end user to add or remove features, repair currently // installed features or uninstall the application. //--------------------------------------------------------------------------- function OnMaintUIBefore() NUMBER nResult, nType; STRING szTitle, szMsg, svDir, svResult, szCaption,szInfo; BOOL bRunningCad; begin szInfo ="即將卸載"+PRODOUCT_NAME+",請肯定已備份數據\n 是否繼續執行卸載操做?"; if MessageBox(szInfo,MB_YESNO) = IDNO then abort; endif; bRunningCad = TRUE; while(bRunningCad) bRunningCad = ProcessRunning("acad"); if(bRunningCad)then szInfo="請肯定關閉全部的AutoCAD應用程序後,\n 再執行卸載操做"; if MessageBox(szInfo,MB_OKCANCEL) = IDCANCEL then abort; endif; endif; endwhile; Dlg_Start: nType = REMOVEALL; Dlg_SdFeatureTree: if (nType = MODIFY) then szTitle = ""; szMsg = ""; nResult = SdFeatureTree(szTitle, szMsg, INSTALLDIR, "", 2); if (nResult = BACK) goto Dlg_Start; endif; switch(nType) case REMOVEALL: ComponentRemoveAll(); // Added in IS 2009 - Set appropriate StatusEx static text. SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_REMOVEALL ) ); case REPAIR: ComponentReinstall(); // Added in IS 2009 - Set appropriate StatusEx static text. SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_REPAIR ) ); case MODIFY: // Added in IS 2009 - Set appropriate StatusEx static text. SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_MODIFY ) ); endswitch; // setup default status SetStatusWindow(0, ""); Enable(STATUSEX); StatusUpdate(ON, 100); end;
///////////////////////////////////////////////// // Function prototypes. ///////////////////////////////////////////////// prototype POINTER ArrayToPointer(BYREF VARIANT); prototype BOOL ProcessRunning(STRING); // Kernel functions. prototype NUMBER Kernel32.OpenProcess(NUMBER, BOOL, NUMBER); prototype NUMBER Kernel32.TerminateProcess(NUMBER, NUMBER); // Process information functions. prototype NUMBER PSAPI.EnumProcesses(POINTER, NUMBER, BYREF NUMBER); prototype NUMBER PSAPI.EnumProcessModules(NUMBER, BYREF NUMBER, NUMBER, BYREF NUMBER); prototype NUMBER PSAPI.GetModuleFileNameExA(NUMBER, NUMBER, BYREF STRING, NUMBER); ///////////////////////////////////////////////// // Structures. ///////////////////////////////////////////////// // Structure to mirror the C/C++ SAFEARRAY data structure. typedef _SAFEARRAY begin SHORT cDims; SHORT fFeatures; LONG cbElements; LONG cLocks; POINTER pvData; // rgsaBound omitted end; // Structure to mirror the C/C++ VARIANT data structure. typedef _VARIANT begin SHORT vt; SHORT wReserver1; SHORT wReserved2; SHORT wReserved3; NUMBER nData; end; ///////////////////////////////////////////////// // Constants. ///////////////////////////////////////////////// #define PSAPI_FILE "psapi.dll" // Windows NT process DLL #define PROCESSID_LENGTH 4 // 4 bytes (DWORD) for a process ID // Process information constants. #define PROCESS_QUERY_INFORMATION 0x400 #define PROCESS_ALL_ACCESS 0x1f0fff #define PROCESS_VM_READ 0x10 ////////////////////////////////////////////////////////////////////////////// // // Function: ArrayToPointer // // Description: Converts an InstallShield array into a C array. // // When an array is created in InstallScript, a VARIANT variable // is created which holds an OLEAutomation SAFEARRAY. To pass // such an array to a DLL function expecting a C-style array, // this function explicitly typecasts the pointer to the array // to a _VARIANT pointer so that the _SAFEARRAY pointer can be // extracted. The pointer to the actual data is then extracted // from the _SAFEARRAY pointer. // // Parameters: structArray - Array variable. // // Returns: POINTER - Pointer to array. // ////////////////////////////////////////////////////////////////////////////// function POINTER ArrayToPointer(structArray) _SAFEARRAY POINTER pstructArray; // _SAFEARRAY array pointer _VARIANT POINTER pstructVariant; // _VARIANT array pointer begin // Typecast the pointer to the array to a _VARIANT pointer. pstructVariant = &structArray; // Extract the _SAFEARRAY pointer from the _VARIANT. pstructArray = pstructVariant->nData; // Return the pointer to the actual data from the _SAFEARRAY. return pstructArray->pvData; end; ////////////////////////////////////////////////////////////////////////////// // // Function: _Process_Running // // Description: Determines if the specified process is running in memory. // // Parameters: szAppName - Name of the application to check. // // Returns: TRUE - The process is running. // FALSE - The process is not running. // ////////////////////////////////////////////////////////////////////////////// function BOOL ProcessRunning(szAppName) BOOL bvRunning; // Process is running NUMBER nvProcessIDs(512); // Array of process IDs NUMBER nvBytesReturned; // Number of bytes returned in process ID array NUMBER nvProcesses; // Number of processes running NUMBER nvIndex; // Loop index NUMBER nvProcessHandle; // Handle to a process NUMBER nvModuleHandle; // Handle to a process module NUMBER nvBytesRequired; // Number of bytes required to store values POINTER pvProcessIDs; // Pointer to process ID array STRING svModuleName; // Module name STRING svFileName; // Module filename begin // The psapi.dll reads the Windows NT performance database. The DLL // is part of the Win32 SDK. if UseDLL(WINSYSDIR ^ PSAPI_FILE) < 0 then // Could not load psapi.dll. MessageBox("ERROR: Could not load [" + WINSYSDIR ^ PSAPI_FILE + "].", SEVERE); return FALSE; endif; // Get the PIDs of all currently running processes. pvProcessIDs = ArrayToPointer(nvProcessIDs); EnumProcesses(pvProcessIDs, 512, nvBytesReturned); // Determine the number of process IDs retrieved. Each process ID // is PROCESSID_LENGTH bytes. nvProcesses = nvBytesReturned / PROCESSID_LENGTH; // Get the executable associated with each process, and check if // its filename matches the one passed to the function. for nvIndex = 1 to nvProcesses // Get a handle to the process. nvProcessHandle = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, 0, nvProcessIDs(nvIndex)); if nvProcessHandle != 0 then // Get a handle to the first module in the process, which // should be the executable. if EnumProcessModules(nvProcessHandle, nvModuleHandle, PROCESSID_LENGTH, nvBytesRequired) != 0 then // Get the path of the module. if GetModuleFileNameExA(nvProcessHandle, nvModuleHandle, svModuleName, SizeOf(svModuleName)) != 0 then // Extract the filename (without an extension) from // the path. ParsePath(svFileName, svModuleName, FILENAME_ONLY); if StrCompare(svFileName, szAppName) = 0 then // The process module matches the application // name passed to the function. bvRunning = TRUE; goto ProcessRunningEnd; endif; endif; endif; endif; endfor; ProcessRunningEnd: if UnUseDLL(PSAPI_FILE) < 0 then MessageBox("ERROR: Could not unload [" + WINSYSDIR ^ PSAPI_FILE + "].", SEVERE); return FALSE; endif; return bvRunning; end;
InstallShield :@http://blog.51cto.com/liucw/1220134
InstallShield Limited Edition for Visual Studio : @https://www.cnblogs.com/zhuxiaohui/p/5139740.html
InstallShield(最全) :@http://blog.csdn.net/duanbeibei/article/details/50333603
ctrl + F7:檢查
F7:編譯
把Product Configuration 1\Release 1\DiskImages\下的DISK1壓縮,運行裏面的setup.exe就可進行安裝