• 运行期可以变动大小和尺寸的自定义控件、



    unit CcDrag;

    interface

    uses
      Windows, SysUtils, Classes, Graphics, Controls, Forms;

    type
      TMousePosition = (mpNone, mpRightBottom, mpRight, mpBottom);
      TCcDrag = class(TGraphicControl)
      private
        { Private Declarations }
        FMouseDown: Boolean;
        FDownPt: TPoint;
        FMousePos: TMousePosition;
        FOldWidth: Integer;
        FOldHeight: Integer;
        FLtdControl: TControl;
        FAssignControl: Boolean;
        FBoundsRect: TRect;
        FFixSize: Boolean;
        FFixHeight: Integer;
        FFixWidth: Integer;
        procedure SetLtdControl(const Value: TControl);
        procedure AdjustControlBounds(const ABoundsRec: TRect);
        procedure SetControlBounds(const ABoundsRect: TRect);
        procedure SetFixSize(const Value: Boolean);
      protected
        { Protected Declarations }
        procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
          X, Y: Integer); override;
        procedure MouseMove(Shift: TShiftState; X, Y: Integer); override;
        procedure MouseUp(Button: TMouseButton; Shift: TShiftState;
          X, Y: Integer); override;
        procedure Paint; override;
        procedure Notification(AComponent: TComponent;
          Operation: TOperation); override;
        // Big Z Add This Procedure
        // 避免在限制边缘拖动时的闪烁,使其表现更好!
        procedure AdjustPosition(const OffsetX, OffsetY: Integer); virtual;
      public
        { Public Declarations }
        constructor Create(AOwner: TComponent); override;
      published
        { Published Declarations }
        property LtdControl: TControl read FLtdControl write SetLtdControl;
        // Big Z Add This 2000.07.21  10:20
        // 增加一个属性,是否可以改变大小
        property FixSize: Boolean read FFixSize write SetFixSize;
        property Width default 90;
        property Height default 120;
        property Align;
        property Anchors;
        property Constraints;
        property DragCursor;
        property DragKind;
        property DragMode;
        property Enabled;
        property ParentShowHint;
        property PopupMenu;
        property ShowHint;
        property Visible;
        property OnClick;
    {$IFDEF VER130}
        property OnContextPopup;
    {$ENDIF}
        property OnDblClick;
        property OnDragDrop;
        property OnDragOver;
        property OnEndDock;
        property OnEndDrag;
        property OnMouseDown;
        property OnMouseMove;
        property OnMouseUp;
        property OnStartDock;
        property OnStartDrag;
      end;

    implementation

    const
      OFFSET = 5;

    procedure TCcDrag.MouseDown(Button: TMouseButton; Shift: TShiftState; X, Y:
      Integer);
    begin
      {Method implementation code}
      inherited MouseDown(Button, Shift, X, Y);

      if Button = mbLeft then
      begin
        FMouseDown := True;
        FDownPt := Point(X, Y);
        FOldWidth := Width;
        FOldHeight := Height;
        if Assigned(FLtdControl) then
          FBoundsRect := FLtdControl.BoundsRect;
        if FMousePos = mpNone then
          Screen.Cursor := crDrag;
      end
    end; {MouseDown}

    procedure TCcDrag.MouseMove(Shift: TShiftState; X, Y: Integer);
    var
      OffsetX, OffsetY: Integer;
    begin
      {Method implementation code}
      inherited MouseMove(Shift, X, Y);

      if FMouseDown then
      begin
        OffsetX := X - FDownPt.x;
        OffsetY := Y - FDownPt.y;
        case FMousePos of
          mpNone:
            begin
              {Left := OffsetX + Left;
              Top := OffsetY + Top;
              if FAssignControl then
                AdjustControlBounds(FBoundsRect)}
              // Big Z Modify Here 2000.07.21  11:18
              AdjustPosition(OffsetX, OffsetY);
            end;
          mpRight:
            begin
              if FOldWidth + OffsetX > 0 then
                Width := FOldWidth + OffsetX;
              if FAssignControl then
                SetControlBounds(FBoundsRect)
            end;
          mpBottom:
            begin
              if FOldHeight + OffsetY > 0 then
                Height := FOldHeight + OffsetY;
              if FAssignControl then
                SetControlBounds(FBoundsRect)
            end;
          mpRightBottom:
            begin
              if FOldWidth + OffsetX > 0 then
                Width := FOldWidth + OffsetX;
              if FOldHeight + OffsetY > 0 then
                Height := FOldHeight + OffsetY;
              if FAssignControl then
                SetControlBounds(FBoundsRect)
            end
        end;
      end
      else
      begin
        if (X >= Width - OFFSET) and (Y >= Height - OFFSET) then
        begin
          Cursor := crSizeNWSE;
          FMousePos := mpRightBottom;
        end
        else if X >= Width - OFFSET then
        begin
          Cursor := crSizeWE;
          FMousePos := mpRight
        end
        else if Y >= Height - OFFSET then
        begin
          Cursor := crSizeNS;
          FMousePos := mpBottom
        end
        else
        begin
          Cursor := crDefault;
          FMousePos := mpNone
        end;
        // Big Z Add This 2000.07.21  10:26
        // 如果设定了 FixSize 属性,则尺寸的固定的值
        if FFixSize then
        begin
          Cursor := crDefault;
          FMousePos := mpNone
        end
      end
    end; {MouseMove}

    procedure TCcDrag.MouseUp(Button: TMouseButton; Shift: TShiftState; X, Y:
      Integer);
    begin
      {Method implementation code}
      inherited MouseUp(Button, Shift, X, Y);

      FMouseDown := False;
      Screen.Cursor := crDefault
    end; {MouseUp}

    constructor TCcDrag.Create(AOwner: TComponent);
    begin
      inherited Create(AOwner);
      {Add any other initialization code here}
      Width := 90;
      Height := 120;
    end; {Create}

    procedure TCcDrag.Paint;
      procedure PaintDot(X, Y: Integer);
      begin
        Canvas.Brush.Style := bsSolid;
        Canvas.Brush.Color := clBlack;
        Canvas.Pen.Style := psSolid;
        Canvas.Pen.Color := clBlack;
        Canvas.Pen.Mode := pmCopy;
        Canvas.Rectangle(X - 2, Y - 2, X + 2, Y + 2);
      end;
    begin
      inherited;

      Canvas.Pen.Style := psDot;
      Canvas.Brush.Style := bsClear;
      Canvas.Pen.Color := clRed;
      Canvas.Pen.Mode := pmNot;
      Canvas.Rectangle(0, 0, Width, Height);
      // Big Z Add This 2000.07.21  11:32
      if not FFixSize then
      begin
        PaintDot(Width, Height shr 1);
        PaintDot(Width shr 1, Height);
        PaintDot(Width, Height)
      end;
    end;

    procedure TCcDrag.Notification(AComponent: TComponent;
      Operation: TOperation);
    begin
      inherited Notification(AComponent, Operation);

      if (Operation = opReMove) and (AComponent = FLtdControl) then
        FLtdControl := nil
    end;

    procedure TCcDrag.SetLtdControl(const Value: TControl);
    begin
      if FLtdControl <> Value then
      begin
        FLtdControl := Value;
        FAssignControl := Assigned(Value);
        if FAssignControl then
        begin
          FBoundsRect := Value.BoundsRect;
          SetControlBounds(FBoundsRect);
        end
      end
    end;

    procedure TCcDrag.SetControlBounds(const ABoundsRect: TRect);
    begin
      if ABoundsRect.Left > Left then
        Left := ABoundsRect.Left;
      if ABoundsRect.Top > Top then
        Top := ABoundsRect.Top;
      if ABoundsRect.Right < (Left + Width) then
        Width := ABoundsRect.Right - Left;
      if ABoundsRect.Bottom < (Top + Height) then
        Height := ABoundsRect.Bottom - Top
    end;

    procedure TCcDrag.AdjustControlBounds(const ABoundsRec: TRect);
    begin
      if ABoundsRec.Left > BoundsRect.Left then
        Left := ABoundsRec.Left;
      if ABoundsRec.Top > BoundsRect.Top then
        Top := ABoundsRec.Top;
      if ABoundsRec.Right < BoundsRect.Right then
        Left := ABoundsRec.Right - Width;
      if ABoundsRec.Bottom < BoundsRect.Bottom then
        Top := ABoundsRec.Bottom - Height
    end;

    // Big Z Add This 2000.07.21  10:26
    // 如果设定了 FixSize 属性,则尺寸的固定的值
    // ----------------------------------------------------------------------------

    procedure TCcDrag.SetFixSize(const Value: Boolean);
    begin
      if FFixSize <> Value then
      begin
        FFixSize := Value;
      end;
    end;

    // Big Z Add This Procedure
    // 避免在限制边缘拖动时的闪烁,使其表现更好!

    procedure TCcDrag.AdjustPosition(const OffsetX, OffsetY: Integer);
    begin
      if not FAssignControl then
      begin
        Left := Left + OffsetX;
        Top := Top + OffsetY;
        Exit;
      end;
      if Left + OffsetX < FBoundsRect.Left then
        Left := FBoundsRect.Left
      else if Left + OffsetX + Width > FBoundsRect.Right then
        Left := FBoundsRect.Right - Width
      else
        Left := Left + OffsetX;
      if Top + OffsetY < FBoundsRect.Top then
        Top := FBoundsRect.Top
      else if Top + OffsetY + Height > FBoundsRect.Bottom then
        Top := FBoundsRect.Bottom - Height
      else
        Top := Top + OffsetY;
    end;

    end.
  • 相关阅读:
    as3 return语句中的运算符
    AIR custom ApplicationUpdaterUI
    Flash Builder 无法连接到应用程序以访存概要分析数据
    Android的所有权限说明
    Tomcat数据源配置
    hibernate 延迟加载(懒加载)
    Android SQLite数据库操作
    Android下载文本文件和mp3文件
    JPA注解
    Android Intent传值且实现窗体跳转
  • 原文地址:https://www.cnblogs.com/lingzhiwen/p/4679927.html
Copyright © 2020-2023  润新知