Добавление распознавателя жестов перетаскивания

Жест перетаскивания позволяет перетаскивать элементы и связанные с ними пакеты данных из одного расположения на экране в другое, используя непрерывный жест. Перетаскивание можно выполнять в одном приложении или запустить в одном приложении и закончить в другом.

Распознавание жестов перетаскивания поддерживается в iOS, Android и универсальной платформе Windows (UWP). Однако в iOS требуется минимальная версия платформы iOS 11.

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

Процесс включения перетаскивания в приложение выглядит следующим образом:

  1. Включите перетаскивание элемента, добавив объект DragGestureRecognizer в его коллекцию GestureRecognizers.
  2. [Необязательно] Создайте пакет данных. Xamarin.Forms автоматически заполняет пакет данных для элементов управления изображением и текстом, но для другого содержимого потребуется создать собственный пакет данных.
  3. Включите перетаскивание элемента, добавив объект DropGestureRecognizer в его коллекцию GestureRecognizers.
  4. [Необязательно] Обработайте событие DropGestureRecognizer.DragOver, чтобы указать тип операции, разрешенной целью отпускания.
  5. [Необязательно] Обработайте пакет данных для получения отпускаемого содержимого. Xamarin.Forms будет автоматически получать изображения и текстовые данные из пакета данных, но для другого содержимого потребуется обработать пакет данных.

Перетаскивание элементов в CollectionView в настоящее время не поддерживается.

Включение перетаскивания

В Xamarin.Forms распознавание жестов перетаскивания обеспечивается классом DragGestureRecognizer. Этот класс определяет приведенные ниже свойства.

  • CanDrag с типом bool, который указывает, может ли элемент, к которому прикреплен распознаватель жестов, быть источником перетаскивания. Значение по умолчанию этого свойства равно true.
  • DragStartingCommand с типом ICommand, который выполняется при первом распознавании жеста перетаскивания.
  • DragStartingCommandParameter с типом object, который передается как параметр в DragStartingCommand.
  • DropCompletedCommand с типом ICommand, который выполняется при отпускании источника перетаскивания.
  • DropCompletedCommandParameter с типом object, который передается как параметр в DropCompletedCommand.

Эти свойства поддерживаются объектами BindableProperty, то есть эти свойства можно указывать в качестве целевых для привязки и стилизации данных.

Класс DragGestureRecognizer также определяет события DragStarting и DropCompleted, которые срабатывают, если свойство CanDrag имеет значение true. Когда объект DragGestureRecognizer обнаруживает жест перетаскивания, он выполняет DragStartingCommand и вызывает событие DragStarting. Далее, когда объект DragGestureRecognizer обнаруживает завершение жеста отпускания, он выполняет DropCompletedCommand и вызывает событие DropCompleted.

Объект DragStartingEventArgs, который прилагается к событию DragStarting, содержит приведенные ниже свойства.

  • Handled с типом bool — указывает, обрабатывал ли обработчик событие или следует ли продолжать обработку Xamarin.Forms.
  • Cancel с типом bool — указывает, следует ли отменять событие.
  • Data с типом DataPackage — указывает пакет данных, сопровождающий источник перетаскивания. Это свойство доступно только для чтения.

В следующем примере кода XAML показан DragGestureRecognizer, присоединенный к Image:

<image source="monkeyface.png">
 <image.gesturerecognizers>
 <draggesturerecognizer></draggesturerecognizer>
 </image.gesturerecognizers>
</image>

В этом примере можно инициировать жест перетаскивания в Image.

В iOS, Android и UWP жест перетаскивания инициируется с помощью длительного нажатия, за которым следует перетаскивание.

Создание пакета данных

Xamarin.Forms автоматически создаст пакет данных при инициировании перетаскивания для приведенных ниже элементов управления.

  • Текстовые элементы управления. Текстовые значения можно перетаскивать из , , , , , Label, RadioButtonи SwitchTimePicker объектов. EntryEditorDatePickerCheckBox
  • Элементы управления изображениями. Изображения можно перетаскивать из элементов управления Button, Image и ImageButton.

В следующей таблице показаны свойства, которые считываются, и все попытки преобразования, которые выполняются при инициировании перетаскивания текстовых элементов управления.

Для содержимого, отличного от текста и изображений, необходимо самостоятельно создать пакет данных.

Пакеты данных представлены классом DataPackage, который определяет приведенные ниже свойства.

  • Properties с типом DataPackagePropertySet, который представляет собой коллекцию свойств, составляющих данные, содержащиеся в DataPackage. Это свойство доступно только для чтения.
  • Image с типом ImageSource, который является изображением, содержащимся в DataPackage.
  • Text с типом string, который является текстом, содержащимся в DataPackage.
  • View с типом DataPackageView, который является версией DataPackage только для чтения.

Класс DataPackagePropertySet представляет контейнер свойств, хранящийся как Dictionary.

Хранение изображений или текстовых данных

Изображения или текстовые данные могут быть связаны с источником перетаскивания путем сохранения данных в свойстве DataPackage.Image или DataPackage.Text. Это можно сделать в обработчике события DragStarting.

В следующем примере XAML показан DragGestureRecognizer, регистрирующий обработчик для события DragStarting:

<path stroke="Black" strokethickness="4">
 <path.gesturerecognizers>
 <draggesturerecognizer dragstarting="OnDragStarting"></draggesturerecognizer>
 </path.gesturerecognizers>
 <path.data>
 <!-- PathGeometry goes here -->
 </path.data>
</path>

В этом примере DragGestureRecognizer присоединяется к объекту Path. Событие DragStarting срабатывает при обнаружении жеста перетаскивания в Path, который выполняет обработчик событий OnDragStarting:

void OnDragStarting(object sender, DragStartingEventArgs e)
{
 e.Data.Text = "My text data goes here";
}

Объект DragStartingEventArgs, сопровождающий событие DragStarting, имеет свойство Data с типом DataPackage. В этом примере свойству Text объекта DataPackage присваивается string. Затем к DataPackage можно получить доступ при отпускании, чтобы получить string.

Хранение данных в контейнере свойств

Любые данные, включая изображения и текст, могут быть связаны с источником перетаскивания путем сохранения данных в коллекции DataPackage.Properties. Это можно сделать в обработчике события DragStarting.

В следующем примере XAML показан DragGestureRecognizer, регистрирующий обработчик для события DragStarting:

<rectangle stroke="Red" fill="DarkBlue" strokethickness="4" heightrequest="200" widthrequest="200">
 <rectangle.gesturerecognizers>
 <draggesturerecognizer dragstarting="OnDragStarting"></draggesturerecognizer>
 </rectangle.gesturerecognizers>
</rectangle>

В этом примере DragGestureRecognizer присоединяется к объекту Rectangle. Событие DragStarting срабатывает при обнаружении жеста перетаскивания в Rectangle, который выполняет обработчик событий OnDragStarting:

void OnDragStarting(object sender, DragStartingEventArgs e)
{
 Shape shape = (sender as Element).Parent as Shape;
 e.Data.Properties.Add("Square", new Square(shape.Width, shape.Height));
}

Объект DragStartingEventArgs, сопровождающий событие DragStarting, имеет свойство Data с типом DataPackage. Коллекция Properties объекта DataPackage, который является коллекцией Dictionary, можно изменить для хранения необходимых данных. В этом примере словарь Properties изменяется для хранения объекта Square, который представляет размер Rectangle для ключа Square.

Включение отпускания

В Xamarin.Forms распознавание жестов отпускания обеспечивается классом DropGestureRecognizer. Этот класс определяет приведенные ниже свойства.

  • AllowDrop с типом bool, который указывает, может ли элемент, к которому прикреплен распознаватель жестов, быть источником отпускания. Значение по умолчанию этого свойства равно true.
  • DragOverCommand с типом ICommand, который выполняется при перетаскивании источника перетаскивания над целевым объектом отпускания.
  • DragOverCommandParameter с типом object, который передается как параметр в DragOverCommand.
  • DragLeaveCommand с типом ICommand, который выполняется при перетаскивании источника перетаскивания на целевой объект. перетаскивания
  • DragLeaveCommandParameter с типом object, который передается как параметр в DragLeaveCommand.
  • DropCommand с типом ICommand, который выполняется при отпускании источника перетаскивания над целевым объектом отпускания.
  • DropCommandParameter с типом object, который передается как параметр в DropCommand.

Эти свойства поддерживаются объектами BindableProperty, то есть эти свойства можно указывать в качестве целевых для привязки и стилизации данных.

Класс DropGestureRecognizer также определяет события DragOver, DragLeave и Drop, которые срабатывают, если свойство AllowDrop имеет значение true. Когда DropGestureRecognizer распознает источник перетаскивания для цели перетаскивания, он выполняет DragOverCommand и вызывает событие DragOver. Затем, если источник перетаскивания перетаскивается из целевого объекта перетаскивания, DropGestureRecognizer выполняет DragLeaveCommand и вызывает событие DragLeave. Затем, когда DropGestureRecognizer распознает жест перетаскивания на целевой объект перетаскивания, выполняется DropCommand и вызывается событие Drop.

Класс DragEventArgs, который предоставляется с событиями DragOver и DragLeave, содержит следующие свойства:

  • Data с типом DataPackage, который содержит данные, связанные с источником перетаскивания. Это свойство доступно только для чтения.
  • AcceptedOperation с типом DataPackageOperation, который указывает, какие операции разрешены целевым объектом отпускания.

Класс DropEventArgs, который прилагается к событию Drop, содержит приведенные ниже свойства.

  • Data с типом DataPackageView, который является версией пакета данных только для чтения.
  • Handled с типом bool — указывает, обрабатывал ли обработчик событие или следует ли продолжать обработку Xamarin.Forms.

В следующем примере кода XAML показан DropGestureRecognizer, присоединенный к Image:

<image backgroundcolor="Silver" heightrequest="300" widthrequest="250">
 <image.gesturerecognizers>
 <dropgesturerecognizer></dropgesturerecognizer>
 </image.gesturerecognizers>
</image>

В этом примере, когда источник перетаскивания отпускается на целевом объекте отпускания Image, источник перетаскивания копируется в целевой объект отпускания при условии, что источником перетаскивания является ImageSource. Это происходит потому, что Xamarin.Forms автоматически копирует перетаскиваемые изображения и текст в совместимые целевые объекты отпускания.

Обработка события DragOver

Событие DropGestureRecognizer.DragOver можно дополнительно обработать, чтобы указать, какие типы операций разрешены целевым объектом отпускания. Это можно сделать, задав свойство AcceptedOperation с типом DataPackageOperation для объекта DragEventArgs, сопровождающего событие DragOver.

Перечисление DataPackageOperation определяет следующие члены:

  • None указывает, что действие не будет выполнено.
  • Copyуказывает, что содержимое источника перетаскивания будет скопировано в целевой объект отпускания.

При создании объекта DragEventArgs свойству AcceptedOperation по умолчанию присвоено значение DataPackageOperation.Copy.

В следующем примере XAML показан DropGestureRecognizer, регистрирующий обработчик для события DragOver:

<image backgroundcolor="Silver" heightrequest="300" widthrequest="250">
 <image.gesturerecognizers>
 <dropgesturerecognizer dragover="OnDragOver"></dropgesturerecognizer>
 </image.gesturerecognizers>
</image>

В этом примере DropGestureRecognizer присоединяется к объекту Image. Событие DragOver срабатывает, когда источник перетаскивания перетаскивается на целевой объект отпускания, но не отпускается, что приводит к выполнению обработчика событий OnDragOver:

void OnDragOver(object sender, DragEventArgs e)
{
 e.AcceptedOperation = DataPackageOperation.None;
}

В этом примере свойству AcceptedOperation объекта DragEventArgs присваивается DataPackageOperation.None. Таким образом, при перемещении источника перетаскивания на целевой объект отпускания никакие действия не выполняются.

Обработка пакета данных

Событие Drop срабатывает при отпускании источника перетаскивания над целевым объектом отпускания. В этом случае Xamarin.Forms автоматически попытается получить данные из пакета данных, когда источник перетаскивания отпускается над приведенными ниже элементами управления.

  • Текстовые элементы управления. Текстовые значения можно удалять на CheckBoxобъекты, а Editorтакже на объекты, DatePickerа TimePickerRadioButtonEntryLabelSwitchтакже на объекты.
  • Элементы управления изображениями. Изображения можно отпускать над элементами управления Button, Image и ImageButton.

Для содержимого, отличного от текста и изображений, необходимо самостоятельно обработать пакет данных.

Класс DropEventArgs, который прилагается к событию Drop, указывает свойство Data с типом DataPackageView. Это свойство является версией пакета данных только для чтения.

Получение изображений или текстовых данных

Изображения или текстовые данные можно получить из пакета данных в обработчике события Drop с помощью методов, определенных в классе DataPackageView.

Класс DataPackageView включает в себя методы GetImageAsync и GetTextAsync. Метод GetImageAsync извлекает изображение из пакета данных, хранимого в свойстве DataPackage.Image, и возвращает Task. Метод GetTextAsync также извлекает текст из пакета данных, хранимого в свойстве DataPackage.Text, и возвращает Task.

В следующем примере показан обработчик событий Drop, который извлекает текст из пакета данных для Path:

async void OnDrop(object sender, DropEventArgs e)
{
 string text = await e.Data.GetTextAsync();


 // Perform logic to take action based on the text value.
}

В этом примере текстовые данные извлекаются из пакета данных с помощью метода GetTextAsync. Затем можно выполнить действие, основанное на текстовом значении.

Извлечение данных из контейнера свойств

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

Класс DataPackageView определяет свойство Properties с типом DataPackagePropertySetView. Класс DataPackagePropertySetView представляет контейнер свойств только для чтения, хранящийся как Dictionary.

В следующем примере показан обработчик событий Drop, который извлекает данные из контейнера свойств пакета данных для Rectangle:

void OnDrop(object sender, DropEventArgs e)
{
 Square square = (Square)e.Data.Properties["Square"];


 // Perform logic to take action based on retrieved value.
}

В этом примере объект Square извлекается из контейнера свойств пакета данных путем указания ключа Square словаря. Затем можно выполнить действие, основанное на извлеченном значении.

Оглавление

Материалы по теме