We have made build 2352 available for download. This build includes mostly updates to the documentation - several more templates have been documented - and it also includes minor fixes to the ReadFileToString and WriteStringToFile methods that would report errors on the wrong api in some circumstances.

We are trying to get into a schedul or releasing something new every Monday but we hit an unexpected problem yesterday so we delayed the release until this morning!

-- Arnor Baldvinsson

1

Two months ago I implemented the Clarion PDF generation templates in a client project. I was pretty horrified by the results as characters were chopped and spaced very strangely. After posting about this on the Clarion newsgroups, Lee White suggested that this was because I was running Large Fonts on my system.

Since I have had to deal with Large Font issues before simply because I use high resolution and need to be able to seeB) I decided to take a closer look at this and see what was going on.

Sure enough the problem stems from code in the ABPRPDF.CLW file where the width of the characters is calculated. To fix this I made some changes to the files.

This involves adding a single method to the PDFGeneratorClass class in ABPRPDF.INC and ABPRPDF.CLW:

Add to class declaration in ABPRPDF.INC (I put it in at the top of the
method list, around line 195):

AdjustDPIValues   PROCEDURE(Long pValue),Long 
!! AB 2009-02-19  Adjusts DPI values

In the classfile, ABPRPDF.clw, I added this:

PDFGeneratorClass.AdjustDPIValues   PROCEDURE(Long pValue)!!,Long 
!! AB 2009-02-19  Adjusts DPI values
HDcScreen  UNSIGNED
IDPI       Long
R          Real
L          Long
 Code
 R = 1
 HDcScreen = GetDC(0)
 If HDcScreen <> 0
   IDPI = GetDeviceCaps(HDcScreen, 88)
   L = ReleaseDC(0, HDcScreen)
   R = IDPI/96
 End
 Return (pValue / R)

In PDFGeneratorClass.AddFontDescriptor method, you have code like this:

!SET the fonts Width
LOOP LOC:I=SELF.FontsNames.FirstChar TO SELF.FontsNames.LastChar
   LOC:CharToTest=CHR(LOC:I)
   IF GetTextExtentPoint32(LOC:DC,LOC:CharToTest, 1,LOC:CharSize)<>0 THEN
      IF LOC:Subclasing THEN
         IF SELF.FontsNames.CharWidth[LOC:I] THEN
            SELF.FontsNames.CharWidth[LOC:I] = LOC:CharSize.eW
         END
      ELSE
         SELF.FontsNames.CharWidth[LOC:I] = LOC:CharSize.eW
      END
   END
END

I changed both of the assignments to the CharWidth to:

SELF.FontsNames.CharWidth[LOC:I] = |
           SELF.AdjustDPIValues(LOC:CharSize.eW)

In PDFGeneratorClass.GetTextWidth method, you have code like this:

 IF SelectObject(LOC:DC, LOC:HFont) THEN
    RV = GetTextExtentPoint32(LOC:DC,pText, LEN(pText),LOC:CharSize)
    LOC:OLDMAPMODE=SetMapMode(LOC:DC,LOC:OLDMAPMODE)
    DeleteObject(LOC:HFont)
    RETURN LOC:CharSize.eW + (LOC:CharSize.eW/20)
 END

I changed the RETURN to adjust the value:

RETURN SELF.AdjustDPIValues(LOC:CharSize.eW + (LOC:CharSize.eW/20))

This takes care of the font sizing problem in any DPI combination that I
threw at it:)

Arnor Baldvinsson

We have made Clarion 7 compatible installs available for ALL of our products! Those who have a valid subscription can log in and download the latest installs. The installs have been tested with the last 2-3 builds of Clarion 7 and anything we have found has been fixed if we could. There is a couple of items that we found to be bugs in Clarion and we are certain that those will be fixed by Softvelocity as soon as possible.

One problem we ran into was with our Checkbox Fixer. It fixes checkboxes and radio buttons on reports so they look better and are more easily readable. We create controls at runtime and rely on getting the font information from the controls on the report. In Clarion 6.3 and older this worked flawlessly. In Clarion 7 the font size for Radio buttons is not related to the actual font size - not sure what it is related to. On our test machines here we would get a value of 25 points while Softvelocity confirmed that they were getting values around 64 points!

Another issue with Clarion 7 is that we cannot use the Menu theming in PowerToolbar in Clarion 7 so it has been disabled. Clarion 7 uses owner drawn menus and there is no way to make the PowerOffice menus work with them unless SV makes it possible to turn the Clarion 7 menus into standard windows menus like they are in Clarion 6.

If you find any problems with the new installs, either for Clarion 7 or older then please let us know as soon as possible so we can fix them right away and release new builds.

We have done a lot to make the look and feel of all our products and all our installs as similar as possible. All our templates now have a "Support" tab where you can go directly to our website, our bug tracker and open a support web page that is installed on your computer. From that page you can log into your account, open the online chat software, etc. etc.

We now use our Build Automator to build all our installs. That means that everything should have exactly the same version numbers, including template source, class source, install, everything. So you can see immediately by looking at the first lines of a source file what version it is if you need to report problems. All the templates also show the version number on the Support tab and the release date. We hope this will help tracking down issues.

One other thing that we are changing and that is that we will be making new installs available for download without overwriting or removing the old installs. We will however not make installs that are older than todays installs available so this is more for future use. This allows you to download older installs if you need to for example if you are working on client projects that use older versions and you don't want to update.

There has been a lot of discussion about placement of demo apps for Clarion 7. All our installs now allow you to select a folder to place the demo apps in for both Clarion 7 and older versions. By default the suggested path is %ROOT%\3rdParty\Examples\ProductName in Clarion 6 and older and CSILD_COMMON_DOCUMENTS\SoftVelocity\Clarion7\Accessory\Icetips\ProductName in Clarion 7. If you install for Clarion 7 a shortcut is created to the demo apps folder during the install.

Arnor Baldvinsson

We have finished testing for the Beta 1 release of the Build Automator today and it will be made available to beta testers after the weekend. This beta includes a lot of fixes that I have been working on for the past several months. Details about the fixes and new features in this build will be publiesed on the Build Automator website after the weekend.

I also worked on a fix for XP Taskpanel which had refresh problems in Clarion 7 resulting in the taskpanel not drawing correctly. In my tests the fix worked without problems in Clarion 7 build 5332, but the customer reporting the problem was still having some problems with it. I will probably not get more information until after the weekend.

-- Arnor Baldvinsson

It has been quite a while since I wrote on my blog and I'm planning on changing that! The past couple of months have just flown by!

I am right now finishing new Clarion 7 compatible installs for all of our Clarion third party products. So far everything is looking good and I should finish the new installs before Monday, April 13. I already have installs for PowerToolbar, XP TaskPanel, XP Themes, Outlookbar, Previewer, Utilities and Magic Buttons ready and tested. What is left is the Magic Locks, Magic Entries, Checkbox Fixer and SQL browse.

I am also getting close to beta testing of a new release of our Build Automator with a ton of fixes and updates.

Once those new installs are built and released I will be in a better position to release updates faster when new features are added or fixes are made. Every install is now built with the Build Automator and SetupBuilder 6.9. Some of the documentation for the older tools has got a bit out of sync and I will be working on getting that updated.

We are looking forward to the release of Clarion 7. While the new IDE takes some time getting used to and there is still a lot of polishing going on, it has some very nice and welcome features, such as a nice editor with code folding and all kinds of nice features. The IDE is much faster to load templates and classes than the old IDE. We have not found any major issues with it in our testing with our products.

There are, however, some limitations in some of our products. XPTheme is not needed in Clarion 7 since it themes all the controls that the XPTheme used to them. Several methods in the XPTheme classes are used by PowerToolbar so we modified the template to also work in C7 without implementing any theming. So far it seems to work fine. PowerToolbar cannot be used to theme the menus in Clarion 7 because it uses owner drawn menus and there is no way to turn them off. PowerToolbar does it's own owner drawn menus and they cannot work together with the Clarion 7 menus. So the menu theming in PowerToolbar is disabled in Clarion 7.

-- Arnor Baldvinsson

2

I stumbled on a really good deal on a HP LaserJet CP1215 color laser printer I had been looking at it at OfficeDepot and they had it for $199. I was looking it up on the HP website and they had it for a $99 special deal and free shipping so I jumped on it.

The printer arrived it last Saturday and tonight I finally got some time set it up. It was easy to set up. I connected it to my Vista 64 machine and there were no issues or problems and it prints just beautifully! I checked it couple of days after I bought it and it was back up to $299 and I see that they are now out of stock;)

It is rated 12ppm in Black only and 8ppm in color. We are starting to send out printed letters to our customers since we get close to 40% of our emails back with errors of one sort or the other, mostly because people have changed email addresses. So it is getting very difficult for us to keep in direct touch with our customers.

We have already sent out one mailing, about 3 weeks ago, and we got pretty good response so we are definitely going to be using this more and more in the future.

I have two excellent Epson photo printers, an older Epson 2200 workhorse and a more recent R-340. After comparing prices for ink and toner I realized that the difference wasn't much - if any - and the laser is faster and does a pretty good job - images and graphics look crips and details are excellent. Besides I would like to use my photo printers to print photos, which is what they were made for!

I will keep you updated on how this printer works in the long run, but so far it looks pretty impressive!

-- Arnor Baldvinsson

Wow, what a roller coaster ride the last few weeks have been! In the beginning of December we reached an agreement with PowerOffice AS in Norway to take over development and sales of their 4 excellent Clarion third party products, Outlookbar, PowerToolbar, XP-Taskpanel and XP-Theme. We immediately started working on getting everything transferred to Icetips which meant changing template and code etc. We also changed the documentation to reflect the new ownership.

I decided to do a bit of a housecleaning on our templates and sources to try to standardize look and feel for all our templates. That also meant creating Build Automator projects for each install as I use the Build Automator to do search and replace operation on the source files after they have been copied to their final destination folders before building the install. This includes updating the version number, copyright notices and other information that can be build related.

Since C7 seemed to be close to come out into public beta with the application generator I decided to head for Clarion 7 installs. At first I started with separate installs, but then Friedrich posted some excellent code that helped me figure out how best to do this in a single install.

We also decided it was time to do some much needed spring cleaning on our website and Sue sat down and came up with the design of the new website. We are very proud of it and feel that is much more functional and much cleaner than the old site, which was banged together in a real hurry and kind of got stuck there. The site has been tested in Firefox 2 and 3, Internet Explorer 6 and 7, Opera and Safari.

Just before Christmas Softvelocity announced that Clarion 7 would be released into public beta before the holidays so we pushed really hard to try to get this done as soon as possible. I got all the installs ready and all the demos converted to Clarion 7. I ran into an issue with the menus in the PowerToolbar which simply cannot be used with Clarion 7 because Clarion 7 uses owner drawn menus, which are not compatible with PowerToolbar since it also uses owner drawn menus. The positive in that is that Clarion 7 seems to do a fairly good job of theming the menus so what I did was that if the template is in Clarion 7 it simply disables the menu theming in the PowerToolbar. XP-Themes will probably not make it into Clarion 7 since it's become redundant as Clarion 7 themes the controls that you previously needed XP-Theme to theme. But it can of course still be used in Clarion 6. Once we get some time to look into it, we will check to see if we can make XP-Theme play nicely with Clarion 7 and the existing themed controls in there. Who knows, maybe we will be able to bring this reliable, old friend forward.

All the installs, except for the XP-Theme install, now have Clarion 7 applications. I have tested them in Clarion 7 build 4542 and as far as I can tell, they all work identical to the Clarion 6 demos - with the exception of the PowerToolbar menus.

The Clarion 7 compatible installs for Outlookbar, PowerToolbar, XP-Taskpanel, XP-Theme and the Icetips Previewer are now ready to download. I'm working on getting the Magic Locks installs ready - ran into a weird issue with one of the demo windows when I was testing under Clarion 7. If nothing comes up we should have all our product installs ready for Clarion 7 by the end of the week.

The PowerOffice products have now become part of our Gold and Silver subscriptions. For the past 17 months or so we have offered 33% discount to previous Icetips customers and we are now extending that to all PowerOffice customers. This discount will end on January 23, 2009.

We hope that the New Year of 2009 will bring us all prosperity and well being. We thank all our customers for the support in the year 2008 and hope we will be able to provide you with good value for your hard earned money in the New Year.

Happy New Year

-- Arnor Baldvinsson

Why duplicate symbol error?

In Clarion 6.3 build 9058, Softvelocity added a bunch of new API function information to the WIN32.LIB and WININET.LIB library files. This caused a conflict with some other LIB files that included two shared function names, DLLInstall and DLLGetVersion.

There has been a fair amount of discussion about this, some confusion about who should fix this problem and even what exactly the problem is.

The problem

The problem, in a nutshell, is that two or more LIB files include the same function name and are both or all included into the same Clarion project or application. This results in the Clarion linker throwing a "Duplicate Symbol" error when it attempts to link in the second LIB file with the duplicate function name.

Can't we change the label and use NAME() to fix it?

No. That only takes care of issues with duplicate labels in Clarion. This is duplicate symbol which means that there are two libs that contain the same API function - in this case DLLGetVersion, DLLInstall.

This could be prototyped in two different places like this:

Module('IcetipsWhatever.lib')
  IT_DLLGetVersion  ...,NAME('DLLGetVersion')
  IT_DLLInstall     ...,NAME('DLLInstall')
END
MODULE('ABWHatever.Lib')
  AB_DLLGetVersion ...,NAME('DLLGetVersion')
  AB_DLLInstall    ...,NAME('DLLInstall')
END

This will give you two different (Clarion) labels for the functions, but they will still generate a "Duplicate Symbol" errors on IcetipsWhatever.Lib and ABWhatever.Lib which both include those two symbols. So this does not solve this particular problem. However it does solve the problem of possibly duplicate labels for the same (or different) API functions prototyped by different vendors.

This is kind of like the mail man trying to delive a letter to an address only to discover that there are two houses on the same street with the same number.

So, how CAN we fix it?

There are only two ways to fix this as far as I know.

  1. Find the offending LIB(s) and remove these two entries using LibMaker and then PLEASE report it to the producer of the LIB
  2. Dynamically load the DLLs and skip the LIBs altogether. This is what I use in our Iceitps Utilities for apis that are not included in the OLD Win32.lib and from now on I will use that as a base so anything that was not in the old win32.lib will be loaded dynamically. We also use this method in our Build Automator to load plugin dlls.

Finding the LIB files - what tools can we use?

The problem is finding the offending LIB files. Many search utilities won't search inside binary files. The version of the excellent Clarion Source Search that I have does not do it. I highly reccommend it for searching Clarion source though! The search in Total Commander DOES find it - one more reason to get that fantastic program!

I did find one freeware tool that does search binaries (or at least the Clarion LIB files!) without problems, called GrepWin. Very easy to use, supports both straight text search and regular expressions and it is FREE;

How do we fix the LIB files?

  1. Search for the DLLInstall or DLLGetVersion in your Clarion\3rdParty\LIB folder and any other LIB folders you can find.
  2. When you find the LIB, first MAKE A BACKUP of it in case you make a mistake and need to start over. Do not skip this step!
  3. Load the LIB file into the Clarion LibMaker (located in the Clarion\Bin folder - there should be a link in the Startup menu as well) and carefully locate the function name and select it in the list.
  4. Hit the Delete button to delete the function from the list
  5. Save the file back to the same LIB file.
  6. Repeat for the other function name.

Recompile your app to check if the error is gone. Repeat as necessary.

What about dynamically loading the functions?

While changing the LIB files can be done by the "end-user" developer, the dynamic loading has to be coded into the product or tool that makes use of the tool and is not reasonable for the end-user to deal with. In 2007 I posted an example application and classes that demonstrate how to do this. If you are interested in loading dlls dynamically at runtime, you can download this small, simple example and try it out yourself.

Hopefully this can help some people who are struggling with the "Duplicate symbol" error in Clarion 6.3 builds 9058 or 9059:)

-- Arnor Baldvinsson

3

What does "Elevated" mean?

One of the differences between Vista and XP is the User Account Control (UAC) in Vista. The UAC controls who has access to what folders and files. A normal user account in Vista does not have administrator privileges. Some access requires administrator privileges, such as writing to files in the Program Files folder, accessing certain control panel applications and write to certain CSIDL folders - see my last blog about where to put data under Vista. For that, Vista requires elevation to administrator privileges and will prompt the user to elevate. The elevation prompts the user for permission to use the software or requests an administrator login.

Require elevation

The elevation requirement is controlled from within the software by the vista manifest. The Vista manifest is an XML file, just like the XP manifest, but with some additional branches, most notably the trustinfo branch. Below is the Vista manifest that we use for our Build Automator It is generated with our AddVistaManifest extension template in our Icetips Utilities.

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly
   xmlns="urn:schemas-microsoft-com:asm.v1"
   manifestVersion="1.0">
<assemblyIdentity
    processorArchitecture="x86"
    version="1.0.0.0"
    type="win32"
    name="BuildAutomator.exe"/>
    <description>Build Automator</description>
    <dependency>
    <dependentAssembly>
    <assemblyIdentity
         type="win32"
         name="Microsoft.Windows.Common-Controls"
         version="6.0.0.0"
         publicKeyToken="6595b64144ccf1df"
         language="*"
         processorArchitecture="x86"/>
    </dependentAssembly>
    </dependency>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
    <security>
      <requestedPrivileges>
        <requestedExecutionLevel
          level="asInvoker"
          uiAccess="false"/>
        </requestedPrivileges>
       </security>
  </trustInfo>
</assembly>

The important part of the manifest is the RequestedExecutionLevel. The level attribute can have one of 3 possible settings:

  • requireAdministrator
  • asInvoker
  • highestAvailable

Normal programs should use asInvoker. Otherwise the program will prompt for elevation every time it is run and unless that is really required it should not be done. To force elevation of a program, the manifest should be set to requireAdministrator.

Running programs

In Clarion we have been able to use the RUN statement to run external programs without much problems. However, with Vista, a problem comes up if you want to run a program that either needs to be elevated by the program running it or the program to be run is using requireAdministrator. Either way it needs to be elevated.

Unfortunately RUN cannot handle this properly. The reason is that RUN uses the CreateProcess API internally and it cannot trigger the elevation process. If you try to use RUN to execute a program that requires administrator privileges is that nothing happens! This can cause support issues that are easily avoided.For that either ShellExecute or ShellExecuteEx must be used. In addition to that, if you want the calling program to wait for the called program you need to use WaitForSingleObject to force the process to wait.

Code sample

The following code sample is from our ITRun method in the ITShellClass of the Icetips Utilities. This is the main code that optionally elevates the program using the RunAs verb for ShellExecuteEx. It will also automatically trigger elevation if the called program uses requireAdministrator manifest.

    Verb = IT_SE_Open   !! Defaults to not elevated
    If Elevate
      If SELF.IsVista
        Verb = IT_SE_RunAs  !! Elevate to requireAdministrator
      End
    End
    !SELF.ODS('  Verb = ' & Verb)
    
    SHi.fMask                  =  IT_SEE_MASK_NOCLOSEPROCESS !!ULONG
    SHi.hwnd                   =  0{Prop:Handle}             !!IT_HWND       ! UNSIGNED
    SHi.lpVerb                 =  Address(Verb)              !!Long
    SHi.lpFile                 =  Address(cCmdLine)          !!Long
    SHi.lpParameters           =  Address(cParam)            !!Long
    SHi.lpDirectory            =  Address(P)                 !!Long
    SHi.nShow                  =  IT_SW_SHOWNORMAL           !!IT_int        ! SIGNED
    !SHi.hInstApp               =                            !!IT_HINSTANCE  ! UNSIGNED
    SHi.lpIDList               =  0                          !!IT_LPVOID     ! ULONG
    SHi.lpClass                =  0                          !!Long
    SHi.hkeyClass              =  0                          !!IT_HKEY       ! UNSIGNED
    SHi.dwHotKey               =  0                          !!IT_DWORD      ! ULONG
    SHi.DUMMYUNIONNAME         =  0                          !!Long          ! Pointer to union...
    !SHi.hProcess               =  !!IT_HANDLE     ! UNSIGNED
    SHi.cbSize                 =  Size(SHi) !!IT_DWORD       !! ULONG
    !SELF.ODS('  Before ShellExecEx')
    If Not SELF.ShellExecEx(SHi)
      hProc = 0
      SELF.ODS('  ShellExecEx failed in ITShellClass.ITRun.')
    Else
      hProc = Shi.hProcess
    End
    !SELF.ODS('  After ShellExecEx')
    If hProc
      If pWait
        RetVal = IT_WaitForSingleObject(hProc,-1)
        If IT_GetExitCodeProcess(hProc, lRetCode)
          RetValue = lRetCode
        Else
          RetValue = RetVal
        End
        RetVal = IT_CloseHandle(hProc)
      End
    End
    If Not cCmdLine &= NULL
      Dispose(cCmdLine)
    End

The WaitForSingleObject is called with a handle to the running process if you want the calling program to wait for the called program. The called program will wait and practically be completely dead until the called program is terminated. When that happens the next line of code uses GetExitCodeProcess to retrieve the exit code from the called program and places it into a variable that is returned from the ITRun method.

Running with the Icetips Utilities

With the Icetips Utilities it is very easy to implement the ITRun to make running programs under Vista a non-issue. First you need to add the Global Utilities extension to your application - also to the data dll, or exporting dll so the classes are included and compiled.

In your procedure data embed you add an instance of the ITShellClass:

ITS  ITShellClass

Now you are ready to use it in the procedure:

 Code
 ITS.ITRun('"C:\Program Files\Icetips Creative\' &|
           'Build Automator\BuildAutomator.exe"',True,'/E',,True)

That is all there is to it!

Running without...

To demonstrate this and show how you can do this easily, we have uploaded a small sample app written in Clarion 6.3. It uses some of the code in the Icetips Utilities methods to let you select a program and run it, with optional parameters and option to wait for the called program to terminate. It also has a button where you can use the standard Clarion RUN statement and observe the differences under vista. I would suggest that you try to run something that requires administrator privileges - most installers do - and see what happens when you use the RUN statement and when you use the ITRun procedure instead.

You can download the ITRun.zip from the Icetips website at http://www.icetips.com/downloadfile.php?FileID=89 Please note that this is a simple ZIP file. Unzip it to a folder and read the docs.txt file in it. Compile the application and run it and try out for yourself how it works.

We have used those methods to run elevated applications, for example Web Updates for Setup Builder installs, for several years without any problems. We hope this little app helps you to get your applications running under Vista.

Our Icetips Utilities mentioned here is a collection of classes and templates for Clarion developers. They are part of our Gold Subscription plan.

The Build Automator is a developer tool to automate compiling and building applications and installs. It works with many developer tools such as Visual Studio, Delphi/RAD Studio 2008, Clarion, SetupBuilder, Inno Setup, Setup Factor and MSI Factory.

Some Interesting Links:

UAC Elevation in Managed Code: Guidance for Implementing COM Elevation

We welcome and appreciate your comments on this entry:)

-- Arnor Baldvinsson