0

We are using Inno Setup (unicode version) to create resource package (or "samples") for our product. The program part of our product knows the location of the samples by a file that is written by samples installer. At current, it is implemented in plain way:

procedure CurStepChanged(CurStep: TSetupStep);
begin
  if ( CurStep = ssPostInstall) then
  begin
    ForceDirectories(ExpandConstant('{userappdata}\MyCompany\MyApp'))
    SaveStringToFile(ExpandConstant('{userappdata}\MyCompany\MyApp\SamplePath.txt'), ExpandConstant('{app}'), False);
  end;
end;

This plain way has a fatal issue: the installer is run in Chinese language Windows, and the whole stuff works in GBK encoding, but our product is built up on UTF8 base.

After some search, I got some solution by calling Windows WideCharToMultiByte inside Pascal code. However this won't work, as it requires UTF16 as input, but what I have is GBK.

In addition, the Inno Setup also won't work with existing UTF8 file name in my SamplePath.txt. If I manually edit the SamplePath.txt file to fill UTF8-encoded Chinese letters, and initialize the app builtin with following code, it displays messy characters in dir selection page:

[Setup]
DefaultDirName={code:GetPreviousSampleDir}

[code]
function GetPreviousSampleDir(Param: String): String;
var
    tmp: AnsiString;
begin
    if FileExists( ExpandConstant('{userappdata}\MyCompany\MyApp\SamplePath.txt') ) then
    begin
        LoadStringFromFile(ExpandConstant('{userappdata}\MyCompany\MyApp\SamplePath.txt'), tmp)
        Result := tmp
    end
    else
    begin
        Result := 'D:\MyApp_samples'
    end;
end;

So is there any way to load/store a file name with i18n characters in UTF8?

jiandingzhe
  • 1,881
  • 15
  • 35
  • Are you using Unicode or Ansi Inno Setup? – Martin Prikryl May 10 '19 at 06:15
  • @MartinPrikryl: Yes the Unicode version, I'm going to append this information to the question. – jiandingzhe May 10 '19 at 06:17
  • OK, so please explain what do you mean by *"whole stuff works in GBK encoding"* -- Where do you get GBK encoding? + Did you try `SaveStringsToUTF8File`? – Martin Prikryl May 10 '19 at 06:23
  • @MartinPrikryl `SaveStringsToUTF8File` will write with BOM that is not wanted. Also the load back part still has issue. – jiandingzhe May 10 '19 at 07:47
  • @MartinPrikryl If you don't use UTF8 calls, it will produce contents with GBK, and it can load back GBK-encoded file name and display it in dir selection page correctly. It seems the inner part of the Inno Setup runs with legacy local code page, as modern Windows works in UTF16. – jiandingzhe May 10 '19 at 07:50

1 Answers1

1

To load a string from UTF-8 file, use LoadStringFromFileInCP from
Inno Setup - Convert array of string to Unicode and back to ANSI

const
  CP_UTF8 = 65001;

{ ... }
var
  FileName: string;
  S: string;
begin
  FileName := 'test.txt';
  if not LoadStringFromFileInCP(FileName, S, CP_UTF8) then
  begin
    Log('Error reading the file');
  end
    else
  begin
    Log('Read: ' + S);
  end;
end;

To save UTF-8 file without BOM:

Martin Prikryl
  • 188,800
  • 56
  • 490
  • 992