首先,我向解答出的朋友们保证,我会及时给你结贴,但不要让我等太多天,我怕我会忘记,但这几天我一定会观注此问题的。其实,我这问题已在CDSN上问过好多次了,但都得不到满意的答案。希望这次能有个高手能详细的帮我解答好这个问题,下面我也详细说明我的问题:在VB6中,我用pictureBox来画长方形小格图(因为我要求有保留BMP图片功能,所以不能用ImageBox控件),我是在pictureBox中用picture1.line的方法来画小方格图的,我在程序中要画的方格图很多,会超出屏幕的原来实际宽度和高度。但是pictureBox控件不会自动象IE浏览器那样当超过屏幕的长或高时,就自动生成一个长和高的滑条,通过鼠标拉动滑条可以看到超出屏幕的其它部份内容。现在我就问,如何解决pictureBox中画图时,当画出的图超出屏幕的部份怎么也用滑条拖动来解决?请列出代码来,因为起先有人说用两个picturebox控件来实现,但我怎么做都没有办法,不懂他们是怎么做到的?

解决方案 »

  1.   

    在Picture1内用滚动条移动Picture2:
    用两个PictureBox控件,首先在窗体添加1个PictureBox控件Picture1,然后在Picture1中间用鼠标加载另1个PictureBox控件Picture2.
    在穿体添加剂个HScroll控件于窗体或Picture1内,调整Picture2的Height.
    垂直滚动条建议不要与水平滚动条同时使用,会报错或当机.
    代码如下:Private Sub Form_Load()
    Me.Height = 11295
    Me.Width = 15360
    Picture1.Width = Me.Width - 400
    'Picture2.Height = Picture1.Height
    Picture2.Width = Picture1.Width * 2.1'倍率可调整
    End SubPrivate Sub HScroll1_Change()
    Picture2.Left = -HScroll1 * 0.5倍率需调整
    End Sub
      

  2.   

    我也是经常用picture控件来画曲线,为了实现图形的缩放功能,我是在内存中使用变量来记录坐标点,然后绘制图像,当图像的横坐标或者纵坐标大于控件的scaleheight或者scalewidth属性时,改变这两个属性的数值,然后重新绘制曲线。这样也可以实现你需要的功能,但是要看你的数据量有多大。我使用的最大量就是干脆设了三个65535的数组,刷新整个图像的时间好像也没用一两秒。
      

  3.   

    首先在窗体添加1个PictureBox控件Picture1,然后在Picture1中间用鼠标画另1个PictureBox控件Picture2.再加上hscroll vscrollDim ox As Integer, oy As Integer, flag As Boolean
    Private Sub Form_Load()
    Picture2.AutoRedraw = True
    Picture2.Left = Picture1.Left
    Picture2.Top = Picture1.Top
    Picture2.Width = Picture1.Width * 10
    Picture2.Height = Picture1.Height * 10
    HScroll1.Min = 0
    HScroll1.Max = 100
    VScroll1.Min = 0
    VScroll1.Max = 100End SubPrivate Sub HScroll1_Change()
    Picture2.Left = -HScroll1.Value * 0.1 * Picture1.Width
    End Sub
    Private Sub Picture2_MouseDown(Button As Integer, Shift As Integer, X As Single, Y As Single)
    If flag Then
        Picture2.Line (ox, oy)-(X, Y), vbRed
        flag = False
    Else
        flag = True
        ox = X
        oy = Y
    End If
    End SubPrivate Sub VScroll1_Change()
    Picture2.Top = -VScroll1.Value * 0.1 * Picture1.WidthEnd Sub
      

  4.   

    呵呵,我记得,好像是把一个autodraw设置为false一个设置为true好像就可以的很久以前看过,,记不清,自己g吧
      

  5.   

    好象以上不对呀,当同时用HScroll和VScroll控件时,就不能画图了,会提示不能画AutoRed图,davysnet(随风),兄的不懂是怎么做的,能否详细一点,最好原码附上一点,不过我画图时就象画墙上的砖块图,会一小格一小格画的,会很多,用你那种记内存方法能解决吗?
      

  6.   

    偶现在用的也是关于大量图片管理的超长窗体,楼主可试试下面方法:
    先在窗体上拖一个双屏幕长的frame1框(你的所有内容都可以在这上面拖出),高18000;宽15085;(窗体的属性Scalemode取1-Twip)
    然后拖水平与垂直的两个滚动条;(注意:要在窗体上拖出)
    Vscrloo1(竖滚动条)属性:LargeChange=20000,Max=11055
    HScroll1(横)属性:LargeChange=8000;Max=1000;Top=18000;Width=14040
    上面是偶的选用参数,你也可自选;
    建立一个模块:下面代码放进去
    Option Explicit
    Public Type POINTL
        x As Long
        y As Long
    End Type
    Declare Function CallWindowProc _
        Lib "user32" Alias "CallWindowProcA" _
            (ByVal lpPrevWndFunc As Long, _
            ByVal hwnd As Long, _
            ByVal Msg As Long, _
            ByVal wParam As Long, _
            ByVal lParam As Long) As Long
    Declare Function SetWindowLong _
        Lib "user32" Alias "SetWindowLongA" _
            (ByVal hwnd As Long, _
            ByVal nIndex As Long, _
            ByVal dwNewLong As Long) As Long
    Declare Function SystemParametersInfo _
        Lib "user32" Alias "SystemParametersInfoA" _
            (ByVal uAction As Long, _
            ByVal uParam As Long, _
            lpvParam As Any, _
            ByVal fuWinIni As Long) As Long
    Declare Function ScreenToClient Lib "user32" _
    (ByVal hwnd As Long, xyPoint As POINTL) As Long
    Public Const GWL_WNDPROC = -4
    Public Const SPI_GETWHEELSCROLLLINES = 104
    Public Const WM_MOUSEWHEEL = &H20A
    Public WHEEL_SCROLL_LINES As Long
    Global lpPrevWndProc As Long
    Public Sub Hook(ByVal hwnd As Long)
        lpPrevWndProc = SetWindowLong(hwnd, GWL_WNDPROC, AddressOf WindowProc)
        Call SystemParametersInfo(SPI_GETWHEELSCROLLLINES, 0, WHEEL_SCROLL_LINES, 0)
        If WHEEL_SCROLL_LINES > Form1.VScroll1.Max Then
            WHEEL_SCROLL_LINES = Form1.VScroll1.Max
        End If
    End Sub
    Public Sub UnHook(ByVal hwnd As Long)
        Dim lngReturnValue As Long
        lngReturnValue = SetWindowLong(hwnd, GWL_WNDPROC, lpPrevWndProc)
    End Sub
    Function WindowProc(ByVal hw As Long, _
            ByVal uMsg As Long, _
            ByVal wParam As Long, _
            ByVal lParam As Long) As Long
        Dim pt As POINTL
        Select Case uMsg
            Case WM_MOUSEWHEEL
                If wParam = -7864320 Then
                    If Form1.VScroll1.Value <= Form1.VScroll1.Max - 300 Then '4个300值可调鼠标滚轮移动屏幕的速度,可取300-1000(值越大,移动速度越快)
                        Form1.VScroll1.Value = Form1.VScroll1.Value + 300
                    Else
                        Form1.VScroll1.Value = Form1.VScroll1.Max
                    End If
                ElseIf wParam = 7864320 Then
                    If Form1.VScroll1.Value >= 300 Then
                        Form1.VScroll1.Value = Form1.VScroll1.Value - 300
                    Else
                        Form1.VScroll1.Value = 0
                    End If
                End If
            Case Else
                WindowProc = CallWindowProc(lpPrevWndProc, hw, uMsg, wParam, lParam)
        End Select
    End FunctionPublic Function HIWORD(LongIn As Long) As Integer
      HIWORD = (LongIn And &HFFFF0000) \ &H10000
    End Function
    Public Function LOWORD(LongIn As Long) As Integer
          LOWORD = LongIn And &HFFFF&
    End Function下面代码放在窗体中:
    Private Sub Form_Load()
        Hook Me.hwnd
    End Sub
    Private Sub Form_Resize()
        If Frame1.Height > Me.Height Then
            VScroll1.Visible = True
        Else
            VScroll1.Visible = False
        End If
        If Frame1.Width > Me.Width Then
            HScroll1.Visible = True
        Else
            HScroll1.Visible = False
        End If
        HScroll1.Left = 0
        HScroll1.Top = Me.ScaleHeight - HScroll1.Height
        VScroll1.Left = Me.ScaleWidth - VScroll1.Width
        VScroll1.Top = 0
        HScroll1.Width = Me.ScaleWidth
        VScroll1.Height = Me.ScaleHeight
        If VScroll1.Visible = True Then
            If HScroll1.Visible = True Then
               HScroll1.Width = Abs(Me.ScaleWidth - VScroll1.Width)
               VScroll1.Height = Abs(Me.ScaleHeight - HScroll1.Height)
            End If
        End If
        HScroll1.Max = (Frame1.Width - Me.Width) + 3 * VScroll1.Width
        VScroll1.Max = (Frame1.Height - Me.Height) + 3 * HScroll1.Height
         HScroll1.ZOrder
         VScroll1.ZOrder
        End Sub
    Private Sub Form_Unload(Cancel As Integer)
        UnHook Me.hwnd
    End Sub
    Private Sub HScroll1_Change()
        Frame1.Left = -HScroll1.Value
    End Sub
    Private Sub VScroll1_Change()
        Frame1.Top = -VScroll1.Value
    End Sub
    Private Sub VScroll1_GotFocus() '此段可防止滚动条闪烁,借用一个按钮控件
        Command1.SetFocus
    End Sub
      

  7.   

    我是用BITBLT函数完成的,楼主是不是想做点阵编辑,类似画图中的放大功能?
      

  8.   

    不是,我是想动态生成砖块不方格图,所以在PICTUREBOX中用picture1.line来画,但是因为有时要画的方格很多,所以会超出屏幕,但又想看到超出的部份,因此希望能在超出时自动生成一个横向(当横向超过时)和纵向(当纵向超过时)的滑条,通过拉动它主可以看到超出的部份,就好比网页内容太大时,用横或纵向的滑条可以看超出的部份
      

  9.   

    很容易啊,用2个picture就搞定。
    关键的地方是当line超出屏幕时要首先设置picture的宽度也要大于屏幕,即picture大于要画的最大坐标
      

  10.   

    两个picturebox
    p1,和p2
    p2在p1中,但是比p1小一圈,在p1中添加滚动条v1,h1。如此p2填充了p1中除了两个滚动条之外的其他空间在p2中画图,当你的坐标大于p2的width和height的时候,相应的增加p2的宽和高以保证可视,与此同时给v1,h1赋值 v1.max=p2.height-p1.height,h1.max=p2.width-p1.width.
    此时,p2大于p1的部分不可见画完结束后,拖动滚动条v1的时候挪动p2.top可以看到隐藏的部分,h1挪动p2.left这个就是逻辑了,你仔细看看
    我做过,成功了
      

  11.   

    不知道大家有没有发现,当用两个picturebox配合画图时,如同时用了HScrol和VScroll控件时,画图会报错,而如用一个HScrol或VScrol时就可以正确拖动,而我希望是长和宽都要有拖动的功能,请问怎么做,最好有成功的代码能放上来,让大家看一看.
      

  12.   

    好的,我是用两个PICTUREBOX来画图,先放一个Picture1控件,然后在Picture1控件中再加一个Picture2控件,代码如下:Private Sub Command1_Click()
      Picture2.Line (10, 10)-(1000, 1000), , B
    End SubPrivate Sub Form_Load()
    Picture2.AutoRedraw = True
    Picture2.Left = Picture1.Left - Picture2.Width
    Picture2.Top = Picture1.Top - Picture2.Height
    Picture2.Width = Picture1.Width * 5
    Picture2.Height = Picture1.Height * 5
    HScroll1.Min = 0
    HScroll1.Max = 100
    'VScroll1.Min = 0
    'VScroll1.Max = 100End SubPrivate Sub HScroll1_Change()
      Picture2.Left = -HScroll1.Value * 0.1 * Picture1.Width
      Picture2.Line (10, 10)-(1000, 1000), , B
    End Sub
    如这样运行时会报错误:
    实例错误'480':
    不能创建AutoRedraw图像但如果我把上面的Picture2.AutoRedraw = True改为Picture2.AutoRedraw = false时就可以正常画图了,但是由于我要抓取Picture2中所画的图,因此,必须把Picture2.AutoRedraw值为true,这问题如何解决??
      

  13.   

    大家都没有见过此类问题是吗?为什么当同时加上VScrol和HScrol控件时,PICTUREBOX的AutoRedraw设真时就会出错?
    有没有类似PICTUREBOX的控件?即可以当容器画图又可以保存当前图的,此问题一直没解决,对PICTUREBOX失去信心了
      

  14.   

    没有这种问题,用滚动条的肯定都是同时用h 和v的.
    你在设计的时候就将Picture2.AutoRedraw 设为 True试试
      

  15.   

    我也有此疑问,不过后来我是直接在WebBrowser里面画图的。
    或者用DhtmlEdit也行。
      

  16.   

    一直不喜欢用两个picturebox的方法。
    用line方法+1个picturebox+内存dc+垂直、水平滚动条就可以了,根据两个滚动条的数值计算需要显示的起始坐标然后用api从内存dc中把相应区域的图形显示出来就可以了,同时可以实现放大缩小功能。
    如果用line控件数组代替line方法会更简单一点。
      

  17.   

    如果P1里面放P2,如果P2的AutoRedraw设为TRUE时,那么如果同时用H和V时,就绝对会报那种错误,如只用V或只用H控件就不会,不信你可以试试,条件是P2的AutoRedraw要设为TRUE,而P1无的
    AutoRedraw无论设不设为TRUE,结果都是错的.
    lsftest() 兄的方法我很想知道,不懂能不能具体一点,如能加上点代码,更是感激不尽
      

  18.   

    大家说了这么多,我就不说了。
    其实可以google,baidu到相似代码的