Windows Mobile 6.5 Start Screen PNG Icon Display problem

Some developers are reporting a problem with the PNG icon not displaying in the Start screen.The usual symptom is that it does not show up immediately after installation but is seen after a device reset. This problem occurs if following the static cab method from the blog post: Using Custom Icons in Windows Mobile 6.5. I can reproduce this pretty consistently by installing again after initially installing. (During this process the first installation is uninstalled.) The static method does not use a setup DLL, but instead uses CAB file directives that are easily specified using Visual Studio to define the installation destination, files to be installed, the program shortcut, and any necessary registry keys.

So why is this happening?

For the PNG file to be displayed, the following sequence must take place, the next step dependant on the next:

  1. Copy the PNG File to the destination directory
  2. Create the registry key pointing to the PNG file
  3. Create the program shortcut

When the shortcut is created the shell will:

  1. Use the shortcut (.lnk) file specified in step 3 above, and look up the registry key specified in step 2 above. The registry key needs to exist for this step to succeed.
  2. Open the PNG file, based on the registry key, and cache the Start screen icon.
  3. If you look at the _setup.xml that is included CAB file, you can see the order of events:
   1: <characteristic type="%CE11%" translation="install">

   2: <characteristic type="MakeDir" />

   3: <characteristic type="SMS Intercept.lnk" translation="install">

   4: <characteristic type="Shortcut">

   5: <parm name="Source" value="%InstallDir%\sms Intercept.exe" translation="install" />

   6: ...

   7: <characteristic type="Registry">

   8: <characteristic type="HKLM\Security\Shell\StartInfo\Start\SMS Intercept.lnk">

   9: <parm name="Icon" value="%InstallDir%\AppIcon.png" datatype="string" translation="install" />

  10: </characteristic>

Note that the instructions to create the shortcut appear sooner in the file than those for the creation of the registry key. In most cases, the timing is such that despite this order, the registry key is in place by the time the shortcut cut is actually created. If the registry key pointing to the location of the PNG file does not exist when the shortcut is created, the PNG icon will not be created.

Unfortunately the order of these events cannot be changed in the Visual Studio project or by reordering the directives in the .INF file.

The workaround is to append the XML for the shortcut creation to the CAB file. This will ensure that the shortcut creation is the last instruction to be processed. You can do this by following these steps:

  1. Remove the shortcut directive from your Smart Device CAB file project in Visual Studio.
  2. Modify the following XML (lines 4 and 6) to match your application:

   1: <characteristic type="FileOperation">

   2:     <characteristic type="%CE11%" translation="install">

   3:     <characteristic type="MakeDir" /> 

   4:         <characteristic type="SMS Intercept.lnk" translation="install">

   5:         <characteristic type="Shortcut">

   6:             <parm name="Source" value="%InstallDir%\sms Intercept.exe" translation="install" /> 

   7:         </characteristic>

   8:         </characteristic>

   9:     </characteristic>

  10: </characteristic>

  1. Save this to a file: shortcut.xml
  2. Get the command line used by CABWIZ to build your CAB file. We are going to use this to build a Post Build step.
    1. Build your CAB file project.
    2. Open the Output window in Visual Studio and you should see something like:

Building file ‘C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Debug\StaticCAB.cab’…

“C:\Program Files\Microsoft Visual Studio 9.0\smartdevices\sdk\sdktools\cabwiz.exe”
     “C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Debug\StaticCAB.inf”
     /dest “C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Debug\”
     /err CabWiz.log

  1. Modify your Visual Studio main application project, to include a post build event. (Project | Properties | Build Event) (Ideally we would do this as part of building the CAB file, but Smart Device CAB projects do not include pre or post build events.)
    1. Paste in the command line with the switch (/postxml) to add the shortcut.xml file into the Post Build event command line:

      “C:\Program Files\Microsoft Visual Studio 9.0\smartdevices\sdk\sdktools\cabwiz.exe”
           “C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Debug\StaticCAB.inf”
           /postxml “C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Shortcut.XML”
          
      /dest “C:\Projects\sms Intercept\sms Intercept\sms Intercept\CAB Static\Static CAB\Debug\”
           /err CabWiz.log

  2. Now when you build the main project, your CAB file will also be built, with instructions in the XML in the correct order.

The static cab project in the PNG Start screen sample with the above implemented can be found here.

I realize this is not the cleanest solution – but it will resolve the problem of the PNG icon sometimes not being displayed if using the static CAB deployment method. At least, you still don’t have to write / maintain any C++ code to support the PNG icon.

Enjoy-

Mike