The principle of drag and drop means. Drag and drop technology

It's easier to take something and put it than to write what you need to take and where to put it. Of course, without a mouse, or a similar device, you can’t select or specify anything, but even in the current state of things, using the drag and drop idea is very natural and comfortable.

The scope of the idea is not only online stores, digital libraries, search or Information Systems, but also the applied area. The idea is very applicable in the development of sites and their elements, created and maintained interactively, without the participation of a programmer.

Description of the idea

Select, move and put - the idea is natural and convenient. It is simply amazing that it was not born when the mouse became an indispensable accessory for the computer.

The most obvious example is choosing a product in an online store. Select the desired product with the mouse and drag it to the shopping cart - simply, naturally and conveniently. File Upload: Taking a document outside of the browser window and placing it on a page element, thus initiating the transfer of the document to the server, is also a practical idea.

For the developer, the idea of ​​"drag and drop" is the manipulation of page elements without manually recalculating the coordinates and sizes of tags, the ability to select multiple elements and align them, and move the sides of block tags.

HTML and CSS - great languages descriptions of tags and their design styles, but when a developer has the ability to interactively manipulate page elements without manually recalculating coordinates and sizes, this makes the work more comfortable and efficient.

Easy file transfer

"Drag and drop": translation from English into Russian literally sounds like "drag and drop." In practice, it sounds and works better: chose, transferred and let go - simply and naturally.

Implementing file transfers on a page to a page, to a server, or for other use is very simple.

In this example, several files on the desktop were selected with the mouse (left figure). On the selection, the left mouse button was pressed and the selected "went" to the basket. The browser itself showed how this happens, wrote a “copy” hint and created the outlines of the files being moved around.

When the mouse was over the basket, the visitor released the left mouse button, the drag and drop event took place and on the site page (bottom image), the JavaScript code was able to receive and process all the files that the visitor provided to the page (site).

Implementation Description

The code that performs this procedure is very simple. Even a novice developer can repeat it in any use cases.

Here, the user interface is represented by two tags: scPlaceFile (this is the basket itself where you want to put files) and scPlaceFiles (this is the result of processing files, in this case a list of them).

The logic of the page is as follows. When the page is loaded in the browser, the "ondrop" event handler is assigned in the basket - put, the rest of the events are blocked and not used.

The page works normally, but as soon as the visitor selects the file (files) and drags them to the basket image, that is, to the scPlaceFile tag, the “files have arrived” event will be processed.

This handler simply displays a list of files. Their number is in event.dataTransfer.files.length, and information about each file is in event.dataTransfer.files[i].name. What to do with the received data is determined by the developer, in this case, a list of received files is simply formed.

Once processed, the event is blocked and not propagated. This is necessary so that the browser does not engage in amateur activities and does not interfere with the processing of the information received.

DnD and external data

Uploading images to the server in "drag and drop" is a common practice in this technology. Typically, a developer creates a file upload form (1) that works in the usual way (2). The visitor can normal mode select files and upload them.

However, if a visitor drags and drops to a certain place in the form, then the file name field (files) will be filled in automatically.

This good decision. It is, of course, very difficult to admit that there is no mouse on the computer. But it is better to develop the user interface in the usual way and in the DnD implementation.

DnD and internal data

Taking care of the interests of the visitor is always important, but the concerns of the developer also matter. You can implement "drag and drop" not only by standard means, but also by handling mouse events on page elements.

The task of calculating tag coordinate values ​​and their sizes arises constantly. Manual calculation is good practice, but the interactive option is more convenient. All tags are always rectangular in shape, and by monitoring mouse events on the sides of elements, you can create the ability to automatically move elements to the right place on the page, or change them.

Handling the mouse button click event - remembering the coordinates of the click location, for example, one of the sides of the element. Move the mouse - the side moves in the desired direction. Releasing the mouse button - the side stops and its coordinates change. This way you can change the position of the element or its size.

It's not formally drag and drop, but the effect is similar and practical. By making universal handlers for any page element, you can get a good interactive result, speed up development and simplify the code.

Visual and manual programming

A mouse on a computer and fingers on a smartphone are completely different approaches to the implementation of the user interface (visitor, developer). It is a completely natural and modern requirement for cross-browser compatibility.

All this together makes it difficult to create pages, but applying the idea of ​​\u200b\u200bdrag and drop in it standard form, using its events, combining this idea with the usual events on elements, you can implement a mechanism in which the creation of the page will occur visually.

Now let's look at the selection of an element or elements. Selection fact - the appearance of a context menu, for example, the goal is to align the selected one (left, right, center), or distribute elements vertically or horizontally with the same step, or change their size (minimum, maximum).

Automatic recalculation of coordinates and dimensions is preferable to manual. Fewer mistakes - the goal is reached faster. In addition, you can make a page in one browser, save the position and size of elements. By opening this page on a smartphone, you can correct the coordinates and dimensions and remember them for specific model smartphone or browser version.

So the same page without manual compliance with the cross-browser compatibility requirement will have different data to display on various devices and in different browsers.

If you allow the visitor to perform these procedures on their own, as well as select the necessary page elements from among those provided by the developer, it is possible to ensure cross-browser compatibility and the required functionality of the page, taking into account the user's opinion.

The Drag and Drop feature can help boost your iPad's performance. Here's how you can use it.

So you can move a file from one cloud storage service to another, copy text from Safari into a text editing app to add a quote or create backup certain photos in the file storage application.

How to drag and drop photos, files and text

1. Touch and hold the photo, file, or highlighted text you want to drag to another app.

2. Drag the element to the desired location in this application or another that you have open in Slide Over or Split View and release.

How to drag and drop multiple photos or files at once

1. Touch and hold one of the photos or files you want to drag.

2. While dragging the current item, tap another photo or file that you also want to drag. Do it again with as many elements as you want to move.

3. Drag all selected objects to the designated place in another application that you have open in Slide Over or Split View and release them.

How to drag text from one application to another

1. Tap and hold on the part of the text you want to drag to select it.

2. Use selection points to highlight the rest of the text you want to drag.

3. Press and hold the selected text.

4. Drag the text to the application where you want to place it and release it.

How to change the position of icons of several applications at once using "Drag and Drop"

While most iOS drag and drop functionality only works on the iPad, this trick actually works on both the iPhone and iPad. This allows you to organize the location of applications on the home screen using « Drag and Drop" instead of moving them one by one.

1. Touch and hold the icon for the app you want to reposition on the home screen.

2. Tap additional apps that you also want to move.

3. Drag these apps to the page or folder where you want them to be and drop them.

182

In this example, we select a div element and make it moveable by calling on it draggable() method. As shown in the figure below, in the opened document, the element takes its usual position, but after that it can be moved with the mouse pointer to any place in the browser window:

The drag and drop feature is useful on its own, but it's even more useful when used in conjunction with the Droppable interaction, which is described next.

Draggable interaction is implemented solely through the use of specific HTML markup and CSS styles. This means that this functionality will work in almost any browser, but elements endowed with it will not be able to work with similar native drag-and-drop facilities. operating systems.

Drag-and-drop operations defined by the HTML5 specification are usually implemented using native operating system mechanisms. If you're using the jQuery UI drag-and-drop mechanism, it's best to disable the HTML5 equivalents to avoid conflicts. To do this, set the draggable attribute of the document's body element to false.

Customizing Draggable Interaction

There are many customization options for Draggable interaction. The most important properties covered in the following sections are summarized in the table below:

Draggable interaction properties
Property Description
axis Restricts movement to certain directions. The default value is false, which means no restrictions, but you can also specify the value "x" (move only along the x-axis) or "y" (move only along the y-axis)
containment Restricts the location of the floating element to a specific area of ​​the screen. Supported value types are described in the table below, with the corresponding example. The default value is false, it means no restrictions
delay Specifies the amount of time an element must be dragged before it moves. The default value is 0, which means no delay
distance Specifies the distance the user must drag an element from its starting position before it actually moves. The default value is 1 pixel
grid Forces binding of the moved element to the grid cells. The default value is false, which means no binding

Restriction of directions of movement

There are several ways in which you can restrict the movement of an element to certain directions. The first of these is to use the axis option, which allows you to limit the direction of movement to the X or Y axis. An example is shown below:

...

Drag vertically
Drag horizontally
Run Example

In this example, we define two div elements, select them with jQuery and call the draggable() method. This method is passed an object that initially restricts both divs to move along the x-direction. By then applying the jQuery filter() method, we can select the dragV element without jQuery searching the entire document again and set it to a different allowed move direction - along the Y axis. Thus, we get a document in which one div element can only be dragged in the vertical direction, and the other - only in the horizontal direction. The result is shown in the figure:

Restricting the allowable area to move an element

You can also limit the area of ​​the screen where you can drag an element. For this, the containment option is used. The value formats that can be specified in this option are described in the table below:

An example of using the containment option is shown below:

...

Drag horizontally
Drag inside parent
Run Example

In this example, both elements are constrained to move in such a way that they can only be dragged inside parent element, which is a fixed-sized div element. For one of the movable divs with the axis option typed additional constraint, which means that it can only move horizontally inside the parent element. The result is illustrated in the figure:

Restricting the ability to move an element to grid cells

The grid option allows you to set the binding of the moved element to the grid cells. This option accepts an array of two elements that specifies the width and height of the grid cells in pixels. An example of using the grid option is shown below:

...

drag me
Run Example

In this example, the grid is set to 100 pixels wide and 50 pixels high. When you drag an element, it "jumps" from one (invisible) cell to another. The snapping effect is a great use case for the interaction functionality, but it's hard to convey with screen shots.

You can create a snapping effect for only one direction by setting the free-motion axis to 1. For example, if you set the grid option to , the element will snap to 100px wide grid cells when moving horizontally, but it will move freely vertically.

Travel Delay

There are two options that allow you to delay the dragging of a floating element. With the delay option, you can set the time in milliseconds that the user must drag the mouse pointer before the element is actually moved. Another kind of delay is provided by the distance option, which specifies the distance, in pixels, that the user must drag the mouse pointer before an element follows it.

An example of using both settings is shown below:

...

Block with time delay
Block with minimum distance
Run Example

In this example, there are two floating elements, one of which has a delay set with the delay option, and the other with the distance option.

In the case of the delay specified by the delay option, the user must drag for the specified amount of time before it actually moves the element. In this example, the duration of this gap is 1000 ms. It is not necessary to move the mouse during this time, but the mouse button must remain pressed during the entire delay period, after which the element can be moved by moving the mouse. After the delay time has elapsed, the element being moved will snap to the position of the mouse pointer, subject to the constraints imposed by the grid, region, and axis options discussed earlier.

The distance option has a similar effect, but in this case the user must drag the mouse pointer at least the specified number of pixels in any direction from the element's starting location. The item being moved will then jump to the current pointer location.

If you apply both settings to the same element, then the element being moved will not move until both delay criteria are met, i.e. until the attempt to drag the element lasts for the specified time and until the mouse pointer moves the specified number of pixels.

Using Draggable Interaction Methods

All of the methods defined for Draggable interaction are part of the set of basic methods that you've already seen in widgets. Methods specific to Draggable interaction are not provided, so we won't cover them in detail. The list of available methods is shown in the table below:

Using Draggable Interaction Events

Draggable interaction supports a simple set of events that notify when an element is being dragged. These events are described in the table below:

As with widget events, these events can also be reacted to. An example of handling the start and stop events is shown below:

...

drag me
Run Example

This example uses the start and stop events to change the text content of an element during the dragging process. This advantage comes from the fact that Draggable interaction is implemented entirely using HTML and CSS: you can use jQuery to change the state of a floating element even while it is moving across the screen.

Using the Droppable interaction

In some situations, dragging an element alone can be enough, but it is most useful when used in conjunction with the Droppable interaction.

Elements to which the Droppable interaction has been applied (accepting elements) gain the ability to accept droppable elements created with the Draggable interaction.

The receiving elements are created with droppable() method, but to get useful functionality, you will need to create event handlers from among those defined for this kind of interaction. The available events are shown in the table below:

Droppable interaction events
Event Description
create Occurs when a Droppable interaction is applied to an element
activate Occurs when the user starts dragging a floating element
deactivate Occurs when the user stops dragging a floating element
over Occurs when the user drags a floating element over the receiving element (but assuming the mouse button has not yet been released)
out Occurs when the user drags a floating element outside of the receiving element
drop Occurs when the user leaves a floating element on the receiving element

An example of creating a simple receiving element that has a single drop event handler is given below:

...

leave here
drag me
Run Example

In this example, a div element is added to the document, the text content of which is represented by the string "Leave it here". We select this element using jQuery and call the droppable() method, passing it a settings object that defines a handler for the drop event. The response to this event is to change the text of the floating element using the text() method.

The drag-and-drop interactive experience created in this example is the simplest, but it provides a useful context for explaining the possibilities. joint work Draggable and Droppable interactions. The different stages of the process of dragging and dropping elements are illustrated in the figure:

All this looks very simple. We drag the element being moved until it is above the receiving element and release it. The dropped element remains where it was left, and its text content changes in response to the occurrence of the drop event. The following sections show you how to use other Droppable interaction events to improve the user experience.

Target Receiving Object Highlight

By using the activate and deactivate events, you can highlight the target receiving object when the user begins the process of dragging an element. In many situations, this idea is very fruitful because it gives the user a reliable indication of which elements are part of the drag-and-drop model. The relevant example is shown below:

... $(function() ( $("#draggable").draggable(); $("#droppable").droppable(( drop: function() ( $("#draggable").text("Dropped ") ), activate: function() ( $("#droppable").css(( border: "medium double green", backgroundColor: "lightGreen" )); ), deactivate: function() ( $("#droppable ").css("border", "").css("background-color", ""); ) )); )); ... Run the example

As soon as the user starts dragging the element, the activate event - associated with our receiving element - fires, and the handler function uses the css() method to change CSS property border and background-color of this element. As a result, the target receiving element is highlighted, indicating to the user that there is a connection between it and the element being moved.

The deactivate event is used to remove CSS property values ​​from the receiving element and reset it as soon as the user releases the mouse button. (This event fires whenever the dragging of an element stops, regardless of whether the dragged element is left on the receiving element or not.) This process is illustrated in the figure:

Element Overlap Handling

Drag-and-drop technology can be improved by adding over and out event handling to it. The over event occurs when 50% of the element being moved is above any part of the receiving element. The out event fires when previously overlapping elements no longer overlap. An example response to these events is shown below:

$(function() ( $("#draggable").draggable(); $("#droppable").droppable(( drop: function() ( $("#draggable").text("Dropped") ) , activate: function() ( $("#droppable").css(( border: "medium double green", backgroundColor: "lightGreen" )); ), deactivate: function() ( $("#droppable"). css("border", "").css("background-color", ""); ), over: function() ( $("#droppable").css(( border: "medium double red", backgroundColor : "red" )); ), out: function() ( $("#droppable").css("border", "").css("background-color", ""); ) )); ) ); Run Example

The same handler functions are used here as in the previous example, but in this case they are associated with the over and out events. When at least 50% of the floating element overlaps with the receiving element, it is framed and its background color changes, as shown in the figure:

This 50% limit is called the tolerance threshold, which can be set when creating the receiving element, as will be shown next.

Droppable interaction setup

The Droppable interaction has a number of properties that you can modify to customize its behavior. These properties are listed in the table below:

Droppable interaction properties
Property Description
disabled If this option is true, the Droppable interaction functionality is initially disabled. Default value is false
accept Narrows down the set of floating elements that the receiving element will respond to. The default value is *, it matches any element
activeClass Defines a class that will be assigned in response to the activate event and removed in response to the deactivate event
hoverClass Defines a class that will be assigned in response to an over event and removed in response to an out event.
tolerance Specifies the minimum degree of overlap at which the over event occurs

Restriction on allowed floating elements

You can limit the set of droppable elements that will be accepted by an element that has the Droppable interoperability functionality by using the accept option. The value of the accept option should be a selector. As a result of this event, Droppable interactions will only occur if the element being moved matches the specified selector. The relevant example is shown below:

...

leave here
Element 1
Element 2
Run Example

In this example, there are two floating elements with IDs drag1 and drag2. When creating an accepting element, the accept option is used, with which we indicate that only the drag1 element will be an acceptable floating element.

When dragging the drag1 element, you will see the same effect as in the previous examples. The activate, deactivate, over, and out events will fire on the receiving element at the appropriate times. At the same time, if you drag a drag2 element that does not match the selector specified in the accept parameter, then these events will not be fired. This element can be freely moved, but it will not be accepted by the receiving element.

Note the change in the way you select an acceptable floating element on which to call the text() method. When there was only one floating element in the document, the id attribute was enough for this:

Drop: function() ( $("#draggable").text("Dropped") ),

In this example, there are two floating elements, and selecting by the id attribute will not give the desired result, since the text in this case will always change in the same floating element, regardless of which one is acceptable to the receiving element.

The solution is to use the ui object that jQuery UI provides as an additional argument to each event handler. The draggable property of the ui object returns a jQuery object containing the element that the user is dragging or trying to drop on the target element, allowing the desired element to be selected as follows:

Drop: function(event, ui) ( ui.draggable.text("Dropped") ),

Changing the overlap threshold

By default, the over event only fires when at least 50% of the element being moved overlaps the receiving element. The amount of this threshold overlap can be changed using the tolerance option, which can take on the values ​​shown in the table below:

The two values ​​I most often use, fit and touch, are the ones that make the most sense to users. I use the fit value when the dragged element should remain in the area of ​​the receiving element where it was moved, and the touch value when the dragged element should return to its original position (an example will be given later). An example of using the fit and touch parameters is shown below:

The clone value tells jQuery UI to create a copy of the floating element along with all of its content and use the result as a helper element. The result is shown in the figure:

The helper element is removed when the user releases the mouse button over the element being moved, leaving the element being moved and the receiving element in their original positions.

As shown in the figure, the original floating element remains in its place and only the auxiliary element moves across the screen following the mouse pointer. If the size of the element being moved is large, as in our example, then it covers the rest of the elements of the document, so it will be difficult for the user to even track the position of the receiving element. This problem can be dealt with by providing a function as the value of the helper option, as shown in the example below:

... $(function() ( $("div.draggable")..png"/>") ) )); $("#basket").droppable(( activeClass: "active", hoverClass: "hover" )); )); ... Run the example

When the user starts dragging an element, jQuery UI calls a function, parameter helper and uses the returned element as a moveable object. In this case, I'm using jQuery to create the img element. The result is shown in the figure:

The small image acts as a placeholder for the floating element, making it much easier to keep track of other elements in the document.

The ui object that jQuery UI passes to Droppable interaction events contains a helper property, and this property can be used to manipulate the helper element while it is being dragged. An example of using this property in conjunction with the over and out events is shown below:

... $(function() ( $("div.draggable")..png"/>") ) )); $("#basket").droppable(( activeClass: "active", hoverClass: "hover", over: function(event, ui) ( ui.helper.css("border", "thick solid #27e6ed") ) , out: function(event, ui) ( ui.helper.css("border", "") ) )); )); ...

Here the over and out events and the ui.helper property are used to display a border around the helper element when it overlaps the host element. The result is shown in the figure:

Snap to the edges of elements

Via snap options it is possible to achieve that the element being moved is "attracted" to the edges of the elements next to which it passes. This option takes a selector as its value. The floating element will snap to the edges of any element that matches the specified selector. An example of using the snap option is shown below:

Run Example jQuery UI

Basket
Tether here
drag me

When a moveable element approaches one of the matched elements, it is sort of "pulled" to it in such a way that their adjacent edges touch. For such a binding, you can select any element, not just the receiving one. In this example, I've added a div element and set the snap option to a value that selects this element in the document, as well as the receiving element.

There are a couple of sub-options that let you fine-tune how elements behave with regard to anchoring. One of them is snapMode option. It can be used to specify the type of binding. The following values ​​are allowed: inner(snap to inner edges of elements), outer(snap to outer edges of elements) and both(snap to all edges; default).

snapTolerance option allows you to specify how far the floating element must approach the edge of the target element before snapping occurs. The default value is 20 which means 20 pixels. The example uses a value of 50, which corresponds to an anchor at a greater distance. It is very important to choose the right value for this option. If the value of the snapTolerance option is too low, then the user may not notice the snapping effect, and if it is too high, the element being moved will start to jump unexpectedly, snapping to elements far away.

For the VCL library, Borland has implemented its own version of the Drag&Drop interface (translated as "drag"). This interface is internal - you can send and receive any Delphi controls inside the form "(except for the form itself). It is implemented without using the corresponding Windows API functions - they must be used when organizing communication with other tasks by dragging and dropping.

By pressing the left mouse button over the control, we can "drag" it to any other element. From the programmer's point of view, this means that at the moments of dragging and releasing the key, certain events are generated that transmit all the necessary information - a pointer to the dragged object, current cursor coordinates, etc. The event receiver is the element on which the this moment the cursor is located. The handler for such an event must tell the system whether the given control accepts the "sending" or not. When the button is released over the receiver control, one or two more events are fired, depending on the receiver's readiness.

CancelDrag Cancels the current drag-and-drop or drag-and-dock operation.

Function FindDragTarget (const Pos: TPoint ;AllowDisabled: Boolean ): TControl ;

The function returns an object of the base class TControl , which refers to the screen position with the coordinates specified by the Pos parameter. This function is used to determine the potential recipient of a drag-and-drop or drag-and-dock operation. If no window control exists for the specified position, then the function returns nil . The AllowDisabled parameter determines whether disabled objects will be taken into account.

Function IsDragObject(Sender: TObject ): Boolean ;

The function determines whether the object specified in the Sender parameter is a descendant of the class TDragObject . This function can be used as the Source parameter in the OnDragOver and OnDockOver event handlers to determine whether the dragged object will be accepted. Also function IsDragObjectcan be used as the Source parameter in the OnDragDrop and OnDockDrop event handlers in order to correctly interpret the dragged object.

DragMode, DragCursor properties, BeginDrag, OnDragOver, OnDragDrop, OnEndDrag, OnStartDrag methods, Accept parameter

The process of dragging information from one object to another with the mouse is widely used in Widows. You can move files between folders, move folders themselves, and more.

All properties, methods, and events associated with the drag and drop process are defined in the TControl class, which is the parent of all Delphi visual components. Therefore, they are common to all components.

The beginning of the drag is determined by the DragMode property, which can be set at design time or programmatically equal to dmManual or dmAutomatic. The value of dmAutomatic (automatic) determines the automatic start of the dragging process when the user clicks the mouse button over the component. However, in this case, the OnMouseDown event associated with the user pressing the mouse button does not occur for this component at all.

The interface for transferring and receiving components appeared a long time ago. It provides interaction between two controls during application execution. In this case, any necessary operations can be performed. Despite the simplicity of implementation and the age of development, many programmers (especially beginners) consider this mechanism obscure and exotic. However, using Drag-and-Drop can be very useful and easy to implement. Now we will verify this.

In order for the mechanism to work, two controls must be configured accordingly. One must be the source (Source), the second - the receiver (Target). In this case, the source does not move anywhere, but is only registered as such in the mechanism.

Believe me, it's easy enough to transform X,Y coordinates, passed in the parameters of the OnDragOver and OnDragDrop events, into form coordinates.

Work with the Left and Top properties of the component that the cursor is hovering over. I will give a simple example. Place a Memo component on the form and set its Align property to alTop. Place a panel on the form, also set the Align property to alTop and set the Height property to a small value, say 6 or 7 pixels. Set DragMode to dmAutomatica and DragCursor to crVSplit. Place another Memo component and set Align to alClient. Select both Memos at the same time, the panel, and create a common OnDragOver event handler as shown below:

Recently I had an idea to develop an android game. To begin with, I decided to write chess. I thought technology Drag and Drop perfect for implementing the mechanism for moving shapes. For the uninitiated, I note that the drag and drop method is in the possibility of dragging some graphic objects onto others and performing one or another action after releasing. The simplest example- remove the shortcut from your PC desktop by dragging it to the trash. By "throwing" the label into the trash, we tell the system that we want to make these two objects interact. The system receives our signal and decides what action it should take. Drag and drop has become widespread due to its intuitive clarity. This approach is backed up by our experience of interacting with real world objects and works great in a virtual environment. As for chess, using drag and drop it is technologically easier to determine the cell where the user dragged the piece, since it is not necessary to calculate the cell number from the coordinates of the drop point. This work will be taken over by the virtual machine.

Purposes of using Drag n Drop technology

Using drag and drop technology allows me to solve three problems with little blood:

  1. Movement visualization. When the user touches a shape and starts moving it around the screen, the shape is replaced by a smaller drawing. Thus, the user understands that the figure is captured.
  2. I limited the area of ​​movement of the figure to the dimensions of the board.
  3. If the user releases the shape in the wrong place, it should return to its original position.

The tasks are defined, let's start their implementation.

Replace ImageView on touch

All of my shapes are ImageView objects. Unfortunately, it turned out that the implementation of Drag & Drop in Android does not allow "right out of the box" to replace the image of an object when it is touched. Nevertheless, this task is quite solvable by means of the API. We need to perform a number of simple steps:

  1. Create a DragShadowBuilder object.
  2. Call the startDrag method.
  3. Hide our ImageView that displays the shape by calling the setVisibility method with the View.INVISIBLE parameter. As a result, only the DragShadowBuilder object will remain on the screen, which will signal to the user that the shape has been captured.

These actions must be implemented in the OnTouchListner handler of the ImageView object. To do this, we will override the onTouch method:

@Override public boolean onTouch(View view, MotionEvent motionEvent) ( if (motionEvent. getAction() == MotionEvent. ACTION_DOWN) ( ClipData clipData= ClipData. newPlainText("" , "" ) ; View. DragShadowBuilder dsb= new View. DragShadowBuilder (view) ;view.startDrag(clipData, dsb, view, 0 ) ;view.setVisibility(View.INVISIBLE) ; return true ; ) else ( return false ; ) )

Everything is very simple. So, with the substitution of the image figured out, let's move on to the next task.

Limiting the drag area for the drag drop function

Restricting the drag area is related to one problem. The fact is that if you release the shape outside the board, the drop event will not happen, because the user dropped the object in an empty place, and the object has nothing to interact with. As a result, the figure will not return to its original state and will remain forever hidden. I've spent a lot of time reading the documentation, but have not found a way to limit the drag area of ​​objects. The revelation came suddenly. I do not need to limit the area at all, I need to know whether the user has released the figure correctly or not.

Determining the correct release
I found answers to my questions in the section "handling drag end events" on the Android Developers site. Here are a few key points:

  1. When the user finishes dragging, the ACTION_DRAG_ENDED event is fired in the DragListeners handler.
  2. In the DragListener, you can get more detailed information about the drag operation by calling the DragEvent.getResult() method.
  3. If the DragListener returns true in response to an ACTION_DROP event, the getResult call will also return true, otherwise it will return false.

So I need to catch the ACTION_DRAG_ENDED event and call the getResult method. If it returns false, then the user dragged the shape off the board and I need to make the ImageView visible.

@Override public boolean onDrag(View view, DragEvent dragEvent) ( int dragAction= dragEvent. getAction() ; View dragView= (View) dragEvent. getLocalState() ; if (dragAction== DragEvent. ACTION_DRAG_EXITED) ( containsDragable= false ; ) else if (dragAction== DragEvent. ACTION_DRAG_ENTERED) ( containsDragable= true ; ) else if (dragAction== DragEvent. ACTION_DRAG_ENDED) ( if (dropEventNotHandled(dragEvent) ) ( dragView. setVisibility(View. VISIBLE) ; ) ) else if (dragAction= = DragEvent. ACTION_DROP& amp;& amp; containsDragable) ( checkForValidMove((ChessBoardSquareLayoutView) view, dragView) ; dragView. setVisibility(View. VISIBLE) ; ) return true ; ) private boolean dropEventNotHandled(DragEvent dragEvent) ( return ! dragEvent. getResult( ) ; )

Now the user can release the figure anywhere, and nothing terrible will happen.

Determination of allowed moves

The last part of the article is devoted to checking the validity of the move that the user is trying to make. Before discussing this topic in detail, I will make a small remark explaining the structure of my application. The checkerboard is represented as a TableLayout, and each cell is a descendant of a LinearLayout and has an OnDragListener.

In addition, each OnDragListener refers to a "mediator" object, which takes care of the interaction of game objects and remembers the position of the current cell.

When the user drags a shape over a cell, the following actions are possible:

  1. Using the ACTION_DRAG_ENTERED event to set the 'containsDraggable' variable to true.
  2. Using the ACTION_DRAG_EXITED event to set the 'containsDraggable' variable to false.
  3. Using the ACTION_DROP event to query the middleware if a shape is allowed to be placed in this cell.

Below is the code that implements the described logic

@Override public boolean onDrag(View view, DragEvent dragEvent) ( int dragAction= dragEvent. getAction() ; View dragView= (View) dragEvent. getLocalState() ; if (dragAction== DragEvent. ACTION_DRAG_EXITED) ( containsDragable= false ; ) else if (dragAction== DragEvent. ACTION_DRAG_ENTERED) ( containsDragable= true ; ) else if (dragAction== DragEvent. ACTION_DRAG_ENDED) ( if (dropEventNotHandled(dragEvent) ) ( dragView. setVisibility(View. VISIBLE) ; ) ) else if (dragAction= = DragEvent.ACTION_DROP& amp;& amp; containsDragable) ( checkForValidMove((ChessBoardSquareLayoutView) view, dragView) ; dragView. setVisibility(View. VISIBLE) ; ) return true ; )

As you can see, regardless of whether the move is valid or not, the ImageView is set to the visible state. I wanted the user to see the shape move. Earlier I mentioned that the cell is a child of LayoutView. This is done to make it easier to move the ImageView from cell to cell. Below is the code for the checkForValidMove method, which shows how the ImageView is moved.

private void checkForValidMove(ChessBoardSquareLayoutView view, View dragView) ( if (mediator. isValidMove(view) ) ( ViewGroup owner= (ViewGroup) dragView. getParent() ; owner. removeView(dragView) ; view. addView(dragView) ; view. setGravity (Gravity.CENTER) ;view.showAsLanded() ;mediator.handleMove(view) ; ) )

I hope this article will help you when developing your own projects.