このサンプル プログラムでは、インクをズームおよびスクロールする方法を示します。 特に、ユーザーはインクの拡大と縮小を段階的に行えます。 また、ズーム四角形を使用して特定の領域にズームする方法も示します。 最後に、このサンプルでは、異なるズーム比でインクを収集する方法と、ズームされた描画領域内でスクロールを設定する方法を示します。
このサンプルでは、 レンダラー オブジェクトのビューとオブジェクトの変換を使用して、ズームとスクロールを実行します。 ビュー変換は、ポイントとペンの幅に適用されます。 オブジェクト変換は、ポイントにのみ適用されます。 ユーザーは、[モード] メニューの [スケール ペンの幅] 項目を変更することで、どの変換を使用するかを制御できます。
注意
メッセージが送信されたときに、特定のインターフェイス メソッド (InkRenderer.SetViewTransform や InkRenderer.SetObjectTransform など) で一部の COM 呼び出しを実行することは問題です。 メッセージが SENT の場合は、POST メッセージ キューにマーシャリングする必要があります。 このシナリオに対処するには、 InSendMesssageEx を呼び出して POST からのメッセージを処理しているかどうかをテストし、メッセージが送信された場合は自分にメッセージを POST します。
このサンプルでは、次の機能を使用します。
- InkCollector オブジェクト
- Renderer オブジェクトの SetViewTransform メソッド
- Renderer オブジェクトの SetObjectTransform メソッド
フォームの初期化
最初に、このサンプルでは、Windows Vista または Windows XP Tablet PC Edition ソフトウェア開発キット (SDK) で提供されているタブレット PC オートメーション インターフェイスを参照します。
using Microsoft.Ink;
このサンプルでは、スケーリングに役立つ InkCollector、、 myInkCollectorおよびいくつかのプライベート メンバーを宣言しています。
// Declare the Ink Collector object
private InkCollector myInkCollector = null;
...
// The starting and ending points of the zoom rectangle
private Rectangle zoomRectangle = Rectangle.Empty;
// The current zoom factor (1 = 100% zoom level)
private float zoomFactor = 1;
// Declare constants for the width and height of the
// drawing area (in ink space coordinates).
private const int InkSpaceWidth = 50000;
private const int InkSpaceHeight = 50000;
...
// Declare constant for the pen width used by this application
private const float MediumInkWidth = 100;
次に、このサンプルでは、フォームの Load イベント ハンドラーで InkCollector を作成して有効にします。 また、InkCollector オブジェクトの DefaultDrawingAttributes プロパティの Width プロパティが設定されています。 最後に、スクロール バーの範囲が定義され、アプリケーションの UpdateZoomAndScroll メソッドが呼び出されます。
private void InkZoom_Load(object sender, System.EventArgs e)
{
// Create the pen used to draw the zoom rectangle
blackPen = new Pen(Color.Black, 1);
// Create the ink collector and associate it with the form
myInkCollector = new InkCollector(pnlDrawingArea.Handle);
// Set the pen width
myInkCollector.DefaultDrawingAttributes.Width = MediumInkWidth;
// Enable ink collection
myInkCollector.Enabled = true;
// Define ink space size - note that the scroll bars
// map directly to ink space
hScrollBar.Minimum = 0;
hScrollBar.Maximum = InkSpaceWidth;
vScrollBar.Minimum = 0;
vScrollBar.Maximum = InkSpaceHeight;
// Set the scroll bars to map to the current zoom level
UpdateZoomAndScroll();
}
ズームとスクロールの値の更新
インク コレクターの描画領域は、多くのイベントの影響を受けます。
UpdateZoomAndScrollメソッドでは、変換マトリックスを使用して、ウィンドウ内のインク コレクターのスケーリングと変換の両方を行います。
注意
Renderer オブジェクトの SetViewTransform メソッドは、ストロークとペン幅の両方に変換を適用しますが、SetObjectTransform メソッドはストロークにのみ変換を適用します。
最後に、アプリケーションの UpdateScrollBars メソッドが呼び出され、フォームが強制的に更新されます。
// Create a transformation matrix
Matrix m = new Matrix();
// Apply the current scale factor
m.Scale(zoomFactor,zoomFactor);
// Apply the current translation factor - note that since
// the scroll bars map directly to ink space, their values
// can be used directly.
m.Translate(-hScrollBar.Value, -vScrollBar.Value);
// ...
if (miScalePenWidth.Checked)
{
myInkCollector.Renderer.SetViewTransform(m);
}
else
{
myInkCollector.Renderer.SetObjectTransform(m);
}
// Set the scroll bars to map to the current zoom level
UpdateScrollBars();
Refresh();
スクロール バーの管理
メソッドは UpdateScrollBars 、現在のウィンドウ サイズ、ズーム設定、 InkCollector 内のスクロール位置で正しく動作するようにスクロール バーを設定します。 このメソッドは、垂直スクロール バーと水平スクロール バーの大きな変更と小さな変更値を計算します。 また、スクロール バーの現在の値と、表示する必要があるかどうかを計算します。
Renderer オブジェクトの PixelToInkSpace メソッドは、ピクセルからズームされた座標空間への変換を処理し、ビューとオブジェクトの変換によって適用されるスケーリングとスクロールを考慮します。
// Create a point representing the top left of the drawing area (in pixels)
Point ptUpperLeft = new Point(0, 0);
// Create a point representing the size of a small change
Point ptSmallChange = new Point(SmallChangeSize, SmallChangeSize);
// Create a point representing the lower right of the drawing area (in pixels)
Point ptLowerRight = new Point(hScrollBar.Width, vScrollBar.Height);
using (Graphics g = CreateGraphics())
{
// Convert each of the points to ink space
myInkCollector.Renderer.PixelToInkSpace(g, ref ptUpperLeft);
myInkCollector.Renderer.PixelToInkSpace(g, ref ptLowerRight);
myInkCollector.Renderer.PixelToInkSpace(g, ref ptSmallChange);
}
// Set the SmallChange values (in ink space)
// Note that it is necessary to subract the upper-left point
// value to account for scrolling.
hScrollBar.SmallChange = ptSmallChange.X - ptUpperLeft.X;
vScrollBar.SmallChange = ptSmallChange.Y - ptUpperLeft.Y;
// Set the LargeChange values to the drawing area width (in ink space)
// Note that it is necessary to subract the upper-left point
// value to account for scrolling.
hScrollBar.LargeChange = ptLowerRight.X - ptUpperLeft.X;
vScrollBar.LargeChange = ptLowerRight.Y - ptUpperLeft.Y;
// If the scroll bars are not needed, hide them
hScrollBar.Visible = hScrollBar.LargeChange < hScrollBar.Maximum;
vScrollBar.Visible = vScrollBar.LargeChange < vScrollBar.Maximum;
// If the horizontal scroll bar value would run off of the drawing area,
// adjust it
if(hScrollBar.Visible && (hScrollBar.Value + hScrollBar.LargeChange > hScrollBar.Maximum))
{
hScrollBar.Value = hScrollBar.Maximum - hScrollBar.LargeChange;
}
// If the vertical scroll bar value would run off of the drawing area,
// adjust it
if(vScrollBar.Visible && (vScrollBar.Value + vScrollBar.LargeChange > vScrollBar.Maximum))
{
vScrollBar.Value = vScrollBar.Maximum - vScrollBar.LargeChange;
}
四角形へのズーム
パネル イベント ハンドラーは pnlDrawingArea 、ウィンドウへの四角形の描画を管理します。 [モード] メニューで [Zoom To Rect] コマンドがオンになっている場合、 MouseUp イベント ハンドラーはアプリケーションの ZoomToRectangle メソッドを呼び出します。 メソッドは ZoomToRectangle 、四角形の幅と高さを計算し、境界条件をチェックし、スクロール バーの値とスケール ファクターを更新してから、アプリケーションの UpdateZoomAndScroll メソッドを呼び出して新しい設定を適用します。
フォームを閉じる
フォームの Dispose メソッドは 、InkCollector オブジェクトを破棄します。