2013-01-15 212 views
2

我写在拉撒路2-3树申请我校的项目。滚动的TImage水平或垂直

一切都做了,现在用GUI打(我得到的分数相同的良好界面,因为我做了好等插入功能,这是很奇怪,但NVM)。

当我有一个像树10+节点,我的300 * 200的图像尺寸是不够大。

我想有这将是像300在TForm的* 200的TImage组件,但它会像10000 * 10000真的,你可以在它滚动。

这有可能吗?

由于

EDIT使问题更清楚

  1. 2-3树是一个数据结构。当在一张纸上绘制它看它是如何工作的,它看起来像这样

  2. 作为一个真正的拉奥努斯/ delphi中的noobie(必须在lazarus中做)使用这段代码来绘制它(即使我怀疑你需要它来回答我的问题):

    procedure TStrom.Paint(Image: TImage); 
    

    VAR C:的TCanvas;

    过程Paint1(V:TNODE;宽度,X,Y:整数); 开始

    if V.L <> nil then //left child 
    begin 
        C.MoveTo(X, Y); 
        C.LineTo(X - Width div 3, Y + 50); 
        Paint1(V.L, Width div 3, X - Width div 3, Y + 50); 
    end; 
    
    if V.S <> nil then //middle child 
    begin 
        C.MoveTo(X, Y); 
        C.LineTo(X + Width div 3, Y + 50); 
        Paint1(V.S, Width div 3, X + Width div 3, Y + 50); 
    end; 
    
    if V.P <> nil then  //right child 
    begin 
        C.MoveTo(X, Y); 
        C.LineTo(X + Width div 3 + Width div 3, Y + 50); 
        Paint1(V.P, Width div 3, X + Width div 3 + Sirka div 3, Y + 50); 
    end; 
    
    if V.isLeaf then 
    begin 
        C.Ellipse(X - 15, Y - 15, X + 15, Y + 15); 
        C.TextOut(X - 3, Y - 8, IntToStr(V.Info1)); 
    end 
    else 
    begin 
        C.Rectangle(X - 15, Y - 15, X + 15, Y + 15); 
        C.TextOut(X - 7, Y - 8, IntToStr(V.Info1)); 
        C.Rectangle(X + 15, Y - 15, X + 50, Y + 15); 
        if V.Info2 <> 0 then 
        C.TextOut(X + 27, Y - 8, IntToStr(V.Info2)); 
    end; 
    
  3. 抽奖功能运作良好,但在3+高度的节点的一些(大部分)被绘制在其他节点上,所以看起来不好。该节点坐在另一个节点上,并且不在其旁边。

  4. 我以为我会让树形图画真实的大,但它会在一个小的“面板”。像这样:TImage真的是1000 * 1000,但在形式上你只能看到它的一小部分。在这部分会有水平和垂直的滚动条,所以你可以滚动浏览图片,看看章节里有什么。 (就像当你通过网页浏览器滚动查看页面底部:))

  5. 我们不允许使用任何其他代码,只是在lazarus组件内置。 (我们也不允许创建新的组件 - >不知道为什么)

  6. 虽然我仍然对如何完成这项工作感到好奇,但我的应用程序不再需要它(安装第二台显示器以查看它是否'd的帮助,它不会,所以我想我会挖掘我的涂料方法有点:-))

+0

什么是“2-3树应用程序”?树和图像如何相关? –

+1

@Sertac,我想我们可以假设一个2-3树的应用程序是一个能够做2-3棵树的应用程序。我想我们也可以假定正在使用图像来显示屏幕上的树。然而,对于理解这个问题来说,这两者都不是至关重要的,它只是简单地询问当图像太大而不适合屏幕时如何引入滚动。图像的性质是无关紧要的。 –

+1

这意味着使用大约400 MB的位图。你应该更好地画一个例如颜料盒。你将能够使用SetWorldTransform,总是用不同的裁剪画相同的。 – bummi

回答

3

您的编辑更清楚地表明您要绘制一个示意图,如example you link to中的最后一棵树。

从您的代码我明白,你正在绘制所有节点,孩子和树叶,在一个单一的画布导致一个大的图像/位图。现在,如何只显示旁边有滚动条的大图像的一部分?

明显的选择是在TScrollBox上放置一个TPaintBox。我不知道拉撒路中的默认组件,但我希望它们都存在。将颜料盒的大小设置为等于视觉树的边界,然后设置:滚动条将自动显示。

油漆盒有一个OnPaint事件,在该事件中,您通过绘制到PaintBox.Canvas来完成油漆工作。为了优化这一点,你可以限制你的绘图到PaintBox.Canvas.ClipRect(在滚动框中可见的部分颜料盒),但我怀疑这很困难,因为你已经很难计算相邻节点之间的正确距离。 (关于这一点:我预计总树的最大宽度和高度是总深度的函数,但我可能很容易被误解。)

如果Lazarus没有TPaintBox,则使用TImage,这也是有一个Canvas属性。缺点是TImage将所有绘图操作“存储”在一个大的内部位图中,当树扩展太多时可能会引发内存或资源问题。

1

所有图像可以合并为一个大图像?如果是这样,那么也许this component回答你的问题。

这是TGraphicControl后裔,能够动画变焦。通过拖动选择矩形放大图形的一部分,通过双击缩小整个图形。如果您需要帮助来更新它,以便能够执行平移操作,请拍摄。

+0

这是光滑的,虽然它不完全回答我的问题,它是值得加1 :) –