正式会员享受无限制浏览网站功能和高速网盘下载,赶快加入本站吧!
您需要 登录 才可以下载或查看,没有账号?立即注册
x
实现点
覆盖安装(note : InstallShield本来就提供, 需要注意的是 : InstallShield工程的新版本要增加版本号,不能是原来的版本号. 打包用的PE文件版本号需要比已经安装的PE文件版本号高, 而且必须要是改前三位版本号,不能改第四位版本号. 否则不能覆盖安装. e.g. 旧PE版本号 1.0.1.0, 新版本号码不能为1.0.1.9, 可以为 9.0.1.0, 1.9.1.0, 1.0.9.0)
对已经安装的旧版本进行检测, 通过查InstallShield自带帮助, 翻了好久,发现可以用 MAINTENANCE 来判断
当用户选择安装时,直接安装. 我采用了跳过 OnMaintUIBefore() 中 SdWelcomeMaint, 直接对 nType 赋值成 REPAIR, 来实现
当用户选择不安装时, 在 OnFirstUIBefore() 和 OnMaintUIBefore() 处 abort 实现安装程序退出.
- #include "ifx.h"
- prototype IsProductWasInstalled();
- prototype GetUnInstallExePathName(BYREF STRING);
- prototype RunUnInstallExe();
- BOOL g_bSetupNow; ///< 如果旧版程序已经安装, 记录用户选择(是否覆盖安装)
- function OnBegin()
- begin
- // TODO: Perform custom initialization steps, check requirements, etc.
- g_bSetupNow = TRUE;
- if IsProductWasInstalled() then
- if (AskYesNo("已经发现本软件已经被安装!\r\n" + "是否继续安装?", YES) = NO) then
- g_bSetupNow = FALSE; ///< 用户选择不安装
- // RunUnInstallExe();
- endif;
- endif;
- end;
- function IsProductWasInstalled()
- BOOL bRc;
- begin
- if (MAINTENANCE != 0) then
- // 产品已经被安装过
- bRc = TRUE;
- else
- // 产品首次被安装(还没有被安装,本次安装是首次)
- bRc = FALSE;
- endif;
- return bRc;
- end;
- function GetUnInstallExePathName(strPathName)
- BOOL bRc;
- begin
- if (RegDBGetItem(REGDB_UNINSTALL_MODIFYPATH, strPathName) < 0) then
- bRc = FALSE;
- else
- bRc = TRUE;
- endif;
- return bRc;
- end;
- function RunUnInstallExe()
- STRING strUnInstallPathName;
- begin
- /**
- if (GetUnInstallExePathName(strUnInstallPathName)) then
- LaunchAppAndWait(strUnInstallPathName, "", WAIT);
- endif;
- */
- ComponentRemoveAll();
- end;
- //---------------------------------------------------------------------------
- // OnFirstUIBefore
- //
- // First Install UI Sequence - Before Move Data
- //
- // The OnFirstUIBefore event is called by OnShowUI when the setup is
- // running in first install mode. By default this event displays UI allowing
- // the end user to specify installation parameters.
- //
- // Note: This event will not be called automatically in a
- // program...endprogram style setup.
- //---------------------------------------------------------------------------
- function OnFirstUIBefore()
- number nResult, nLevel, nSize, nSetupType;
- string szTitle, szMsg, szOpt1, szOpt2, szLicenseFile;
- string szName, szCompany, szTargetPath, szDir, szFeatures;
- BOOL bLicenseAccepted;
- begin
- /// 不安装时的处理 : 退出安装程序
- if (g_bSetupNow == FALSE) then
- abort;
- endif;
- // Added in InstallShield 15 - Show an appropriate error message if
- // -removeonly is specified and the product is not installed.
- if( REMOVEONLY ) then
- Disable( DIALOGCACHE );
- szMsg = SdLoadString( IDS_IFX_ERROR_PRODUCT_NOT_INSTALLED_UNINST );
- SdSubstituteProductInfo( szMsg );
- MessageBox( szMsg, SEVERE );
- abort;
- endif;
- nSetupType = COMPLETE;
- szDir = TARGETDIR;
- szName = "";
- szCompany = "";
- bLicenseAccepted = FALSE;
- // Beginning of UI Sequence
- Dlg_Start:
- nResult = 0;
- Dlg_SdWelcome:
- szTitle = "";
- szMsg = "";
- //{{IS_SCRIPT_TAG(Dlg_SdWelcome)
- nResult = SdWelcome( szTitle, szMsg );
- //}}IS_SCRIPT_TAG(Dlg_SdWelcome)
- if (nResult = BACK) goto Dlg_Start;
- Dlg_SdLicense2:
- szTitle = "";
- szOpt1 = "";
- szOpt2 = "";
- //{{IS_SCRIPT_TAG(License_File_Path)
- szLicenseFile = SUPPORTDIR ^ "License.rtf";
- //}}IS_SCRIPT_TAG(License_File_Path)
- //{{IS_SCRIPT_TAG(Dlg_SdLicense2)
- nResult = SdLicense2Ex( szTitle, szOpt1, szOpt2, szLicenseFile, bLicenseAccepted, TRUE );
- //}}IS_SCRIPT_TAG(Dlg_SdLicense2)
- if (nResult = BACK) then
- goto Dlg_SdWelcome;
- else
- bLicenseAccepted = TRUE;
- endif;
- Dlg_SdRegisterUser:
- szMsg = "";
- szTitle = "";
- //{{IS_SCRIPT_TAG(Dlg_SdRegisterUser)
- nResult = SdRegisterUser( szTitle, szMsg, szName, szCompany );
- //}}IS_SCRIPT_TAG(Dlg_SdRegisterUser)
- if (nResult = BACK) goto Dlg_SdLicense2;
- Dlg_SetupType2:
- szTitle = "";
- szMsg = "";
- nResult = CUSTOM;
- //{{IS_SCRIPT_TAG(Dlg_SetupType2)
- nResult = SetupType2( szTitle, szMsg, "", nSetupType, 0 );
- //}}IS_SCRIPT_TAG(Dlg_SetupType2)
- if (nResult = BACK) then
- goto Dlg_SdRegisterUser;
- else
- nSetupType = nResult;
- if (nSetupType != CUSTOM) then
- szTargetPath = TARGETDIR;
- nSize = 0;
- FeatureCompareSizeRequired( MEDIA, szTargetPath, nSize );
- if (nSize != 0) then
- MessageBox( szSdStr_NotEnoughSpace, WARNING );
- goto Dlg_SetupType2;
- endif;
- endif;
- endif;
- Dlg_SdAskDestPath2:
- if ((nResult = BACK) && (nSetupType != CUSTOM)) goto Dlg_SetupType2;
- szTitle = "";
- szMsg = "";
- if (nSetupType = CUSTOM) then
- //{{IS_SCRIPT_TAG(Dlg_SdAskDestPath2)
- nResult = SdAskDestPath2( szTitle, szMsg, szDir );
- //}}IS_SCRIPT_TAG(Dlg_SdAskDestPath2)
- TARGETDIR = szDir;
- endif;
- if (nResult = BACK) goto Dlg_SetupType2;
- Dlg_SdFeatureTree:
- if ((nResult = BACK) && (nSetupType != CUSTOM)) goto Dlg_SdAskDestPath2;
- szTitle = "";
- szMsg = "";
- szFeatures = "";
- nLevel = 2;
- if (nSetupType = CUSTOM) then
- //{{IS_SCRIPT_TAG(Dlg_SdFeatureTree)
- nResult = SdFeatureTree( szTitle, szMsg, TARGETDIR, szFeatures, nLevel );
- //}}IS_SCRIPT_TAG(Dlg_SdFeatureTree)
- if (nResult = BACK) goto Dlg_SdAskDestPath2;
- endif;
- Dlg_SQLServer:
- nResult = OnSQLServerInitialize( nResult );
- if( nResult = BACK ) goto Dlg_SdFeatureTree;
- Dlg_ObjDialogs:
- nResult = ShowObjWizardPages( nResult );
- if (nResult = BACK) goto Dlg_SQLServer;
- Dlg_SdStartCopy2:
- szTitle = "";
- szMsg = "";
- //{{IS_SCRIPT_TAG(Dlg_SdStartCopy2)
- nResult = SdStartCopy2( szTitle, szMsg );
- //}}IS_SCRIPT_TAG(Dlg_SdStartCopy2)
- if (nResult = BACK) goto Dlg_ObjDialogs;
- // Added in 11.0 - Set appropriate StatusEx static text.
- SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_FIRSTUI ) );
- return 0;
- end;
- //---------------------------------------------------------------------------
- // OnMaintUIBefore
- //
- // Maintenance UI Sequence - Before Move Data
- //
- // The OnMaintUIBefore event is called by OnShowUI 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.
- //
- // Note: This event will not be called automatically in a
- // program...endprogram style setup.
- //---------------------------------------------------------------------------
- function OnMaintUIBefore()
- number nResult, nType;
- string szTitle, szMsg;
- begin
- /// 不安装时的处理 : 退出安装程序
- if (g_bSetupNow == FALSE) then
- abort;
- endif;
- // nType defaults to MODIFY.
- nType = REPAIR; ///< 只有选修复, 才能实现覆盖安装
- //Initialize SQL
- OnSQLServerInitializeMaint();
- // Beginning of UI Sequence
- Dlg_Start:
- // Added in Version 9.5 - Support for REMOVEONLY option.
- if( !REMOVEONLY ) then
- // In standard mode show maintenance dialog
- Disable( BACKBUTTON );
- /// 不让用户选择, 直接进行"修复", 实现覆盖安装
- // nType = SdWelcomeMaint( szTitle, szMsg, nType );
- Enable( BACKBUTTON );
- nResult = NEXT;
- else
- // Hide the initial progress dialog as otherwise the user can
- // click on it, and hide the MessageBox.
- Disable( DIALOGCACHE );
- // In RemoveOnly mode, set to remove.
- nType = REMOVEALL;
- endif;
- // Show Uninstall Confirmation Dialog
- if ( nType = REMOVEALL ) then
- nResult = MessageBox( SdLoadString( IFX_MAINTUI_MSG ), MB_YESNO );
- if (nResult != IDYES ) then
- if( REMOVEONLY ) then
- // In REMOVEONLY mode, abort the setup.
- abort;
- else
- // In non-REMOVEONLY mode, redisplay the previous dialog.
- goto Dlg_Start;
- endif;
- endif;
- endif;
- Dlg_SdFeatureTree:
- if ( nType = MODIFY ) then
- szTitle = "";
- szMsg = SdLoadString( SD_STR_COMPONENT_MAINT_MSG );
- nResult = SdFeatureTree( szTitle, szMsg, TARGETDIR, "", -1 );
- if ( nResult = BACK ) goto Dlg_Start;
- endif;
- Dlg_ObjDialogs:
- nResult = ShowObjWizardPages( nResult );
- if ( ( nResult = BACK ) && ( nType != MODIFY ) ) goto Dlg_Start;
- if ( ( nResult = BACK ) && ( nType = MODIFY ) ) goto Dlg_SdFeatureTree;
- switch(nType)
- case REMOVEALL:
- // Ensure that all previously installed features are removed.
- FeatureRemoveAllInMediaAndLog();
- // Added in 11.0 - Set appropriate StatusEx static text.
- SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_REMOVEALL ) );
- case REPAIR:
- // Changed for DevStudio 9, Disk1 files are now always updated when installed
- // so when running from ADDREMOVE we need to prevent these files from being
- // updated since this will result in files being updated that are locked by the setup.
- // Updating these files when running from ADDREMOVE should not be needed since updates
- // are not run directly from Add/Remove.
- if( ADDREMOVE ) then
- // Reinstall all previously installed features, except
- // disk1 features.
- FeatureUpdate( "" );
- else
- // Reinstall all previously installed features.
- FeatureReinstall();
- endif;
- // Added in 11.0 - Set appropriate StatusEx static text.
- SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_REPAIR ) );
- case MODIFY:
- // Added in 11.0 - Set appropriate StatusEx static text.
- SetStatusExStaticText( SdLoadString( IDS_IFX_STATUSEX_STATICTEXT_MAINTUI_MODIFY ) );
- endswitch;
- end;
- //---------------------------------------------------------------------------
- // OnMoveData
- //
- // The OnMoveData event is called by OnShowUI to initiate the file
- // transfer of the setup.
- //
- // Note: This event will not be called automatically in a
- // program...endprogram style setup.
- //---------------------------------------------------------------------------
- function OnMoveData()
- number nResult, nMediaFlags;
- begin
- // Don't install the DISK1COMPONENT if MAINT_OPTION_NONE was specified.
- if( MAINT_OPTION = MAINT_OPTION_NONE ) then
- FeatureSelectItem( MEDIA, DISK1COMPONENT, FALSE );
- endif;
- // Updated in 11.5, disable the cancel button during file transfer unless
- // this is non-maintenance mode or repair mode.
- if( MAINTENANCE && ( !REINSTALLMODE || UPDATEMODE ) ) then
- Disable( CANCELBUTTON );
- endif;
- // Show Status
- // Note: Start status window at 1 in case CreateInstallationInfo call
- // is lengthy.
- SetStatusWindow( 1, "" );
- Enable( STATUSEX );
- StatusUpdate( ON, 100 );
- // Create the uninstall infomation (after displaying the progress dialog)
- // Don't create uninstall information if MAINT_OPTION_NONE was specified.
- if( MAINT_OPTION != MAINT_OPTION_NONE ) then
- CreateInstallationInfo();
- endif;
- // Move Data
- nResult = FeatureTransferData( MEDIA );
- // Moved in 11.0, Check for failure before creating uninstall key.
- // Handle move data error and abort if error occured.
- if( nResult < ISERR_SUCCESS ) then
- OnComponentError();
- abort;
- endif;
- // Create uninstall key, if DISK1COMPONENT was installed.
- if( IFX_DISK1INSTALLED ) then
- // Store text-subs for maintenance mode later, only do this when
- // disk 1 is installed. Note that any text-subs that are updated after
- // this call will not be remembered during maintenance mode.
- FeatureSaveTarget("");
- // Write uninstall information.
- MaintenanceStart();
- // Customize Uninstall Information
- OnCustomizeUninstInfo();
- endif;
- // Disable Status
- Disable( STATUSEX );
- end;
复制代码 |