Einzelnen Beitrag anzeigen

taaktaak

Registriert seit: 25. Okt 2007
Ort: Radbruch
1.993 Beiträge
 
Delphi 7 Professional
 
#10

Re: TRichEdit - CFM_Link : nach SaveToFile ist alles futsch

  Alt 2. Nov 2007, 09:15
Moin, Moin.

Hmmm, mit dem Optimieren ist das so eine Sache.

1. Das Speichern ist nicht so kritisch, da der Anwender hier keine so hohe Anforderung hat, sofort eine optische Rückmeldung zu erhalten.

2. Anders beim Laden aus der Datei, nach Auswahl des Textes in einer Auswahlliste sollte das RichEdit (im Optimalfall) praktisch sofort gefüllt sein - leider bremst die Prüfung auf vorhande Revised-Attribute im Text den Ladevorgang enorm aus (Ladezeit für etwa 13000 Zeichen langen Text auf einem Notebook: über 3 Sekunden).

Habe nun die für den Ladevorgang zuständigen Routinen verbessert:

Delphi-Quellcode:
  function IsRevised(re:TRichEdit;Position:Integer):Boolean;
  var NewRange : TCharRange;
  begin
    NewRange.cpMin:=Position;
    NewRange.cpMax:=Position+1;
    SendMessage(re.Handle,EM_ExSetSel,0,LParam(@NewRange));
    SendMessage(re.Handle,EM_GetCharFormat,SCF_Selection,LParam(@CF2Get));
    Result:=CF2Get.dwEffects and CFE_Revised=CFE_Revised;
  end;

  procedure SetLink(re:TRichEdit;Position:Integer);
  var NewRange : TCharRange;
  begin
    NewRange.cpMin:=Position;
    NewRange.cpMax:=Position+1;
    SendMessage(re.Handle,EM_ExSetSel,0,LParam(@NewRange));
    SendMessage(re.Handle,EM_SetCharFormat,SCF_Selection,LParam(@CF2Set));
  end;
Gegenüber der Ursprungsversion sind die Initialisierungen 'raus (muss ja nicht 13.000x initialisiert werden). Ebenso Save/Restore der SelPosition. Die eigentliche Ladeprozendur sieht dann beispielhaft folgendermassen aus (im Original abweichend, nur um das Schema zu demonstrieren):

Delphi-Quellcode:
procedure Load(var RE:TRichEdit;FName:String);
var i : Integer;
    CF2Get,
    CF2Set : TCharFormat2;
  
  FillChar(CF2Get,SizeOf(CF2Get),0);
  CF2Get.cbSize:=SizeOf(CF2Get);
  CF2Get.dwMask:=CFM_Revised;

  FillChar(CF2Set,SizeOf(CF2Set),0);
  CF2Set.cbSize :=SizeOf(CF2Set);
  CF2Set.dwMask :=CFM_Link;
  CF2Set.dwEffects:=CFE_Link;
  
  RE.Lines.BeginUpdate;
  RE.Lines.LoadFromFile(FName);

  for i:=0 to length(RE.Text)-1 do // konvertiere Revised-Attribut
    if IsRevised(RE,i) then SetLink(RE,i); // zurück in Link-Attribut

  RE.Lines.EndUpdate;

  // ...
end;
"Rumbasteln" an der FOR-Schleife, die den RichEdit-Text prüft und ggf. das Attribut konvertiert, brachten bisher leider NUR Geschwindigkeitsnachteile (z.B. wortweise weiter, wenn am Anfang des Textes kein Attribut gefunden).

Die Ladezeit konnte nun auf etwas über 2 Sekunden reduziert werden - ist aber immer noch zu lang. Hat jemand eine Idee?

Gruß Ralph

PS : Muss jetzt mal was für die Firma tun und bin erst mal nicht am PC
Ralph
  Mit Zitat antworten Zitat