Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Wie Caretposition in RichEdit setzen? (https://www.delphipraxis.net/52236-wie-caretposition-richedit-setzen.html)

Armageddon 25. Aug 2005 20:45


Wie Caretposition in RichEdit setzen?
 
Hallo,

habe mit folgendem Code aus einem fremden RichEdit die Caretposition herausbekommen:

Delphi-Quellcode:
//RichEdit1 füllen
//Caretposition vom ersten Fenster speichern
  SendMessage(StrToInt(Fenster1_Handle), EM_GETSEL, wParam(@lCol), 0);
  lLine := SendMessage(StrToInt(Fenster1_Handle), EM_LINEFROMCHAR, lCol, 0);
  lCol := lCol - SendMessage(StrToInt(Fenster1_Handle), EM_LINEINDEX, -1, 0);
//Inhalt des ersten Fensters kopieren
  SendMessage(StrToInt(Fenster1_Handle), EM_SETSEL, 0, -1);
  SendMessage(StrToInt(Fenster1_Handle), WM_COPY, 0, 0);
  SendMessage(StrToInt(Fenster1_Handle), EM_SETSEL, 0, 0);
  RichEdit1.ReadOnly := False;
  RichEdit1.PasteFromClipboard;
  RichEdit1.ReadOnly := True;
So weit so gut. Nun habe ich ja zum Schluß den Text den ich kopiert habe in meinem RichEdit eingefügt. Möchte nun aber in meinem RichEdit den Caret genau an die gleiche Position setzen wie er in dem fremden RichEdit vor dem kopieren war. Ebenfalls möchte ich den Caret des fremden RichEdit wieder an seine ursprüngliche Position setzen. Wie kann ich die beiden Werte für die Linie und die Spalte für mein Vorhaben verwenden?

Gruß Markus

r2c2 25. Aug 2005 21:22

Re: Wie Caretposition in RichEdit setzen?
 
Delphi-Referenz durchsuchenTRichEdot.CaretPos

Falls es das noch nicht geben sollte:

Delphi-Referenz durchsuchenTRichEdit.SelStart

//Nachtrag: Warum machst du das ganze so umständlich? CaretPos tuts doch auch. Außerdem: Warum nimmst du die Zwischenablage? Der User wirds dir danken, wenn sein Clipboard-Inhalt weg is. Besser:
Delphi-Quellcode:
RichEdit2.Lines.Assign(RichEdit1.Lines);
mfg

Christian

Armageddon 26. Aug 2005 00:52

Re: Wie Caretposition in RichEdit setzen?
 
Zufälliger Weise ist der Text in einem RichEdit einer Fremden Anwendung und das geht soviel ich weiß nur über das Handle mittels SendMessage oder hab ich da was falsch verstanden?

r2c2 26. Aug 2005 08:26

Re: Wie Caretposition in RichEdit setzen?
 
Zitat:

Zitat von Armageddon
Zufälliger Weise ist der Text in einem RichEdit einer Fremden Anwendung und das geht soviel ich weiß nur über das Handle mittels SendMessage oder hab ich da was falsch verstanden?

Sorry, dann hab ich dich falsch verstanden. Den Text bekommt man aber AFAIK auch ohne das Clipdoard und zwar über GetText oder so ähnlich. Wie das mit dem Caret dann aussieht, hab ich dann leider auch keine Ahnung. Ich hätte deinen Post wohl besser lesen sollen. Mist! PISA hat doch Recht...

mfg

Christian

P.S.: Alle Angaben sind wie immer ohne Gewähr...

Luckie 26. Aug 2005 08:53

Re: Wie Caretposition in RichEdit setzen?
 
Zitat:

Zitat von Armageddon
Zufälliger Weise ist der Text in einem RichEdit einer Fremden Anwendung und das geht soviel ich weiß nur über das Handle mittels SendMessage oder hab ich da was falsch verstanden?

Jupp, aber kein Grund die Zwischenablage zu benutzen, mit WM_GETTEXT bekommst du den Inhalt des RichEdits.

xaromz 26. Aug 2005 08:56

Re: Wie Caretposition in RichEdit setzen?
 
Hallo,

warum setzt Du nicht mit
Delphi-Quellcode:
SendMessage(Handle, EM_SETSEL, Alte_Position, Alte_Position);
Dein Caret zurück?

Gruß
xaromz

Armageddon 26. Aug 2005 13:37

Re: Wie Caretposition in RichEdit setzen?
 
Hi allerseits,

@r2c2: Kein Problem ist mir auch schon des öfteren passiert. :)

@Luckie: Hmmm das muß ich mal ausprobieren. Ich hoffe ich bekomme so auch die Formatierungen wie Schriftfarbe usw. auch mitgeliefert. :gruebel:

@xaromz: Danke für den Tipp. Da bin ich Heute Mittag als ich mal nicht viel zu tun hatte beim Arbeiten durch herumprobieren auch draufgekommen. Trotzdem Danke.

Jetzt fehlt nur noch das der RichEdit-Inhalt des fremden RichEdit nach dem markieren und Kopieren wieder an genau die gleiche Stelle gescrollt wird so das nicht auffällt das jemals was passiert ist. Daran happert es bis jetzt noch. Hat evtl. jemand da noch nen Tipp?

Luckie 26. Aug 2005 13:38

Re: Wie Caretposition in RichEdit setzen?
 
nein, da musst du über den Stream gehen. Code dazu hat Nico hier im Forum schon mal gepostet.

Flocke 26. Aug 2005 13:46

Re: Wie Caretposition in RichEdit setzen?
 
Suche mal nach EM_STREAMIN bzw. EM_STREAMOUT hier im Forum. Darüber kommst du an den Inhalt des Richedit ohne die Markierung oder die Zwischenablage zu verändern.

Armageddon 27. Aug 2005 19:52

Re: Wie Caretposition in RichEdit setzen?
 
Das mit dem Stream wäre natürlich die beste Lösung. Habe mir auch schon einige Programmcodes dazu angesehen aber komme damit einfach nicht klar. Auch beim Swissdelphicenter hab ich schon geschaut und was ausprobiert aber außer ein dutzend Fehlermeldungen geht da auch nix. Es kann doch nicht so schwer sein den kompletten Inhalt heraus zu streamen. Oder etwa doch? Kann mir da jemand mal nen kleinen Beispielcode geben?

@Lucky: Wenn ich nach dem Namen Nico suche finde ich leider nix. Bin leider nicht so oft hier das ich auf anhieb weiß wen Du damit genau meinst. :?

xaromz 27. Aug 2005 22:39

Re: Wie Caretposition in RichEdit setzen?
 
Hallo,

hier mal meine Routinen:
Delphi-Quellcode:
type
  TBufferClass = class(TObject)
    Buffer: AnsiString;
    Position: Integer;
  end;

function StringSave(dwCookie: LongInt; pbBuff: PByte;
  cb: LongInt; var pcb: LongInt): LongInt; stdcall;
var
  S: PString;
begin
  Result := NoError;

  S := PAnsiString(dwCookie);
  try
    S^ := S^ + PChar(pbBuff);
    pcb := cb;
  except
    Result := $0002; // WriteError
  end;
end;

function StringLoad(dwCookie: LongInt; pbBuff: PByte;
  cb: LongInt; var pcb: LongInt): LongInt; stdcall;
var
  BC: TBufferClass;
  S: PAnsiString;
begin
  Result := NoError;

  BC := TBufferClass(dwCookie);

  try
    pcb := 0;
    try
      pcb := cb;
      if pcb > Length(BC.Buffer) - BC.Position then
        pcb := Length(BC.Buffer) - BC.Position;

      if pcb > 0 then
      begin
        S := PAnsiString(BC.Buffer);
        Inc(S, BC.Position);

        Move(S^, pbBuff^, pcb);
        BC.Position := BC.Position + pcb;
      end;
    except
      Result := $0003; // ReadError
    end;
  finally
  end;
end;

procedure LoadRichEditFromString(Handle: THandle; S: AnsiString);
var
  EditStream: TEditStream;
  BC: TBufferClass;
begin
  BC := nil;
  try
    BC := TBufferClass.Create;
    BC.Buffer := S;
    BC.Position := 0;
    with EditStream do
    begin
      dwCookie := Integer(BC);
      pfnCallBack := @StringLoad;
      dwError := 0;
    end;
    SendMessage(Handle, EM_STREAMIN, SF_RTF, Longint(@EditStream));
  finally
    BC.Free;
  end;
end;

function SaveRichEditToString(Handle: THandle): AnsiString;
var
  EditStream: TEditStream;
  S: AnsiString;
begin
  try
    with EditStream do
    begin
      dwCookie := Integer(@S);
      pfnCallBack := @StringSave;
      dwError := 0;
    end;

    SendMessage(Handle, EM_STREAMOUT, SF_RTF, Longint(@EditStream));
  finally
    Result := S;
  end;
end;
Wichtig sind nur die beiden Routinen am Ende. Diese lesen bzw. schreiben den kompletten Inhalt eines RichEdits,

Gruß
xaromz

Armageddon 27. Aug 2005 23:22

Re: Wie Caretposition in RichEdit setzen?
 
Liste der Anhänge anzeigen (Anzahl: 4)
Danke xaromz,

aber irgendwie bin ich entweder zu blöd oder ich weiß auch nicht an was es liegt. :wall:
Egal welches Beispiel das ich bisher gefunden habe benutze, ich bekomme immer Zugriffsverletzungen sobald es ein RichEdit ist das in einer fremden Anwendung läuft. Ich weiß das es ein RichEdit ist welches in der fremden Anwendung ist, ich weiß das Handle und ich weiß daß das Programm welches das fremde RichEdit enthält mit Delphi programmiert wurde. Das müßte doch reichen verflixt noch eins. Habe mal ein paar Screenshots angehängt.

Hoffe es weiß jemand Rat.

Flocke 29. Aug 2005 10:00

Re: Wie Caretposition in RichEdit setzen?
 
Es könnte daran liegen, dass der Prozess, dem das RichEdit gehört, einen anderen Adressraum hat. Hast du mal einen Breakpoint in "StringSave" gesetzt und geschaut was dort passiert?

Armageddon 29. Aug 2005 15:26

Re: Wie Caretposition in RichEdit setzen?
 
Ohje jetzt scheint es kompliziert zu werden. Ich kann mir zwar Vorstellen was Du meinst aber ich weiß beim besten Willen nicht wie ich das anstellen soll. Das komische ist das dies auch passiert wenn ich ein leeres form nehme darauf ein RichEdit platziere dieses kompilieren lasse. Dann starte etwas reinschreibe, das Handle mit dem WinSpy herausfinde. Und schließlich versuche es miot meiner Anwwendung die das ja können soll, heraus zu streamen. Pling, plong, Außnahmefehler ohne Ende ist das Ergebnis. Es ist zum Heulen.

:wall:

Flocke 29. Aug 2005 15:33

Re: Wie Caretposition in RichEdit setzen?
 
Wenn meine Vermutung stimmt, dann kann das RichEdit der fremden Anwendung ja noch nicht einmal etwas mit dem Inhalt der EditStream-Struktur anfangen.

Ich habe mehrere Lösungsansätze vor Auge (VirtualAllocEx im fremden Adressraum, Pipes), aber die sind alle alles andere als einfach.

[Nachtrag]

Wahrscheinlich ist von der Komplexität her dein erster Ansatz über die Zwischenablage wirklich der einfachste... auch wenn es für den User unangenehm ist, dass der Inhalt der Zwischenablage verändert wird und dass die Position im RichEdit verändert wird.

Armageddon 29. Aug 2005 15:42

Re: Wie Caretposition in RichEdit setzen?
 
Also bleib ich doch bei der guten alten Zwischenablage. Die Leute die das Programm benutzen werden haben zu 99% sowieso nichts in der Windowszwischenablage. Von daher zu verschmerzen.

Nimmt man den Programm-Code um Daten von RichEdit1 an RichEdit2 in der gleichen Anwendung zu streamen dann gehts. Ist halt jammerschade das es von fremden Anwendungen aus so kompliziert ist. Vielleicht findet sich ja mal jemand der das in den Griff bekommt und der Allgemeinheit den Code zur Verfügung stellt.

Trotzdem Danke.


Alle Zeitangaben in WEZ +1. Es ist jetzt 23:51 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