![]() |
Problem mir StringResourcen...
Ich habe in meinem Hauptprogramm und in div. Sprach-dll's Stringresourcen untergebracht und gebe dem User die Möglichkeit über eine Exportfunktion die aktuellen Sprachresourcen zu exportieren und da fangen meine Probleme an...
Das schreiben der rc an sich ist kein Problem, ich schreibe die Werte mit einer Schleife in die entspr. Datei, dabei durchlaufe ich einfach alle Werte von 0 bis... und das weiß ich eben nie genau :roll: ... Bisher muß ich die bettr. Scheife nach jeder Resourcenanpassung von Hand anopassen, dass nun auch die neuen Texte berücksichtigt werden :? Kann man irgendwie herausfinden, ob eine Textresource mit einem bestimmten Index vorhanden ist? |
Re: Problem mir StringResourcen...
Ich hab jetzt mal eine Funktion geschrieben, die mir eigentlich den höchsten Index liefern sollte...
Delphi-Quellcode:
Diese Funktion tut es allerdings nicht, weil GetLastError offensichtlich sehr unzuverlässig ist :evil: :roll:
function GetMaxResID: integer;
var Buffer: array[0..MAX_PATH] of Char; n: integer; begin for n := 0 to 9999 do begin if Loadstring(hinstance, n, @buffer, MAX_PATH) = 0 then begin if GetLastError <> ERROR_SUCCESS then break else Result := n; end else Result := n; end; end; Die Funktion liefert mir bei realen 163 Strings "abwechselnd" (unregelmäßig) 162 (korrekt) und 175 :gruebel: |
Re: Problem mir StringResourcen...
:shock: ... warum benutzt du nicht:
![]() |
Re: Problem mir StringResourcen...
Zitat:
|
Re: Problem mir StringResourcen...
Sicher?
Zitat:
|
Re: Problem mir StringResourcen...
Sicher!
Codeauszug
Delphi-Quellcode:
EnumResourceNamesProc wird bei mir ganze 38 mal aufgerufen, obwohl allein meine eigenen Stringresourcen schon 162 Durchläufe auslösen sollten :gruebel: ...
function GetMaxResID: integer;
function EnumResourceNamesProc(Module: HMODULE; ResType: PChar; ResID: Integer; lParam: TStringList): Integer; stdcall; function Fill(Wert: string): string; begin Result := Wert; while Length(Result) < 6 do Result := '0' + Result; end; var ResourceName: string; begin lParam.Add(Fill(IntToStr(lParam.Count)) + '-' + Fill(IntToStr(ResID))); Result := 1; end; var Buffer: array[0..MAX_PATH] of Char; n: integer; MyList: TStringList; begin n := 0; MyList := TStringList.Create; MyList.Sorted := True; windows.EnumResourceNames(hinstance, RT_STRING, @EnumResourceNamesProc, Integer(MyList)); for n := 0 to MyList.Count - 1 do showmessage(MyList[n]); |
Re: Problem mir StringResourcen...
Moin FriFra,
eine Stringresource kann bis zu 16 Strings umfassen. Dadurch erklärt sich wohl die Differenz. [EDIT] Und ich hab' sogar den Link zu meinem alten Thread wiedergefunden: ![]() [/EDIT] |
Re: Problem mir StringResourcen...
Diesen Tread hatte ich auch schon gelesen und auch umgesetzt... Das Problem habe ich trotzdem noch.
Selbst wenn ich mit EnumResourceNames alle Resourcen ermittle und versuche jede "Teilresource" zu laden um bei einem möglichen Fehler (nicht vorhanden) abzubrechen liefert mir GetLastError trotz definitiv nicht vorhandener ID ein ERROR_SUCCESS, deshalb komme ich auch so auf 175 statt 163 :roll: Testcode:
Delphi-Quellcode:
Wobei es effektiv völlig egal wäre, ob ich mit EnumResourceNames arbeite oder einfach nur "blind" versuchen würde alle Strings mit den IDs von 0 - 9999 zu laden... würde GetLastError funktionieren, tut es aber nicht, deshalb liefern beide Versionen ein falsches Ergebnis, wobei die vorherige Version bei mir wenigstens sporadisch das richtige Ergebnis lieferte :roll:
function GetMaxResID: integer;
function EnumResourceNamesProc(Module: HMODULE; ResType: PChar; ResID: Integer; lParam: TStringList): Integer; stdcall; function Fill(Wert: string): string; begin Result := Wert; while Length(Result) < 6 do Result := '0' + Result; end; var i: integer; Buffer: array[0..MAX_PATH] of Char; begin for i := (ResID - 1) * 16 to ResID * 16 do begin if LoadString(hinstance, i, @buffer, MAX_PATH) = 0 then begin if GetLastError <> ERROR_SUCCESS then break; end; lParam.Add(Fill(IntToStr(i { + ((ResId - 1) * 16)}))) end; Result := 1; end; var Buffer: array[0..MAX_PATH] of Char; n: integer; MyList: TStringList; begin n := 0; MyList := TStringList.Create; MyList.Sorted := True; windows.EnumResourceNames(hinstance, RT_STRING, @EnumResourceNamesProc, Integer(MyList)); if (MyList.Count > 0) and (StrToIntDef(MyList[0], -1) = 0) then begin Result := 0; for n := 1 to MyList.Count - 1 do begin if StrToIntDef(MyList[n], -1) = StrToIntDef(MyList[n - 1], -1) + 1 then Result := n else break; end; end else Result := 0; MyList.Free; end; |
Re: Problem mir StringResourcen...
Hallo FriFra,
funktioniert das bei dir?
Delphi-Quellcode:
D7 kam übrigens mit einer Demo für einen Resource Explorer - vielleicht gibt es den auch noch unter D2005?
// funktioniert nur bei fortlaufender ID
function GetMaxStringID(start: integer): integer; begin Result := start; while SysUtils.LoadStr(Result) <> '' do Inc(Result); if Result = start then Result := -1 else Result := Result - 1; end; Grüße vom marabu |
Re: Problem mir StringResourcen...
Das ist keine Lösung, da es auch gültige Stringresourcen geben kann die einen leeren String enthalten ;) und da wäre dann frühzeitig schluß :? ...
P.S.: Die "leeren" strings kommen ganz einfach zu stande, wenn in z.B: ein Control aus meinem Programm entferne und ich die Caption/den Text vorerst nicht mehr benötige, dann mache ich diesen Text leer, um ihn bei der nächsten Gelegenheit für etwas anderes zu nutzen (wäre er nicht leer, würde ich den Überblick verlieren). |
Alle Zeitangaben in WEZ +1. Es ist jetzt 00:58 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz