views:

136

answers:

3

Hi all,

I'm trying to write some Romanian text into a RichEdit component (Delphi 7) , and even i set the Font Property - Charset to "EASTEUROPE_CHARSET" it doesn't work.

What i want to accomplish is to paste some text (in romanian) in a RichEdit, load into a StringList, set the property order to true and assign it to another RichEdit component (sort the list in a alphabetical order).

I know this shouldn't be a problem in Delphi2009 and up, but at this point I can work only with Delphi 7.

word examples : opoziţie, computerizată.

Any ideas?

Best regards,

+2  A: 

Check the language settings in Windows. If you are running English windows, try setting the "treat non-unicode programs as..." to Romanian. Or, run on native Romanian Windows. To run in a mixed environment (needing to show different charsets simultaneously), you'll likely need Unicode.

Chris Thornton
so, i haven't other solution than write the application on d2009 or 2010, so i can use Unicode...any other solution is welcomed...best regards,
Radu Barbu
Romanian versions of Windows are a rarity in Romania, and all of us Romanian programmer need to make our programs work on both Romanian copies of Windows as well as Enghlish copies. The problem is, we didn't have Windows 95 in Romanian. When XP got a Romanian version, it was only in the Pro edition, not the Home, and the Enghlish Pro was cheaper then Romanian Pro. Then there are the big OEM producers, they don't make versions of PCs for the Romanian market, so we get English preinstalled Windows most of the time. Not funny at all!
Cosmin Prund
+2  A: 

Try this code, it reads the text from RichEdit1 as UNICODE text, manually converts S and T + Comma to S and T + Cedilla and then uses WideCharToMultiByte to convert the text to code page 1250. The code point conversions need to be done because code page 1250 only encodes the cedilla-based versions of Ş and Ţ, while the new Romanian keyboards under Vista and Windows 7 generate the (correct) comma-based versions of Ş and Ţ!

procedure TForm1.Button1Click(Sender: TObject);
var GetTextStruct:GETTEXTEX;
    GetLenStruct:GETTEXTLENGTHEX;
    RequiredBytes:Integer;
    NumberOfWideChars:Integer;
    WideBuff:PWideChar;
    AnsiBuff:PChar;
    i:Integer;
begin
  ;

  // Get length of text
  GetLenStruct.flags := GTL_NUMBYTES or GTL_USECRLF or GTL_PRECISE;
  GetLenStruct.codepage := 1200; // request unicode
  RequiredBytes := SendMessage(RichEdit1.Handle, EM_GETTEXTLENGTHEX, Integer(@GetLenStruct), 0);

  // Prepare structure to get all text
  FillMemory(@GetTextStruct, SizeOf(GetTextStruct), 0);
  GetTextStruct.cb := SizeOf(GetTextStruct);
  GetTextStruct.flags := GT_USECRLF;
  GetTextStruct.codepage := 1200; // request unicode

  WideBuff := GetMemory(RequiredBytes);
  try
    // Do the actual request
    SendMessage(RichEdit1.Handle, EM_GETTEXTEX, Integer(@GetTextStruct), Integer(WideBuff));
    // Replace the "new" diactrics with the old (make Romanian text compatible with code page 1250)
    NumberOfWideChars := RequiredBytes div 2;
    for i:=0 to NumberOfWideChars-1 do
    case Ord(WideBuff[i]) of
      $0218: WideBuff[i] := WideChar($015E);
      $0219: WideBuff[i] := WideChar($015F);
      $021A: WideBuff[i] := WideChar($0162);
      $021B: WideBuff[i] := WideChar($0163);
    end;
    // Convert to code-page 1250
    RequiredBytes := WideCharToMultiByte(1250, 0, WideBuff, -1, nil, 0, nil, nil);
    AnsiBuff := GetMemory(RequiredBytes);
    try
      WideCharToMultiByte(1250, 0, WideBuff, -1, AnsiBuff, RequiredBytes, nil, nil);
      Memo1.Lines.Text := AnsiBuff; // AnsiBuff now contains the CRLF-terminated version of the
                                    // text in RichEdi1, corectly translated to code page 1250
    finally FreeMemory(AnsiBuff);
    end;
  finally FreeMemory(WideBuff);
  end;

end;

Then use something similar to turn AnsiString into UNICODE and push into the RichEdit. Of course, the only real solution is to switch to Delphi 2009 or Delphi 2010 and use Unicode all over.

Cosmin Prund
thank you Cosmin! +1
Radu Barbu
+1  A: 

i've resolved it with JvWideEditor from Jedi. Code is bellow

procedure TForm2.SortUnicode;
var asrt:TWStringList;
    i:Integer;
begin
 JvWideEditor1.Lines.Clear;
 JvWideEditor2.Lines.Clear;
 asrt:=TWStringList.Create;
 if OpenDialog1.Execute then
  begin
   wPath:=OpenDialog1.FileName;
   JvWideEditor1.Lines.LoadFromFile(wPath,[foUnicodeLB]);
   try
   asrt.AddStrings(JvWideEditor1.Lines);
   for i:=asrt.Count-1 downto 0 do 
    begin
      if Trim(asrt.Strings[i])='' then
       asrt.Delete(i);
    end;
   asrt.Duplicates:=dupAccept;
   asrt.CaseSensitive:=true;
   asrt.Sorted:=True;

   JvWideEditor2.Lines.AddStrings(asrt);
   JvWideEditor2.Lines.SaveToFile(GetCurrentDir+'\res.txt',[foUnicodeLB]);
   finally
    FreeAndNil(asrt);
   end;
  end;
end;
Radu Barbu
Also check out the TNT component set if you're stuck on D7. You REALLY should move to D2010 and be using full Unicode Strings.
Warren P