# Utility functions

The library contains the following two utility functions that you can use

* [Transfer Element](#transfer-element)
* [Create Image Element](#create-image-element)



### Transfer Element

<details>

<summary>Type definition </summary>

```typescript
type TransferOptions = {
  action: "copy" | "move";
  position: "prepend" | "append" | "index";
  index: number | null;
  makeDraggable: boolean;
  reActivate: boolean;
  reuseOptions: boolean;
  reuseListeners: boolean;
  options: DraggableOptions;
};
```

</details>

<details>

<summary>Default Values</summary>

```typescript
const TRANSFER_OPTIONS: TransferOptions = {
  action: "copy",
  position: "append",
  index: null,
  makeDraggable: true,
  reActivate: true,
  reuseOptions: true,
  reuseListeners: true,
  options: DEFAULT_DRAGGABLE_OPTIONS,
} as const;
```

</details>



This utility method is part of the ReDrop class and helps you easily move or copy element from one container to another. You can find more information about transfer element [here](../../api-docs/redrop/transferelm)

To understand this method you need to understand the transferOptions.

* **action**: Choose between `"move"` or `"copy"` based on your requirement. If the action is set to `"move"`, the original element will be relocated. In the case of `"copy"`, a duplicate of the element will be created.
* **position**: Choose between `"prepend"`, `"append"`, or `"index"`. If you select `"index"`, you will also need to specify the `index` property.
* **index**: When the position is set to `"index"`, you must provide a valid index where the element should be added. If sorting is enabled, the index will be accessible as one of the arguments in dropzone-related event functions, such as `"dragEnter"`, `"dragLeave"`, or `"drop"`.
* **makeDraggable**: This property lets you control whether an element should be draggable when moved or copied from one container to another. If the element is already draggable, this property will have no effect for the `"move"` action. However, for the `"copy"` action, it will create a clone of the element and make it draggable.
* **reActivate**: When `makeDraggable` is set to `"true"` and the action is `"move"`, you can use this property to reinitialise the element as draggable. By default, if a draggable element is moved and `makeDraggable` is `"true"`, no additional effect is applied since the element is already draggable.
* **reuseOptions**: If an element is already draggable and is reactivated or if the action is set to `"copy"`, creating a new draggable element, you can use this property to reuse the existing draggable options already associated with the element.
* **reuseListeners**: Similar to `reuseOptions`, this property applies to event listeners. If events are already attached to the element, you can avoid reattaching them by setting this property to `"true"`.
* **options**: If `reuseOptions` is set to `"false"` and you want to define your own draggable options, use this property to specify them.



### Create Image Element&#x20;

<details>

<summary>Type Definition</summary>

{% code overflow="wrap" %}
```typescript
type ImageOptions = {
    id?: string;
    className?: string;
    width?: number | string;
    height?: number | string;
    alt?: string;
    title?: string;
    loading?: "lazy" | "eager";
    decoding?: "async" | "sync" | "auto";
    crossOrigin?: "anonymous" | "use-credentials" | "";
    referrerPolicy?: ReferrerPolicy;
    style?: Partial<CSSStyleDeclaration>;
    [key: string]: any;
};
export declare function createImgElm(url: string, options?: ImageOptions): HTMLImageElement;
```
{% endcode %}

</details>



This utility function helps you set a custom drag preview as image. It can be used with the customPreview property of draggable option's [#modifier](../../../api-docs/options#modifier "mention")

How to use

You can import this function with other import from redrop-dnd. It expects first argument as the image url and second as the image options and it will return a image element.

To use this function with customPreview property

Static custom preview

```typescript
import { Redrop, createImgElm } from "redrop-dnd";

const dndManager = new Redrop();

// static custom preview
const draggableOptions = {
  dragPreview: {
      customPreview: createImgElm(
        `https://picsum.photos/id/${Math.floor(Math.random() * 200)}/200/300`,
        {
          width: 200,
          height: 200,
        },
      ),
    },
}

const draggableItem1 = dndManager.makeDraggable(".draggables", draggableOptions)
```

Dynamic custom preview

```typescript
import { Redrop, createImgElm } from "redrop-dnd";

const dndManager = new Redrop();

const dynamicPreview = (element: DraggableElement) => {
  // dynmaicPreview function will also get access to draggable element through function
  // argument in case you need to use it
  return createImgElm(`https://picsum.photos/id/${Math.floor(Math.random() * 200)}/200/300`, {
    width: 200,
    height: 200,
  });
};

// static custom preview
const draggableOptions = {
  dragPreview: {
      customPreview: dynamicPreview,
    },
}

const draggableItem1 = dndManager.makeDraggable(".draggables", draggableOptions)
```



The difference between static and dynamic custom previews lies in how the preview content is generated.

* **Static Custom Preview**: When you pass an HTML element directly, it creates a static custom preview. This means the same HTML element will be reused for the custom preview every time, without any changes.
* **Dynamic Custom Preview**: In this case, you pass a function instead of an HTML element. This function is called each time an element is dragged, allowing the preview content to change dynamically.

For instance, if you use the previously shared example, you'll observe the following:

* In the static custom preview, the image remains the same because the same HTML element is reused.
* In the dynamic custom preview, the image changes every time. This happens because the API used generates a random image with each call, so dragging an element triggers the function and displays a new image each time.
