Einzelnen Beitrag anzeigen

alzaimar
(Moderator)

Registriert seit: 6. Mai 2005
Ort: Berlin
4.956 Beiträge
 
Delphi 2007 Enterprise
 
#5

Re: Synchroner Datenaustausch zwischen verschiedenen Anwendu

  Alt 12. Mai 2009, 08:04
Du könntest dir eine Recordstruktur bauen, die die vorzunehmenden Änderungen beschreibt, z.B. so:
Delphi-Quellcode:
Type
TControlCommand = Record
  ccControlName : String[80]; // Wichtig! Statische Strings nehmen.
  Case Integer Of // Eine variante Record-Struktur
    0 : (ccNewBoolean : Boolean);
    1 : (ccNewInteger : Integer);
    2 : (ccNewString : String[255]);// S.o.! Unbedingt ein statischer ShortString!
  End;

PControlCommand = ^TControlCommand;

// Alternativ eine Klasse, die Du serialisieren und deserialisieren kannst
Hier die Implementierung des Senders. Das Handle des Empfänger-Formulars muss allerdings bekannt sein. Das ginge per 'FindWindow'.
Delphi-Quellcode:
...
// Sender verschickt Änderungen. Dazu alle OnChange-Ereignisse der Controls mit diesem Event verbinden!
Procedure TSenderForm.SendChange (Sender : TObject);
Var
  cmd : TControlCommand;
  copystruct : TCopyDataStruct;
  HwndReceiver : THandle;

Begin
// Hier wurde der 'Sender' (irgendein Control) verändert, bewegt, angeklickt, getippt etc.
  If Sender is TControl Then Begin
    cmd.ccControlName := TControl(Sender).Name;
    If Sender is TCheckBox Then
      cmd.ccNewBoolean := TCheckBox(Sender).Checked
    Else If Sender is TRadiobutton Then
      cmd.ccNewBoolean := TRadiobutton(Sender).Checked
    Else If Sender is TTrackBar Then
      cmd.ccNewInteger := TTrackBar(Sender).Position
    Else If Sender is TEdit Then
      cmd.ccNewString := TEdit(Sender).Text
    Else
      Raise Exception.CreateFmt ('Controls der Klasse %s werden nicht unterstützt',[TControl(Sender).ClassName]);
    
    copyStruct.dwData := 0; // Hier kannst Du einen 32bit-Integer angeben (Ein 'Kommando' z.B.)
    copyStruct.cbData := SizeOf (TControlCommand);
    copystruct.lpData := @cmd;
    HwndReceiver := FindWindow('TReceiverForm',nil);
    If HwndReceiver>0 Then
      PostMessage (HwndReceiver, WM_COPYDATA, Handle, integer (@copystruct));
  End;
End;
Und hier der Receiver....
Delphi-Quellcode:
Type
  TReceiverForm = Class (TForm)
  ...
// Deklaration des Message-Handlers
    Procedure CMCopyData (Var Msg : TMessage); Message WM_COPYDATA;
  ...
  End;

Procedure TReceiverForm.CMCopyData (Var Msg : TMessage);
Var
  cmd : PControlCommand;
  ctrl : TControl;
 
Begin
// In Msg.lParam steht ein Zeiger auf eine TCopyDataStruct.
// Der lpData-Member ist widerum ein Zeiger auf ein TControlCommand
  cmd := PControlCommand (PCopyDataStruct(Msg.lParam)^.lpData);
  ctrl := FindControl (cmd^.ccControlName);
  if Assigned (ctrl) then
    If ctrl is TCheckBox Then
      TCheckBox(ctrl).Checked := cmd^.ccNewBoolean
    Else If ctrl is TRadiobutton Then
      TRadiobutton(ctrl).Checked := cmd.ccNewBoolean
    Else If ctrl is TTrackBar Then
      TTrackBar(ctrl).Position := cmd.ccNewInteger
    Else If ctrl is TEdit Then
      TEdit(ctrl).Text := cmd.ccNewString
End;
(getippt und nicht getestet)

Das funktioniert, wenn die zu synchronisierenden Controls auf dem Sender- und Receiver-Formular den gleichen Namen haben.

Im Prinzip übertrage ich über die TControlCommand-Struktur nur den Namen des geänderten Controls sowie eine Information, *was* sich verändert hat (bei einer Checkbox die 'Checked' Eigenschaft, bei einem TEdit der Text usw.) Auf der Empfängerseite suche ich das korrespondierende Control und änderen eben entsprechend die korrespondierende Eigenschaft. Das lässt sich natürlich beliebig erweitern.

Allerdings kann es sein, das es zu Problemen kommt, wenn man sehr viele Änderungen durchführt, weil der WM_COPYDATA-Mechanismus auf Empfängerseite nicht besonders geschützt ist: Laut OH soll man die Daten aus der CopyStruct 'so schnell wie möglich' abholen. Vielleicht wäre hier eine Crictical Section angebracht.
"Wenn ist das Nunstruck git und Slotermeyer? Ja! Beiherhund das Oder die Flipperwaldt gersput!"
(Monty Python "Joke Warefare")
  Mit Zitat antworten Zitat