Announcement

Collapse
No announcement yet.

Mit dem Maus einen Mausrahmen ziehen

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Mit dem Maus einen Mausrahmen ziehen

    Hallo Leute, <BR>
    ich wollte in meinen kleinen Programm, die Funktionalität anbieten, wie <BR>unter Windows oder in anderen Programmen gibt. Wenn ich die Linke <BR>Maustaste drücke und die Ziehe, sollte ein Rahmen aufgebaut werden. <BR>Und beim loslassen der Maustaste wieder verschwinden. Eine Bekannte Sache.<BR>
    <BR>
    Soweit so gut. Ich habe eine "Sahpe" genommen und die <BR>Ereignisse "OnMouseDown", "OnMouseMove" und "OnMouseUp" programmiert. <BR>Es funktioniert auch! Super!. <BR>
    <BR>
    <B>Problem ist aber: </B><BR>
    Wenn ich andere Objekte in mein Form habe wie "Groupbox" etc. läuft mein <BR>Rahmen nicht über die Objekte sondern Hinter den <BR>Objekten . "BringToFront" bringt den erwünschten Effekt auch nicht <BR>
    <BR>
    <B>Meine Frage ist: </B><BR>
    Gibt es einen anderen Weg? Wenn ja, was muss ich machen! <BR>
    Oder was muss ich tun damit mein "Rahmen" über die Objekte läuft? <BR>
    <BR>
    Vielleicht muss man die eine oder andere Propertie setzen?! <BR>
    <BR>

    Gruß + Danke <BR>
    M. Oda

  • #2
    Hallo,<br>
    zeichne das Rechteck doch auf dem Desktop.<br>
    <pre>
    <font face="Verdana" size="1" color="#000000">unit Unit1;
    interface
    uses
    Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
    StdCtrls, Buttons;
    type
    TForm1 = class(TForm)
    Edit1: TEdit;
    Button1: TButton;
    ListBox1: TListBox;
    SpeedButton1: TSpeedButton;
    procedure FormMouseDown(Sender: TObject; Button: TMouseButton;
    Shift: TShiftState; X, Y: Integer);
    procedure FormMouseUp(Sender: TObject; Button: TMouseButton;
    Shift: TShiftState; X, Y: Integer);
    procedure FormMouseMove(Sender: TObject; Shift: TShiftState; X,
    Y: Integer);
    procedure FormCreate(Sender: TObject);
    private
    { Private-Deklarationen }
    FDrawing : Boolean;
    FDeskTopDC : hDC;
    FCanvas : TCanvas;
    FOrigin : TPoint;
    FMovePt : TPoint;
    FScreenRect : TRect;
    public
    { Public-Deklarationen }
    end;
    var
    Form1: TForm1;
    implementation
    {$R *.DFM}
    procedure TForm1.FormMouseDown(Sender: TObject; Button: TMouseButton;
    Shift: TShiftState; X, Y: Integer);
    var
    FormRect : TRect;
    FormClientRectLeftTop : TPoint;
    begin
    FDrawing:=True;
    FormRect:=ClientRect;
    // LinksOben des ClientRects in Screen-Koordinaten umwandeln.
    FormClientRectLeftTop:=ClientToScreen(Point(Client Rect.Left,ClientRect.Top));
    // FormRect entsprechend verschieben
    OffsetRect(FormRect,FormClientRectLeftTop.X,FormCl ientRectLeftTop.Y);
    // Mausbereich einschränken
    ClipCursor(@FormRect);
    // Startpunkt in Screen-Koordinaten umwandeln.
    FOrigin:=ClientToScreen(Point(X,Y));
    FMovePt:=ClientToScreen(Point(X,Y));
    // Gerätekontext des Desktops holen
    FDeskTopDC:=GetDC(0);
    FCanvas:=TCanvas.Create;
    // Setzen des Canvas Handles auf das Desktop Handle.
    FCanvas.Handle:=FDeskTopDC; // Hier bin ich mir nicht sicher ob es
    // so richtig ist, oder ob es irgendwelche
    // Spätfolgen o. Nebenwirkungen hat.
    end;
    procedure TForm1.FormMouseUp(Sender: TObject; Button: TMouseButton;
    Shift: TShiftState; X, Y: Integer);
    var
    iCnt : Integer;
    begin
    If FDrawing then
    begin
    FDrawing:=False;
    ReleaseDC(Handle,FDeskTopDC); // Desktop DC wieder freigeben
    FCanvas.Free;
    ClipCursor(@FScreenRect); // Mausbereich wieder zurücksetzen
    For iCnt:=0 to ControlCount-1 do // alles neu zeichen lassen
    Controls[iCnt].Refresh;
    Invalidate;
    end;
    end;
    procedure TForm1.FormMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer);
    var
    NewPt : TPoint;
    begin
    If (FDrawing) and (ssLeft in Shift) then
    begin
    FCanvas.Brush.Style:=bsClear;
    NewPt:=ClientToScreen(Point(X,Y));
    FCanvas.Pen.Mode:=pmNotXor;
    FCanvas.Rectangle(FOrigin.X,FOrigin.Y,FMovePt.X,FM ovePt.Y);
    FCanvas.Rectangle(FOrigin.X,FOrigin.Y,NewPt.X,NewP t.Y);
    FCanvas.Pen.Mode:=pmCopy;
    FMovePt:=NewPt;
    end;
    end;
    procedure TForm1.FormCreate(Sender: TObject);
    begin
    FScreenRect:=Rect(0,0,Screen.Width,Screen.Height);
    end;
    end.
    </font></pre&gt

    Comment


    • #3
      mit GetWindowDC(Form.Handle) ginge das auch.<br>
      Aber das Problem ist das die "überzeichneten" Controls den Rahmen beim Neuzeichnen zerstören.

      Gruß Hage

      Comment


      • #4
        Hallo Leute,
        ich werde es mal ausprobieren. Da ich mich mit diesem Technik nicht auskenne (rot Anfänger).
        Danke für die Antworten

        Gruß
        M. Od

        Comment


        • #5
          Hallo Jens,<BR>
          danke für den Code. Wie gesagt kenne ich mich mit dieser Technik sehr wenig aus. Es funktioniert Prima! Nur nach dem die Maustaste <BR> losgelassen wird, wandert die Maus nach links oben in die Ecke und reagiert nicht. Erst nach nochmaligem Drücken der Maustaste kann die Maus bewegt werden.<BR>
          Gruß + Danke
          M. Od

          Comment


          • #6
            Hallo Muammer,<br>ich habe das Problem nicht. <br>
            evt hast Du ClipCursor(@FScreenRect); // Mausbereich wieder zurücksetzen vergessen

            Comment

            Working...
            X