Главная » WPF » Рукописный ввод

0

Для рукописного  ввода базовым типом данных является класс Stroke, опреде# ленный  в пространстве  имен System.Windows.Ink. В некоторых  отношениях ру# кописные данные намного проще обогащенного текста; по существу, это не более чем последовательности пакетов, получаемых  от дигитайзера.

был впервые включен в версию Windows XP для Tablet  PC (если не вспоминать  о мифических версиях  Pen Windows). Для него разработан двоичный  формат  хранения  (ISF  – ink serialized format)  и модели программиро# вания для COM  и .NET. При разработке  WPF мы хотели полностью  интегриро# вать рукописный ввод в состав платформы. Двоичный формат почти не изменил# ся, но модель программирования все же была немного модифицирована для луч# шей увязки  с остальными частями платформы.

О двоичном  формате  можно вообще не говорить  без ущерба для понима#

ния.  Достаточно   знать,  что  объектная   модель  Stroke   реализована  поверх очень эффективного двоичного потока. Эта деталь объясняет некоторые странности  в ее интерфейсе. В большинстве  случаев  все необходимые  дан# ные можно  с помощью  простого  StylusPoint API,  но, если нужен  доступ ко всем  данным,  то  к  вашим  услугам  более  развитый   StylusPointDescription API10. Чтобы продемонстрировать работу с рукописным вводом, мы вос# пользуемся элементом  управления InkCanvas и будем  обрабатывать  собы# тие InkCollected (рис. 3.32):

Рис. 3.33. Изменения отображения с помощью дополнительных свойств из объектной модели рукописного ввода

Как вы, наверное, уже начали  осознавать,  пакеты стилоса устроены  доволь# но сложно.  Причина в том, что разные  производители могут расширять поток рукописного ввода. Так, производители дигитайзеров очень часто вводят до# полнительные кнопки. Другой пример – данные об угле наклона  пера и даже о его вращении.  Конечная  цель – собрать всю возможную  информацию о манере

письма  или  рисования конкретного человека,  чтобы цифровой  результат  был не хуже или даже лучше получающегося при использовании обычного пера и бумаги.

Чтобы получить  дополнительные данные, мы должны сообщить объектной модели рукописного  ввода, какие данные должны передаваться из пакетов в мо# дель. Можно  запрашивать данные глобально  (задав  свойство DefaultStylusPoint Description объекта InkCanvas) или для каждого штриха (с помощью метода Reformat  объекта StylusPointCollection).

Многие современные планшеты поддерживают свойства XTilt и YTilt (углы наклона в двух направлениях),  которые открывают возможность для очень инте# ресных визуализаций. Но в примере ниже я ограничусь кнопкой BarrelButton, имеющейся в большинстве планшетов. Первыми тремя свойствами в запросе должны быть X, Y и NormalPressure. Если кнопка пера нажата, мы рисуем окруж# ности по#другому (рис. 3.33):

public InkTest() { InitializeComponent();

_ink.DefaultStylusPointDescription = new StylusPointDescription(

new StylusPointPropertyInfo[]

{

new StylusPointPropertyInfo(StylusPointProperties.X), new StylusPointPropertyInfo(StylusPointProperties.Y),

new StylusPointPropertyInfo(StylusPointProperties.NormalPressure), new StylusPointPropertyInfo(StylusPointProperties.BarrelButton),

});

}

void Collected(object sender, InkCanvasStrokeCollectedEventArgs e) {

_overlay.Children.Clear();

Brush fill = new SolidColorBrush(Color.FromArgb(120, 255, 0, 0)); Brush altFill = new SolidColorBrush(Color.FromArgb(120, 0, 255, 0)); foreach (StylusPoint pt in e.Stroke.StylusPoints) {

double markerSize = pt.PressureFactor * 35.0; Ellipse marker = new Ellipse(); Canvas.SetLeft(marker, pt.X   markerSize / 2); Canvas.SetTop(marker, pt.Y   markerSize / 2); marker.Width = marker.Height = markerSize; marker.Fill = fill;

if (pt.GetPropertyValue(StylusPointProperties.BarrelButton)

!= 0) {

marker.Fill = null; marker.Stroke = Brushes.Black; marker.StrokeThickness = 2.0;

}

_overlay.Children.Add(marker);

}

}

Источник: К. Андерсон  Основы  Windows Presentation Foundation. Пер. с англ. А. Слинкина — М.: ДМК Пресс, 2008 — 432 с.: ил.

По теме:

  • Комментарии