How to display a non-blocking warning for the oper

2019-01-18 05:54发布

问题:

I already block installation of our software on operating systems where it is known not to work like this:

<Condition Message="This software needs Windows XP or newer.">
   <![CDATA[VersionNT >= 501]]>
</Condition>

Now I would also like to display a non-blocking warning if the user tries to install the software on an operating system (VersionNT + Service Pack) that is not explicitly supported, even though it might work.

For example, we only explicitly support the latest service pack of each operating system.

How can I display such a warning?

回答1:

I tackled this problem in 3 parts:

  1. defining an OSWarningText property which is only set when a warning needs to be given
  2. authoring a custom warning screen
  3. Inserting the custom warning screen in the UI sequence if necessary

1. Defining an OSWarningText property

First, declare the property and give it the "unset" value by default:

  <Property Id="OSWarningText" Value="{}"/>

To construct the actual value of the property, set an intermediary property for each possible warning. Make sure the conditions for each warning do not overlap:

  <SetProperty Id="OSWarningText1" After="AppSearch"
     Value="Detected XP SP [ServicePackLevel]. SP3 or higher is recommended.">
     <![CDATA[(VersionNT = 501) AND NOT (ServicePackLevel >= 3)]]>
  </SetProperty>

  <SetProperty Id="OSWarningText2" After="SetOSWarningText1"
     Value="Detected Vista SP [ServicePackLevel]. SP2 or higher is recommended.">
     <![CDATA[(VersionNT = 600) AND NOT (ServicePackLevel >= 2)]]>
  </SetProperty>

Assuming the conditions don't overlap, we can safely condense the warnings in a single property like this:

  <SetProperty Id="OSWarningText" After="SetOSWarningText2"
     Value="[OSWarningText1][OSWarningText2]" />    

2. Authoring a custom warning screen.

This is similar to the example for adding a checkbox for the desktop shortcut. Copy one of the existing dialog definitions from the wix sources, e.g. InstallDirDlg.wxs and rename it to WarningDlg.wxs.

Set the dialog ID to Id="WarningDlg. Strip out the unnecessary controls and replace them by a warning image and our previously defined OSWarningText:

<Control Id="OSWarning" Type="Text" X="100" Y="80" Width="250" Height="60"
    NoPrefix="yes" Text="[OSWarningText]" />

<Control Id="WarningIcon" Type="Icon" X="20" Y="60" Width="64" Height="64"
   Text="Warning.ico" >
   <Binary Id="Warning.ico" SourceFile="..\icons\warning.ico"/>
</Control>

The idea is to create something like this:

3. Inserting the custom warning screen in the UI sequence

Now we need to make sure that the warning screen is displayed between the welcome dialog and the license agreement dialog, but only if there actually is a warning to show. This is a special case of the more general branching wizard sequences problem.

Again, copy a predefined UI sequence from the wix sources, e.g. WixUI_InstallDir.wxs and rename the UI ID to Id="MyWixUI". Reference this in your main wxs file as <UIRef Id="MyWixUI" />. Now find and edit the event handlers for the WelcomeDlg next button.

You can set properties in response to a button press and an extra condition, and you can show the next dialog based on a property. We'll make use of that to handle the WelcomeDlg next button like this:

  1. reset the WelcomeDlg_Next property to "unset"
  2. set the WelcomeDlg_Next property to "WarningDlg" but only if OSWarningText is set
  3. set the WelcomeDlg_Next property to "LicenseAgreementDlg" but only if OSWarningText is NOT set.
  4. Show the dialog given by WelcomeDlg_Next, if the property was correctly set.

The Wix code to do that looks like this:

        <Publish Dialog="WelcomeDlg" Control="Next"
            Property="WelcomeDlg_Next" Value="{}"
            Order="1">1</Publish>
        <Publish Dialog="WelcomeDlg" Control="Next"
            Property="WelcomeDlg_Next" Value="WarningDlg"
            Order="2">OSWarningText</Publish>
        <Publish Dialog="WelcomeDlg" Control="Next"
            Property="WelcomeDlg_Next" Value="LicenseAgreementDlg"
            Order="3">NOT OSWarningText</Publish>
        <Publish Dialog="WelcomeDlg" Control="Next"
            Event="NewDialog" Value="[WelcomeDlg_Next]"
            Order="4">WelcomeDlg_Next</Publish>

Then do the equivalent for the License Agreement "back" button: it should go back to the welcome screen if there is no warning, or else to the warning screen.