Delphi 如何在纸上画画

Delphi 如何在纸上画画,delphi,canvas,components,tpanel,Delphi,Canvas,Components,Tpanel,我需要画一个TPanel,最好是直接画,这样上面就不会有另一个组件妨碍mousevent事件捕获(我想画一个小的“大小抓地力”)。我该怎么做呢?最简单的方法就是在面板上放一个标签。但是如果你真的不想这样做,在代码编辑器中输入TCanvas,点击F1,然后在引擎盖下学习它是如何工作的。(不要说我没有警告过你……)这是众多让你的生活更轻松的方法之一。我只是进入Delphi,在TRzPanel上输入: RzPanel1.画布.矩形 我相信还有其他的解决办法,但我不必和雷兹一起寻找 (仅仅是一个满意的客

我需要画一个TPanel,最好是直接画,这样上面就不会有另一个组件妨碍mousevent事件捕获(我想画一个小的“大小抓地力”)。我该怎么做呢?

最简单的方法就是在面板上放一个标签。但是如果你真的不想这样做,在代码编辑器中输入TCanvas,点击F1,然后在引擎盖下学习它是如何工作的。(不要说我没有警告过你……)

这是众多让你的生活更轻松的方法之一。我只是进入Delphi,在TRzPanel上输入:

RzPanel1.画布.矩形

我相信还有其他的解决办法,但我不必和雷兹一起寻找

(仅仅是一个满意的客户,大约10年了……)


编辑:鉴于您的目标,以及您已经声明拥有Raize组件,我还应该指出,TRzSizePanel处理面板的大小调整和有用的事件,如OnCanResize(以确定是否允许调整到特定的新宽度或高度)。

如何在运行时将大小控制柄添加到正在调整大小的控件:

塔德帕内尔:

要真正做到这一点,您可能应该编写一个后代类。替代
Paint
方法以绘制尺寸夹点,替代
MouseDown
MouseUp
MouseMove
方法以向控件添加尺寸调整功能

我认为这是一个比试图在应用程序代码中使用
TPanel
更好的解决方案,原因如下:

  • Canvas
    属性在
    TPanel
    中受保护,因此您无法从类外访问它。你可以通过打字来解决这个问题,但那是作弊
  • “可调整大小”听起来更像是面板的一个功能,而不是应用程序的一个功能,因此将其放在面板控件的代码中,而不是应用程序的主代码中
  • 以下是一些让您开始学习的内容:

    type
      TSizablePanel = class(TPanel)
      private
        FDragOrigin: TPoint;
        FSizeRect: TRect;
      protected
        procedure Paint; override;
        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;
      end;
    
    procedure TSizeablePanel.Paint;
    begin
      inherited;
      // Draw a sizing grip on the Canvas property
      // There's a size-grip glyph in the Marlett font,
      // so try the Canvas.TextOut method in combination
      // with the Canvas.Font property.
    end;
    
    procedure TSizeablePanel.MouseDown;
    begin
      if (Button = mbLeft) and (Shift = []) 
          and PtInRect(FSizeRect, Point(X, Y)) then begin
        FDragOrigin := Point(X, Y);
        // Need to capture mouse events even if the mouse
        // leaves the control. See also: ReleaseCapture.
        SetCapture(Handle);
      end else inherited;
    end;
    

    我想知道您是如何创建components标记的?;)就像你的问题+1谢谢-@MasterPeter的微笑,@Mason Wheeler的修复。我在这里开始了一个类似的问题(更全球化,适用于VCL中的任何控件):我实际上认为我可以做TCanvas部分,因为我必须使用一些示例代码。。。但是如何暴露面板本身的TCanvas?我发现了这一点,但听起来好像缺少了什么:该链接中的TMyPanel(panel)代码是关键。如果在要访问画布的同一单元中定义继承类,则可以访问该类的任何受保护属性。这是德尔福“一个单位内的班级是朋友”原则的一部分。这也是一种黑客行为。:-)当你说“这也是一种黑客行为”——这是否意味着你认为这种方法不合适?(我只是想从这些关于这个问题的好答案中尽我所能地学习。)太好了——我有Raize,所以我会研究这个问题(以前没有考虑过,因为我想开始时“尽可能简单/低水平”,但这可能是最好的途径)。谢谢你花时间发布这篇文章。Raize是如何让这比在普通的TPanel上画画更容易的呢?除非出于某种原因,Raize控件将Canvas属性设置为公共而非受保护。从代码示例来看,这似乎正是原因所在。我发现使用Raize组件简化了我的编码,并使我的应用程序在视觉上保持一致。Ray几乎考虑了所有事情,他对raize.public.rzcomps.support新闻组的支持非常出色——我阅读了他在该新闻组中写的所有内容,因为他的编码实践非常干净。出于同样的原因,他的源代码值得一读。谢谢Rob!你所描述的(并且慷慨地提供了一些“起始代码”)是我正在尝试做的,但是我意识到我需要弄清楚绘图/画布部分,所以直接在应用程序代码中探索。非常感谢您在这里的投入——非常有帮助!:-)请注意,这也是明智的,因为例如非窗口上的Lazarus(可能还有Kylix),不允许在.PAINT事件之外的画布上进行绘制。因此,直接强制执行确保在绘制事件中完成唯一图形的结构是明智的。