web-dev-qa-db-ja.com

vb.netでスクロールホイールを使用してPictureboxを拡大する方法

グラフィックオーバーレイのセットを使用して、グラフィックオブジェクトを使用してピクチャーボックスコントロール内に画像を描画しています。ピクチャーボックスをパネル内に配置し、パネルを自動スクロールに設定しました。今私が知る必要があるのは、マウスのスクロールホイールを使用して、描画される画像の品質を維持しながら、画像のサイズを少しずつ大きくすることです。誰もがこれを行う方法を知っていますか?

以下のAbdiasSoftwareコードで更新すると、pictureboxのSizemodeプロパティがStretchImageに設定されていると、画像が小さくなり始めます。このコードが正しく機能しないようにするのを妨げる可能性のあるマウスのパン機能があります。何か案は?これが正しく機能しない原因は何ですか?

[〜#〜]解決済み[〜#〜]

このコードは、以下の2つのコードのどれよりもはるかにうまく機能しました。

Private Sub PictureBox_MouseWheel(sender As System.Object,
                             e As MouseEventArgs) Handles PictureBox1.MouseWheel
    If e.Delta <> 0 Then
        If e.Delta <= 0 Then
            If PictureBox1.Width < 500 Then Exit Sub 'minimum 500?
        Else
            If PictureBox1.Width > 2000 Then Exit Sub 'maximum 2000?
        End If

        PictureBox1.Width += CInt(PictureBox1.Width * e.Delta / 1000)
        PictureBox1.Height += CInt(PictureBox1.Height * e.Delta / 1000)
    End If

End Sub
8
Greg Willard

このコードを試すことができます。フォーム(_Panel1_内の_PictureBox1_と_PictureBox1_)に_Panel1_と_Panel1.AutoScroll = True_が存在し、PictureBoxに画像が設定されていることを前提としています。

コードはズームの中心点を計算しませんが、そのためにe.Location(またはe.X/e.Y)を使用できます。

更新-これは、以前よりも堅牢な(はずの)新しいコードです(下を参照):

_Public Class Form1

    Private _originalSize As Size = Nothing
    Private _scale As Single = 1
    Private _scaleDelta As Single = 0.0005

    Private Sub Form_MouseWheel(sender As System.Object, e As System.Windows.Forms.MouseEventArgs) Handles Me.MouseWheel

        'if very sensitive mouse, change 0.00005 to something even smaller   
        _scaleDelta = Math.Sqrt(PictureBox1.Width * PictureBox1.Height) * 0.00005

        If e.Delta < 0 Then
            _scale -= _scaleDelta
        ElseIf e.Delta > 0 Then
            _scale += _scaleDelta
        End If

        If e.Delta <> 0 Then _
        PictureBox1.Size = New Size(CInt(Math.Round(_originalSize.Width * _scale)), _
                                    CInt(Math.Round(_originalSize.Height * _scale)))

    End Sub

    Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
        PictureBox1.SizeMode = PictureBoxSizeMode.StretchImage

        'init this from here or a method depending on your needs
        If PictureBox1.Image IsNot Nothing Then
            PictureBox1.Size = Panel1.Size
            _originalSize = Panel1.Size
        End If

    End Sub

End Class
_

古いコード-動作しますが、おそらくScale()の丸め誤差が原因で、大きな変更では不安定になります。

_Public Class Form1

    Private _scale As New SizeF(1, 1)
    Private _scaleDelta As New SizeF(0.01, 0.01) '1% for each wheel tick

    Private Sub Form_MouseWheel(sender As System.Object, 
                                e As MouseEventArgs) Handles Me.MouseWheel
'count incrementally 
        _scale.Height = 1
        _scale.Width = 1

        If e.Delta < 0 Then
            _scale += _scaleDelta
        ElseIf e.Delta > 0 Then
            _scale -= _scaleDelta
        End If

        If e.Delta <> 0 Then _
        PictureBox1.Scale(_scale)

    End Sub

    Private Sub Form1_Load(sender As System.Object, 
                           e As EventArgs) Handles MyBase.Load

        PictureBox1.SizeMode = PictureBoxSizeMode.StretchImage

        'init picturebox size = image size
        If PictureBox1.Image IsNot Nothing Then
            PictureBox1.Scale(New SizeF(1, 1))
            PictureBox1.Size = PictureBox1.Image.Size
        End If

    End Sub

End Class
_
6
user1693593

画像の比率を無視するStretchImageSizeModeには望ましくない影響があることに気づきました。 「ズーム」アルゴリズムに含める幅と高さの比率変数を追加しました。見る _ratWidthおよび_ratHeight以下のコードで。

Public Class Form1

Private _originalSize As Size = Nothing
Private _scale As Single = 1
Private _scaleDelta As Single = 0.0005
Private _ratWidth, _ratHeight As Double

Private Sub Form_MouseWheel(sender As System.Object, e As System.Windows.Forms.MouseEventArgs) Handles Me.MouseWheel

    'if very sensitive mouse, change 0.00005 to something even smaller   
    _scaleDelta = Math.Sqrt(PictureBox1.Width * PictureBox1.Height) * 0.00005

    If e.Delta < 0 Then
        _scale -= _scaleDelta
    ElseIf e.Delta > 0 Then
        _scale += _scaleDelta
    End If

    If e.Delta <> 0 Then _
    PictureBox1.Size = New Size(CInt(Math.Round((_originalSize.Width * _ratWidth) * _scale)), _
                                CInt(Math.Round((_originalSize.Height * _ratHeight) * _scale)))

End Sub

Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
    PictureBox1.SizeMode = PictureBoxSizeMode.StretchImage

    'init this from here or a method depending on your needs
    If PictureBox1.Image IsNot Nothing Then
        _ratWidth = PictureBox1.Image.Width / PictureBox1.Image.Height
        _ratHeight = PirctureBox1.Image.Height / PictureBox1.Image.Width
        PictureBox1.Size = Panel1.Size
        _originalSize = Panel1.Size
    End If
End Sub
End Class
0
tbm0115

基本的に、画像ビューアが必要です。以前にこれを使用しました: http://cyotek.com/blog/creating-a-scrollable-and-zoomable-image-viewer-in-csharp-part-4

それは素晴らしい働きをします。ただし、これはユーザーコントロールです。

pictureboxの場合、画像からグラフィックを作成し、それを補間する必要があります。ここに例があります: http://www.dotnetcurry.com/ShowArticle.aspx?ID=196

私はこれをチェックしませんでしたが、うまくいくようです。

0
urlreader