Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   GUI-Design mit VCL / FireMonkey / Common Controls (https://www.delphipraxis.net/18-gui-design-mit-vcl-firemonkey-common-controls/)
-   -   Delphi Realisierung von Mehrsprachigkeit (https://www.delphipraxis.net/82336-realisierung-von-mehrsprachigkeit.html)

xZise 11. Dez 2006 14:20


Realisierung von Mehrsprachigkeit
 
Da ich ein Freund von Programmen bin, welche Mehrsprachig sind, baue ich meist (für mich) zu statische Mehrsprachigkeitvisuallisierung ein.

Aber jetzt frage ich mich, wie man am Besten die mehrsprachigkeit Visuallisiert.
Okay ... Komplett vielleicht schwer umzusetzen, aber ich meine eigentlich die Komponenten (Edits, MainMenüs, Labels ...).

Ich habe es für mein Mainmenü so umgesetzt:
Delphi-Quellcode:
procedure TForm1.changeLanguage(fileName : string);
var
  i, j : Integer;
  ini : TIniFile;
begin

  ini := TIniFile.Create(fileName);
  try
    for i := 0 to mmMenu.Items.Count - 1 do begin
      mmMenu.Items[i].Caption := ini.ReadString(mmMenu.Items[i].Name, 'Name', mmMenu.Items[i].Caption);
      for j := 0 to mmMenu.Items[i].Count - 1 do
        mmMenu.Items[i].Items[j].Caption := ini.ReadString(mmMenu.Items[i].Name, mmMenu.Items[i].Items[j].Name, mmMenu.Items[i].Items[j].Caption);
    end;
  finally
    ini.Free;
  end;

end;
Aber was ist, wenn ich jetzt das für Edits realisieren will!
Weil Edits haben ja nicht die Eigenschaft "Caption" sondern "Text".
Wie würdet ihr das machen?
Ich hätte es so gemacht ("Grundriss"):
Ini-Datei (Sprachdatei)
Code:
[<Formularname>]
<KomponentenName>=<Übersetzung für die Komponente>
....
Delphi-Quellcode:
Form1.Component[i].<Text> := ini.ReadString(Form1.Name, Form1.Component[i].Name, '')

hoika 11. Dez 2006 14:29

Re: Realisierung von Mehrsprachigkeit
 
Hallo,

das gibt es schon als fertige Lösung (gettext)
siehe auch

http://dybdahl.dk/dxgettext/

Heiko

Khabarakh 11. Dez 2006 14:35

Re: Realisierung von Mehrsprachigkeit
 
Wenn du das Problem unbedingt zu Fuß lösen willst, würde ich die Übersetzungen nicht ganzen Controls zuordnen, sondern ihren jeweiligen Eigenschaften. Schließlich gibt es viele Fälle, in denen mehr als eine Eigenschaft lokalisiert werden muss.

xZise 11. Dez 2006 15:19

Re: Realisierung von Mehrsprachigkeit
 
Zitat:

Zitat von hoika
Hallo,

das gibt es schon als fertige Lösung (gettext)
siehe auch

http://dybdahl.dk/dxgettext/

Heiko

Habe ich es richtig gesehen, dasss es sich dabei um zu installierende Komponenten handelt?

OldGrumpy 11. Dez 2006 15:32

Re: Realisierung von Mehrsprachigkeit
 
Nein, was da installiert wird, ist das "Drumherum". Die eigentliche Übersetzung macht eine Unit die einfach ins Uses eingetragen wird. Texte holt man sich dann z.B. mit der Funktion _('Text') (ja, die Funktion heisst wirklich "Unterstrich"), Forms und ähnliches übersetzt man fast 100% automatisch mittels Aufruf von TranslateComponent(self) :) Der Windows-Installer bringt ausser den ganzen Tools, Sourcen und Dokumentation auch noch ne Explorer-Integration mit. Steht aber auch alles in der Dokumentation beschrieben, inkl. Schritt-für-Schritt-Tutorial zur ersten mehrsprachigen Exe :)

hoika 11. Dez 2006 15:57

Re: Realisierung von Mehrsprachigkeit
 
Hallo,

die Funktion heisst getText, aber für faule wurde die halt überladen (?)
und man kann _ benutzen.

;) :lol:


Heiko

kalmi01 11. Dez 2006 15:58

Re: Realisierung von Mehrsprachigkeit
 
Moin moin,

vielleicht ist das ja was für Dich ?

shmia 11. Dez 2006 17:05

Re: Realisierung von Mehrsprachigkeit
 
Ich würde übrigens gleich zu Actions und ActionLists greifen.
Dann müssen nur die [TAction].Caption übersetzt werden und die Menueitems und evtl. vorhandene Toolbuttons ändern sich gleich mit.

xZise 11. Dez 2006 17:38

Re: Realisierung von Mehrsprachigkeit
 
Zitat:

Zitat von OldGrumpy
Nein, was da installiert wird, ist das "Drumherum". Die eigentliche Übersetzung macht eine Unit die einfach ins Uses eingetragen wird. Texte holt man sich dann z.B. mit der Funktion _('Text') (ja, die Funktion heisst wirklich "Unterstrich"), Forms und ähnliches übersetzt man fast 100% automatisch mittels Aufruf von TranslateComponent(self) :) Der Windows-Installer bringt ausser den ganzen Tools, Sourcen und Dokumentation auch noch ne Explorer-Integration mit. Steht aber auch alles in der Dokumentation beschrieben, inkl. Schritt-für-Schritt-Tutorial zur ersten mehrsprachigen Exe :)

Zitat:

Zitat von kalmi01
Moin moin,

vielleicht ist das ja was für Dich ?

Ich besitzte Turbo Delphi Exporer ;) d.h. ich kann keine Fremdpackges installieren (was ja im 2. Fall 100% so ist (und im 1. scheint es auch so.)).

Aber ich guck mir mal den 1. Fall nochmal an.

PS: Ich weiß ;) Ich könnte es auch dynamisch erstellen, aber ich möchte iegtnlich nicht darauf verzichten.

TonyR 11. Dez 2006 17:55

Re: Realisierung von Mehrsprachigkeit
 
Hi xZise, ich wollte dich bloß mal kurz darauf aufmerksam machen, dass man Komponenten in TurboDelphi installieren kann!!!
Ich habe dazu schon mal einen Thread erstellt (Komponente in Turbo Delphi verwenden)

Und als bester Beitrag gilt der hier von Balu:
Zitat:

Im zweiten Teil wirst du fündig werden. http://www.danielstools.de/downloads/count.php?id=18

OldGrumpy 11. Dez 2006 19:58

Re: Realisierung von Mehrsprachigkeit
 
Zitat:

Zitat von xZise
Ich besitzte Turbo Delphi Exporer ;) d.h. ich kann keine Fremdpackges installieren (was ja im 2. Fall 100% so ist (und im 1. scheint es auch so.)).

Aber ich guck mir mal den 1. Fall nochmal an.

PS: Ich weiß ;) Ich könnte es auch dynamisch erstellen, aber ich möchte iegtnlich nicht darauf verzichten.

Red ich eigentlich Kisuaheli oder sowas? Da ist keine Komponente zu installieren, zefixnochamol :mrgreen:

xZise 11. Dez 2006 20:07

Re: Realisierung von Mehrsprachigkeit
 
Ach das wolltest du sagen Grumpy ;)

Ne im ernst ;) Ich habe zuerst befürtchtet, ich müsse eine Kombosammlung installieren. Sry, aber es scheint zu gehen.
Ich muss nur mal damit klarkommen ;) weil z.Zt. stört mich der Pfad ein wenig :D

PS: thx wegen den Third-Party-Komponeten :stupid:

OldGrumpy 11. Dez 2006 20:47

Re: Realisierung von Mehrsprachigkeit
 
Der Pfad ist ja praktisch nur während der Entwicklung relevant, du kannst die Übersetzungen später in die Exe einbetten und fertig. Eine Exe, alle Sprachen - automatisch oder auf Knopfdruck.

xZise 11. Dez 2006 20:58

Re: Realisierung von Mehrsprachigkeit
 
Zitat:

Zitat von OldGrumpy
Der Pfad ist ja praktisch nur während der Entwicklung relevant, du kannst die Übersetzungen später in die Exe einbetten und fertig. Eine Exe, alle Sprachen - automatisch oder auf Knopfdruck.

Geschieht dies automatisch? Oder muss ich das über Ressourcen erledigen.

OldGrumpy 11. Dez 2006 21:01

Re: Realisierung von Mehrsprachigkeit
 
Unter Windows dank Explorer-Integration nur ein Rechtsklick auf die Exe und Auswahl des Menüpunktes "Embed translations". Geht natuerlich auch kommandozeilenbasiert über das entsprechende Tool im dxgettext-Paket. Steht alles im Handbuch.

xZise 12. Dez 2006 15:17

Re: Realisierung von Mehrsprachigkeit
 
Ok... Nun habe ich ein ganz anderes Problem. Ich meine es soweit zu verstanden zu haben, aber...
Ich kann keine po-Datei erstellen (mit poEdit), und ich kann die auch nicht mit "msginit.exe" weil "name.pot" fehlt :(

PS: poEdit-Fehlermsg:
Zitat:

---------------------------
Poedit Fehler
---------------------------
poEdit hat keine Dateien in den verarbeiteten Verzeichnissen gefunden.
---------------------------
OK
---------------------------
(Also mir sagt die Msg nichts)

OldGrumpy 12. Dez 2006 19:27

Re: Realisierung von Mehrsprachigkeit
 
Zuerstmal musst Du im Explorer einen Rechtsklick auf Dein Projektverzeichnis machen und den Punkt "Extract translations to template" anwählen. Die Optionen dann noch richtig einstellen (wie, hängt von Deinen Projekteinstellungen und auch nen bissl vom Geschmack ab) und dann die erzeugte Datei in den passenden Pfad speichern. Also mit locale usw. - Dieses File öffnest Du dann mit poEdit und bearbeitest die Texte da drin.

Bevor Du das File dann speichern kannst, musst Du in poEdit im Menü unter Catalog, Settings die Standardwerte für das Translationfile (also Dummywerte) mit den korrekten Infos überschreiben. Das ist ein Sicherheitsmechanismus damit man nicht mehrere Übersetzungsdateien durcheinanderwerfen kann. Entgegen der Dokumentation erstellt poEdit übrigens mit den Standardeinstellungen das zugehörige *.mo automatisch.

Nun kannst Du die Exe starten (die übersetzten Texte sollten nun automatisch erscheinen sofern Du nach Handbuch vorgegangen bist) zum Testen. Wenn alle Texte sitzen, kannst Du mit Rechtsklick auf die Exe die Texte in die Exe einbetten.

Ich gebe zu, die ersten Schritte mit dxgettext sind etwas holperig, wenn man aber erstmal eine gewisse Routine entwickelt hat, geht einem das sehr einfach von der Hand, zumal ja die meisten Sachen automatisch gehen.
Delphi-Quellcode:
Form.Caption:=_('Text');
ist fast so schnell geschrieben wie
Delphi-Quellcode:
Form.Caption:='Text';
und alle grafischen Komponenten lassen sich bis auf wenige Ausnahmen (auch hier siehe Handbuch) ja mit TranslateComponent(self) mit einem Handschlag lokalisieren.

xZise 12. Dez 2006 22:03

Re: Realisierung von Mehrsprachigkeit
 
Wow!
Das ist ja ein heftiges Teil :P

Nur habe ich jetzt ein richtig dummes Problem mit den .po-Dateien :(

Ich krieg da nicht neue Einträge hinzu (z.B. für Messages) :(

OldGrumpy 13. Dez 2006 01:17

Re: Realisierung von Mehrsprachigkeit
 
Die neuen Einträge erzeugst Du ja schon allein dadurch, dass Du im Programm eine entsprechende Referenz anbringst. Du musst danach nur erneut die Translations extrahieren und die beiden po-Files mergen. Das steht aber auch alles im Handbuch und im Tutorial :)

Kleines Beispiel:

Alte Programmversion:

Delphi-Quellcode:
Form1.Caption:=_('Erster Text');
Wenn Du hierfür die Übersetzungen extrahierst, hast Du einen Eintrag im po-File. Wenn nun noch Code dazukommt:

Delphi-Quellcode:
Form1.Caption:=_('Erster Text');
Form2.Caption:=_('Zweiter Text');
...musst Du erneut die Übersetzungen extrahieren, dabei kommt ein po-File mit zwei Texten heraus. Die bereits existierende Übersetzung für den ersten Text kannst Du jetzt mit dem Mergetool in das neue po-File übernehmen. Die Syntax suchst Du Dir jetzt aber bitte selber raus, ist schon spät :)

Nach dem gleichen Muster gehst Du auch vor, wenn sich ein Text ändert. Die restlichen Texte musst Du nicht auch noch neu übersetzen, sondern kannst einfach die beiden Übersetzungen mergen, und nur die neuen Texte müssen übersetzt werden.

xZise 13. Dez 2006 14:23

Re: Realisierung von Mehrsprachigkeit
 
Also das dies hinzugefügt wird ist gut soweit...
NUR... Erkennt er keine TTreeViews ;) Und dementsprechend keine Einträge darin...
Werde es wohl "Hardcore" machen müssen (also .po mit Editor öffnen und selber hinzufügen)...

Und wehe es gibt eine Möglichkeit Einträge hinzuzufügen, und die stehen in dem HB :P

PS: Handbuch = Docs?

OldGrumpy 13. Dez 2006 17:32

Re: Realisierung von Mehrsprachigkeit
 
Handbuch, Manual, Docs... alles das gleiche in Grün. Zeig mal bitte nen Codebeispiel für die TTreeView die er nicht erkennt. Das wundert mich jetzt nämlich doch sehr. Einträge zum po-File hinzufügen bringt nämlich genau NULL. Denn der Inhalt des po-Files wird ja nicht einfach gelesen und irgendwo drübergezogen, sondern nur benutzt, um die Texte die der _()-Funktion übergeben werden, sowie die Texte die TranslateComponent(self) findet, zu übersetzen. Wenn beim Extrahieren Komponenten nicht gefunden werden, bedeutet das im Umkehrschluss dann aber auch, dass die Übersetzungen selbst wenn sie vorhanden sind, nicht angezogen werden (werden?). Wenn Du die TreeViews dynamisch erzeugst, also Texte erst zur Laufzeit reinschreibst, dann musst Du halt überall _() drum rum schreiben. Bei statisch vorhandenen TreeViews müssten aber eigentlich alle per OI eingetragenen Texte erkannt und extrahiert werden. Vielleicht fehlt nur ein TranslateComponent()-Aufruf an der richtigen Stelle? Troubleshooting gibts im Online Manual übrigens auch... Aber wie gesagt, stell mal Codebeispiel hin, dann kann man da mehr sagen.

xZise 13. Dez 2006 17:41

Re: Realisierung von Mehrsprachigkeit
 
1. Statisch (also nicht dynamisch)
2. Alle Werte vordefiniert
3. = Codebeispiel ist schlecht (außer die .dfm?)

Vielleicht, guckst du dir das mal an: Editor

OldGrumpy 13. Dez 2006 17:54

Re: Realisierung von Mehrsprachigkeit
 
Ja, pack doch .pas und .dfm als attachment (bitte gepackt) hier rein. Mir gehts darum, dass ich mir das mal hier selber anschauen kann.

Edit: Hab da gerade was gefunden (google...), allerdings muss ich erstmal schauen zu welcher Version das gehört:
Zitat:

Zitat von Google-Suchergebnis
Some components, like treeviews and listviews, have item list properties that you need to handle manually by adding your own procedure to explicitly iterate over the list and use _() to translate them. For a treeview, here's the code I added to my base form: type THackTreeView = class(TCustomTreView); procedure TfrmGnuGT.HandleTreeView(Obj: TObject); var N:TTreeNode;T:THackTreeView; begin T := THackTreeView(Obj); N := T.Items.GetFirstNode; while N <> nil do begin N.Text := _(N.Text); N := N.GetNext; end; end; I also had to tell dxgettext that I want to handle treeview translations myself, so I added a call to TP_GlobalHandleClass in AfterConstruction: TP_GlobalHandleClass(TCustomTreeView,HandleTreeVie w); I also added similar handlers for listviews and the KWizard.

Jetzt wo ich drüber nachdenke kommt mir auch in den Sinn dass alle meine Treeviews dynamisch gefüllt werden, daher ist mir wohl das Problem noch nie aufgefallen. :)

Zweiter Edit: Hier ist noch ein Hinweise darauf, dass es am Verhalten der TTreeView liegt, und wie das zu umgehen ist: TreeView und andere Samples

Hoffe, das hilft Dir weiter :)
Da ich eigentlich aus der Ecke von C/C++ komme, fülle ich meine Controls meist eh dynamisch mit Inhalten, alte Angewohnheit ;) Daher ist mir das bisher noch gar nicht aufgefallen :)

xZise 29. Dez 2006 14:38

Re: Realisierung von Mehrsprachigkeit
 
So... Ich bin wieder dahin gekommen :P
Nun habe ich aber ein ziemlich Problematisches Problem (lol)...

Und zwar habe ich ein Label mit der Caption "Items (X)" wobei X sich während der Runtime ändert.
Wie kriege ich es jetzt hin, dass er mir es trotzdem brav übersetzt?

jbg 29. Dez 2006 15:37

Re: Realisierung von Mehrsprachigkeit
 
Das geht mit
Delphi-Quellcode:
Format(_('Items (%d)'), [Items.Count]);

OldGrumpy 29. Dez 2006 15:42

Re: Realisierung von Mehrsprachigkeit
 
Oh, da war jemand schneller :)

Der grundlegende Trick ist halt, Platzhalter zu verwenden und seine Strings die variable Anteile enthalten können mittels der Format-Funktion zusammenzubauen. Ausser %d für Integer gibts auch noch eine Reihe weitere Platzhalter, dazu steht aber auch einiges in der Delphi-Hilfe. Bei mir ists fast immer %s (für nen String) oder %d (für nen Integerwert), Fließkommazahlen und Werte in anderen Zahlensystemen kann man aber auch benutzen.

xZise 29. Dez 2006 20:42

Re: Realisierung von Mehrsprachigkeit
 
Okay... Funktioniert soweit ;)

Außer dass er sich wehement dagegen aufbringt mir "Items (%d)" zu übersetzen!

Andere Strings mit "%d" funktionieren (Stichprobe)...

Gabs da einen Bug mit Zahlen die in () sind?


Alle Zeitangaben in WEZ +1. Es ist jetzt 11:23 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz