msgProc: Drag & Drop
Drag-and-drop messages let your container receive dragged content from the operating system, other browser tabs, or other elements on the page. WakaPAC wraps the HTML5 Drag and Drop API into four messages that flow through msgProc like any other event, with coordinates packed into lParam and transfer data in event.detail.
Enabling Drop Targets
Add the data-pac-drop-target attribute to any element within or on a PAC container to accept drops. Without this attribute, drag events pass through to the browser's default behavior. The attribute value optionally sets the drop effect cursor — valid values are copy, move, and link. Defaults to copy if omitted or unrecognized.
<div data-pac-id="fileUploader" data-pac-drop-target>
Drop files here
</div>
<!-- Explicit move cursor -->
<div data-pac-id="sortableList" data-pac-drop-target="move">
Reorder items
</div>
The attribute can also be placed on a child element inside the container. The drop target attribute controls where drops are accepted; the nearest data-pac-id ancestor determines which container receives the messages.
<div data-pac-id="editor">
<div class="toolbar">...</div>
<div class="dropzone" data-pac-drop-target>
Drop images here
</div>
</div>
Message Flow
A complete drag-and-drop interaction produces this message sequence:
User drags item into container → MSG_DRAGENTER (once)
User hovers over a drop target → MSG_DRAGOVER (once per drop target element)
User drags item out of container → MSG_DRAGLEAVE (once)
Or if the user drops:
User drags item into container → MSG_DRAGENTER (once)
User hovers over a drop target → MSG_DRAGOVER (once per drop target element)
User releases → MSG_DROP (once)
Drag Enter (MSG_DRAGENTER)
MSG_DRAGENTER fires once when a drag operation first crosses the container boundary. Use this to show visual feedback such as highlighting the drop zone.
Message Parameters
| Parameter | Type | Description |
|---|---|---|
wParam |
number | Modifier key and button state flags: MK_SHIFT, MK_CONTROL, MK_ALT, MK_RBUTTON, MK_MBUTTON |
lParam |
number | Packed cursor coordinates relative to the container. Extract using MAKEPOINTS() |
Detail Properties
| Property | Type | Description |
|---|---|---|
types |
string[] | Array of available data types in the drag operation (e.g., ['text/plain', 'Files']). Use this to determine what kind of content is being dragged before the drop occurs. See Common Type Values |
Drag Over (MSG_DRAGOVER)
MSG_DRAGOVER fires once when the cursor enters a new drop target element within the container. It does not fire continuously — it dispatches when the underlying target element changes. Use this to update positional feedback such as insertion markers or placement previews.
Message Parameters
| Parameter | Type | Description |
|---|---|---|
wParam |
number | Modifier key and button state flags: MK_SHIFT, MK_CONTROL, MK_ALT, MK_RBUTTON, MK_MBUTTON |
lParam |
number | Packed cursor coordinates relative to the container. Extract using MAKEPOINTS() |
Detail Properties
| Property | Type | Description |
|---|---|---|
dropTarget |
HTMLElement | The drop target element (the element with data-pac-drop-target) that the cursor is currently over |
types |
string[] | Array of available data types in the drag operation. See Common Type Values |
Drag Leave (MSG_DRAGLEAVE)
MSG_DRAGLEAVE fires once when the drag operation exits the container boundary. Use this to remove visual feedback added during MSG_DRAGENTER.
Message Parameters
| Parameter | Type | Description |
|---|---|---|
wParam |
number | Modifier key and button state flags: MK_SHIFT, MK_CONTROL, MK_ALT, MK_RBUTTON, MK_MBUTTON |
lParam |
number | Packed cursor coordinates relative to the container. Extract using MAKEPOINTS() |
Detail Properties
| Property | Type | Description |
|---|---|---|
types |
string[] | Array of available data types in the drag operation. See Common Type Values |
Drop (MSG_DROP)
MSG_DROP fires when the user releases a dragged item over a drop target within the container. This is the only point where full drag data (text content, HTML, URIs, file contents) is accessible. The browser's default behavior (navigating to dropped files) is always prevented.
Message Parameters
| Parameter | Type | Description |
|---|---|---|
wParam |
number | Modifier key and button state flags: MK_SHIFT, MK_CONTROL, MK_ALT, MK_RBUTTON, MK_MBUTTON |
lParam |
number | Packed cursor coordinates relative to the container. Extract using MAKEPOINTS() |
Detail Properties
| Property | Type | Description |
|---|---|---|
dropTarget |
HTMLElement | The drop target element (the element with data-pac-drop-target) that received the drop |
text |
string | Plain text content from the drag operation. Empty string if not available |
html |
string | HTML content from the drag operation. Empty string if not available |
uri |
string | URI list from the drag operation (e.g., dragged links). Empty string if not available |
files |
object[] | Array of file metadata objects, each containing name (string), size (number, bytes), and type (string, MIME type). Same shape as MSG_PASTE files. Empty array if no files |
rawFiles |
FileList | The native FileList from DataTransfer for direct file access. Use this for reading file contents or uploading |
Example: File Upload Drop Zone
msgProc(event) {
if (event.message === wakaPAC.MSG_DRAGENTER) {
// Check if the drag contains files
if (event.detail.types.includes('Files')) {
this.dropHighlight = true;
}
}
if (event.message === wakaPAC.MSG_DRAGLEAVE) {
this.dropHighlight = false;
}
if (event.message === wakaPAC.MSG_DROP) {
this.dropHighlight = false;
// Process dropped files
const files = event.detail.rawFiles;
for (let i = 0; i < files.length; i++) {
this.uploadFile(files[i]);
}
}
}
Common Type Values
The types array in MSG_DRAGENTER, MSG_DRAGOVER, and MSG_DRAGLEAVE identifies what kind of content is being dragged. Multiple values can be present at once — for example, dragging a link from a web page typically produces ['text/plain', 'text/html', 'text/uri-list'].
| Value | Source |
|---|---|
'Files' |
Files dragged from the OS (file manager, desktop) |
'text/plain' |
Plain text dragged from a text selection or input field |
'text/html' |
Rich text dragged from a web page or editor |
'text/uri-list' |
Links dragged from the browser address bar, bookmarks, or hyperlinks |
Drag sources can also set custom MIME types, which appear in the array as-is.
Best Practices
- Always provide visual feedback: Use MSG_DRAGENTER to highlight drop zones and MSG_DRAGLEAVE to remove the highlight. Users need to see where they can drop
- Check types early: Use
event.detail.typesin MSG_DRAGENTER to determine if your container should accept the drag. Show different visual states for accepted vs rejected content - Use files for validation, rawFiles for processing: The
filesarray provides lightweight metadata for type-checking and size validation. UserawFilesonly when you need to read actual file contents - Clean up on MSG_DRAGLEAVE: Any visual state added in MSG_DRAGENTER must be removed in MSG_DRAGLEAVE. The user may drag in and out multiple times before dropping
- MSG_PASTE and MSG_DROP share a file shape: The
filesmetadata array uses the same{ name, size, type }structure in both messages. Code that validates file drops works for paste and vice versa