{"id":14973551,"url":"https://github.com/gnucoop/ng2-dnd","last_synced_at":"2025-10-02T00:31:37.366Z","repository":{"id":65458947,"uuid":"82827462","full_name":"gnucoop/ng2-dnd","owner":"gnucoop","description":"Angular 2 Drag-and-Drop without dependencies","archived":false,"fork":true,"pushed_at":"2018-12-17T16:24:15.000Z","size":468,"stargazers_count":2,"open_issues_count":0,"forks_count":1,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-01-15T14:15:32.651Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":false,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":"akserg/ng2-dnd","license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gnucoop.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":".github/CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2017-02-22T16:34:34.000Z","updated_at":"2022-02-06T15:47:48.000Z","dependencies_parsed_at":"2023-01-24T13:25:14.324Z","dependency_job_id":null,"html_url":"https://github.com/gnucoop/ng2-dnd","commit_stats":null,"previous_names":[],"tags_count":42,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnucoop%2Fng2-dnd","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnucoop%2Fng2-dnd/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnucoop%2Fng2-dnd/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnucoop%2Fng2-dnd/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gnucoop","download_url":"https://codeload.github.com/gnucoop/ng2-dnd/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":234916159,"owners_count":18906643,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-09-24T13:48:56.550Z","updated_at":"2025-10-02T00:31:37.018Z","avatar_url":"https://github.com/gnucoop.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Angular 2+ Drag-and-Drop\nAngular 2+ Drag-and-Drop without dependencies.\nBased on [Angular 2 Drag-and-Drop by Sergey Akopkokhyants](https://github.com/akserg/ng2-dnd)\n\n\n_Some of these APIs and Components are not final and are subject to change!_\n\n## Installation\n```bash\nnpm install ngx-dnd --save\n```\n\n## Usage\nIf you use SystemJS to load your files, you might have to update your config:\n\n```js\nSystem.config({\n    map: {\n        'ngx-dnd': 'node_modules/ngx-dnd/bundles/ngx-dnd.umd.js'\n    }\n});\n```\n\n#### 1. Add the default styles\n- Import the `style.css` into your web page\n\n#### 2. Import the `DndModule`\nImport `DndModule.forRoot()` in the NgModule of your application. \nThe `forRoot` method is a convention for modules that provide a singleton service.\n\n```ts\nimport {BrowserModule} from '@angular/platform-browser';\nimport {NgModule} from '@angular/core';\nimport {DndModule} from 'ngx-dnd';\n\n@NgModule({\n    imports: [\n        BrowserModule,\n        DndModule.forRoot()\n    ],\n    bootstrap: [AppComponent]\n})\nexport class AppModule {\n}\n```\n\nIf you have multiple NgModules and you use one as a shared NgModule (that you import in all of your other NgModules), \ndon't forget that you can use it to export the `DndModule` that you imported in order to avoid having to import it multiple times.\n\n```ts\n@NgModule({\n    imports: [\n        BrowserModule,\n        DndModule.forRoot()\n    ],\n    exports: [BrowserModule, DndModule],\n})\nexport class SharedModule {\n}\n```\n\n#### 3. Use Drag-and-Drop operations with no code\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'simple-dnd',\n    template: `\n\u003ch4\u003eSimple Drag-and-Drop\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable to drag\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragEnabled]=\"true\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv\u003eDrag Me\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv dnd-droppable class=\"panel panel-info\" (onDropSuccess)=\"simpleDrop=$event\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003ePlace to drop\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv *ngIf=\"simpleDrop\"\u003eItem was dropped here\u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class SimpleDndComponent {\n    simpleDrop: any = null;\n}\n```\n\n#### 4. Restriction Drag-and-Drop operations with drop zones\nYou can use property *dropZones* (actually an array) to specify in which place you would like to drop the draggable element:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'zone-dnd',\n    template: `\n\u003ch4\u003eRestricted Drag-and-Drop with zones\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-primary\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable to drag\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragEnabled]=\"true\" [dropZones]=\"['zone1']\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv\u003eDrag Me\u003c/div\u003e\n                        \u003cdiv\u003eZone 1 only\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable to drag\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragEnabled]=\"true\" [dropZones]=\"['zone1', 'zone2']\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv\u003eDrag Me\u003c/div\u003e\n                        \u003cdiv\u003eZone 1 \u0026 2\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv dnd-droppable class=\"panel panel-info\" [dropZones]=\"['zone1']\" (onDropSuccess)=\"restrictedDrop1=$event\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eZone 1\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv *ngIf=\"restrictedDrop1\"\u003eItem was dropped here\u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv dnd-droppable class=\"panel panel-warning\" [dropZones]=\"['zone2']\" (onDropSuccess)=\"restrictedDrop2=$event\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eZone 2\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv *ngIf=\"restrictedDrop2\"\u003eItem was dropped here\u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class ZoneDndComponent {\n    restrictedDrop1: any = null;\n    restrictedDrop2: any = null;\n}\n```\n\n#### 5. Transfer custom data via Drag-and-Drop\nYou can transfer data from draggable to droppable component via *dragData* property of Draggable component:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'custom-data-dnd',\n    template: `\n\u003ch4\u003eTransfer custom data in Drag-and-Drop\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable to drag\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragEnabled]=\"true\" [dragData]=\"transferData\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv\u003eDrag Me\u003c/div\u003e\n                        \u003cdiv\u003e{{transferData | json}}\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv dnd-droppable class=\"panel panel-info\" (onDropSuccess)=\"transferDataSuccess($event)\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003ePlace to drop (Items:{{receivedData.length}})\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv [hidden]=\"!receivedData.length \u003e 0\" *ngFor=\"let data of receivedData\"\u003e{{data | json}}\u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class CustomDataDndComponent {\n    transferData: Object = {id: 1, msg: 'Hello'};\n    receivedData: Array\u003cany\u003e = [];\n\n    transferDataSuccess($event: any) {\n        this.receivedData.push($event);\n    }\n}\n```\n\n#### 6. Use a custom function to determine where dropping is allowed\nFor use-cases when a static set of `dropZone`s is not possible, a custom function can be used to dynamically determine whether an item can be dropped or not. To achieve that, set the `allowDrop` property to this boolean function.\n\nIn the following example, we have two containers that only accept numbers that are multiples of a user-input base integer. `dropZone`s are not helpful here because they are static, whereas the user input is dynamic.\n\n```js\nimport { Component } from '@angular/core';\n\n@Component({\n    selector: 'custom-function-dnd',\n    template: `\n\u003ch4\u003eUse a custom function to determine where dropping is allowed\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable to drag\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragData]=\"6\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003edragData = 6\u003c/div\u003e\n                \u003c/div\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragData]=\"10\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003edragData = 10\u003c/div\u003e\n                \u003c/div\u003e\n                \u003cdiv class=\"panel panel-default\" dnd-draggable [dragData]=\"30\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003edragData = 30\u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-6\"\u003e\n        \u003cpre\u003eallowDropFunction(baseInteger: any): any {{ '{' }}\n  return (dragData: any) =\u003e dragData % baseInteger === 0;\n{{ '}' }}\u003c/pre\u003e\n        \u003cdiv class=\"row\"\u003e\n            \u003cdiv class=\"col-sm-6\"\u003e\n                \u003cdiv dnd-droppable class=\"panel panel-info\" [allowDrop]=\"allowDropFunction(box1Integer)\" (onDropSuccess)=\"addTobox1Items($event)\"\u003e\n                    \u003cdiv class=\"panel-heading\"\u003e\n                        Multiples of\n                        \u003cinput type=\"number\" [(ngModel)]=\"box1Integer\" style=\"width: 4em\"\u003e\n                        only\n                    \u003c/div\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv *ngFor=\"let item of box1Items\"\u003edragData = {{item}}\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n            \u003cdiv class=\"col-sm-6\"\u003e\n                \u003cdiv dnd-droppable class=\"panel panel-warning\" [allowDrop]=\"allowDropFunction(box2Integer)\" (onDropSuccess)=\"addTobox2Items($event)\"\u003e\n                    \u003cdiv class=\"panel-heading\"\u003e\n                        Multiples of\n                        \u003cinput type=\"number\" [(ngModel)]=\"box2Integer\" style=\"width: 4em\"\u003e\n                        only\n                    \u003c/div\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv *ngFor=\"let item of box2Items\"\u003edragData = {{item}}\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e\n`\n})\nexport class CustomFunctionDndComponent {\n    box1Integer: number = 3;\n    box2Integer: number = 10;\n\n    box1Items: string[] = [];\n    box2Items: string[] = [];\n\n    allowDropFunction(baseInteger: number): any {\n        return (dragData: any) =\u003e dragData % baseInteger === 0;\n    }\n\n    addTobox1Items($event: any) {\n        this.box1Items.push($event.dragData);\n    }\n\n    addTobox2Items($event: any) {\n        this.box2Items.push($event.dragData);\n    }\n}\n```\n\n#### 7. Shopping basket with Drag-and-Drop\nHere is an example of shopping backet with products adding via drag and drop operation:\n\n```js\nimport { Component } from '@angular/core';\n\n@Component({\n    selector: 'shoping-basket-dnd',\n    template: `\n\u003ch4\u003eDrag-and-Drop - Shopping basket\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eAvailable products\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv *ngFor=\"let product of availableProducts\" class=\"panel panel-default\"\n                    dnd-draggable [dragEnabled]=\"product.quantity\u003e0\" [dragData]=\"product\" (onDragSuccess)=\"orderedProduct($event)\" [dropZones]=\"['demo1']\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cdiv [hidden]=\"product.quantity===0\"\u003e{{product.name}} - \\${{product.cost}}\u003cbr\u003e(available: {{product.quantity}})\u003c/div\u003e\n                        \u003cdiv [hidden]=\"product.quantity\u003e0\"\u003e\u003cdel\u003e{{product.name}}\u003c/del\u003e\u003cbr\u003e(NOT available)\u003c/div\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv dnd-droppable (onDropSuccess)=\"addToBasket($event)\" [dropZones]=\"['demo1']\" class=\"panel panel-info\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eShopping Basket\u003cbr\u003e(to pay: \\${{totalCost()}})\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cdiv *ngFor=\"let product of shoppingBasket\" class=\"panel panel-default\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                    {{product.name}}\u003cbr\u003e(ordered: {{product.quantity}}\u003cbr\u003ecost: \\${{product.cost * product.quantity}})\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class ShoppingBasketDndComponent {\n    availableProducts: Array\u003cProduct\u003e = [];\n    shoppingBasket: Array\u003cProduct\u003e = [];\n\n    constructor() {\n        this.availableProducts.push(new Product('Blue Shoes', 3, 35));\n        this.availableProducts.push(new Product('Good Jacket', 1, 90));\n        this.availableProducts.push(new Product('Red Shirt', 5, 12));\n        this.availableProducts.push(new Product('Blue Jeans', 4, 60));\n    }\n\n    orderedProduct($event: any) {\n        let orderedProduct: Product = $event.dragData;\n        orderedProduct.quantity--;\n    }\n\n    addToBasket($event: any) {\n        let newProduct: Product = $event.dragData;\n        for (let indx in this.shoppingBasket) {\n            let product: Product = this.shoppingBasket[indx];\n            if (product.name === newProduct.name) {\n                product.quantity++;\n                return;\n            }\n        }\n        this.shoppingBasket.push(new Product(newProduct.name, 1, newProduct.cost));\n        this.shoppingBasket.sort((a: Product, b: Product) =\u003e {\n            return a.name.localeCompare(b.name);\n        });\n    }\n\n    totalCost(): number {\n        let cost: number = 0;\n        for (let indx in this.shoppingBasket) {\n            let product: Product = this.shoppingBasket[indx];\n            cost += (product.cost * product.quantity);\n        }\n        return cost;\n    }\n}\n\nclass Product {\n  constructor(public name: string, public quantity: number, public cost: number) {}\n}\n```\n\n#### 8. Simple sortable with Drag-and-Drop\nHere is an example of simple sortable of favorite drinks moving in container via drag and drop operation:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'simple-sortable',\n    template: `\n\u003ch4\u003eSimple sortable\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003e\n                Favorite drinks\n            \u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cul class=\"list-group\" dnd-sortable-container [sortableData]=\"listOne\"\u003e\n                    \u003cli *ngFor=\"let item of listOne; let i = index\" class=\"list-group-item\" dnd-sortable [sortableIndex]=\"i\"\u003e{{item}}\u003c/li\u003e\n                \u003c/ul\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-6\"\u003e\n        \u003cdiv class=\"panel panel-default\"\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                My prefences:\u003cbr/\u003e\n                \u003cspan *ngFor=\"let item of listOne; let i = index\"\u003e{{i + 1}}) {{item}}\u003cbr/\u003e\u003c/span\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class SimpleSortableComponent {\n    listOne: Array\u003cstring\u003e = ['Coffee', 'Orange Juice', 'Red Wine', 'Unhealty drink!', 'Water'];\n}\n```\n\n#### 9. Simple sortable With Drop into recycle bin\nHere is an example of multi list sortable of boxers moving in container and between containers via drag and drop operation:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'recycle-multi-sortable',\n    template: `\n\u003ch4\u003eSimple sortable With Drop into recycle bin\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-success\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003e\n                Favorite drinks\n            \u003c/div\u003e\n            \u003cdiv class=\"panel-body\" dnd-sortable-container [sortableData]=\"listOne\" [dropZones]=\"['delete-dropZone']\"\u003e\n                \u003cul class=\"list-group\"\u003e\n                    \u003cli *ngFor=\"let item of listOne; let i = index\" class=\"list-group-item\"\n                    dnd-sortable [sortableIndex]=\"i\"\u003e{{item}}\u003c/li\u003e\n                \u003c/ul\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-6\"\u003e\n        \u003cdiv class=\"panel panel-default\"\u003e\n            \u003cdiv class=\"panel-body\" dnd-sortable-container [dropZones]=\"['delete-dropZone']\" [sortableData]=\"listRecycled\"\u003e\n                Recycle bin: Drag into me to delete it\u003cbr/\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n        \u003cdiv *ngIf=\"listRecycled.length\"\u003e\n        \u003cb\u003eRecycled:\u003c/b\u003e \u003cspan\u003e{{listRecycled.toString()}} \u003c/span\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class RecycleMultiSortableComponent {\n    listOne: Array\u003cstring\u003e = ['Coffee', 'Orange Juice', 'Red Wine', 'Unhealty drink!', 'Water'];\n    listRecycled: Array\u003cstring\u003e = [];\n}\n```\n\n#### 10. Simple sortable With Drop into something, without delete it\nHere is an example of simple sortable list of items copying in target container:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'simple-sortable-copy',\n    template: `\n\u003ch4\u003eSimple sortable With Drop into something, without delete it\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        \u003cdiv class=\"panel panel-warning\"\n            dnd-sortable-container [sortableData]=\"sourceList\" [dropZones]=\"['source-dropZone']\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eSource List\u003c/div\u003e\n            \u003cdiv class=\"panel-body\"\u003e\n                \u003cul class=\"list-group\"\u003e\n                    \u003cli *ngFor=\"let source of sourceList; let x = index\" class=\"list-group-item\"\n                        dnd-sortable [sortableIndex]=\"x\" [dragEnabled]=\"true\"\n                        [dragData]=\"source\"\u003e{{source.name}}\u003c/li\u003e\n                \u003c/ul\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-6\"\u003e\n        \u003cdiv class=\"panel panel-info\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eTarget List\u003c/div\u003e\n            \u003cdiv class=\"panel-body\" dnd-droppable (onDropSuccess)=\"addTo($event)\" [dropZones]=\"['source-dropZone']\"\u003e\n                \u003cul class=\"list-group\"\u003e\n                    \u003cli *ngFor=\"let target of targetList\" class=\"list-group-item\"\u003e\n                        {{target.name}}\n                    \u003c/li\u003e\n                \u003c/ul\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class SimpleSortableCopyComponent {\n\n    sourceList: Widget[] = [\n        new Widget('1'), new Widget('2'),\n        new Widget('3'), new Widget('4'),\n        new Widget('5'), new Widget('6')\n    ];\n\n    targetList: Widget[] = [];\n    addTo($event: any) {\n        this.targetList.push($event.dragData);\n    }\n}\n\nclass Widget {\n  constructor(public name: string) {}\n}\n```\n\n#### 11. Multi list sortable between containers\nHere is an example of multi list sortable of boxers moving in container and between containers via drag and drop operation:\n\n```js\nimport {Component} from '@angular/core';\n\n@Component({\n    selector: 'embedded-sortable',\n    template: `\n\u003ch4\u003eMove items between multi list sortable containers\u003c/h4\u003e\n\u003cdiv class=\"row\"\u003e\n    \u003cdiv class=\"col-sm-3\"\u003e\n        Drag Containers \u003cinput type=\"checkbox\" [(ngModel)]=\"dragOperation\"/\u003e\n        \u003cdiv dnd-sortable-container [sortableData]=\"containers\" [dropZones]=\"['container-dropZone']\"\u003e\n            \u003cdiv class=\"col-sm3\"\n                    *ngFor=\"let container of containers; let i = index\"\n                    dnd-sortable [sortableIndex]=\"i\" [dragEnabled]=\"dragOperation\"\u003e\n                \u003cdiv class=\"panel panel-warning\"\n                    dnd-sortable-container [sortableData]=\"container.widgets\" [dropZones]=\"['widget-dropZone']\"\u003e\n                    \u003cdiv class=\"panel-heading\"\u003e\n                        {{container.id}} - {{container.name}}\n                    \u003c/div\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        \u003cul class=\"list-group\"\u003e\n                            \u003cli *ngFor=\"let widget of container.widgets; let x = index\" class=\"list-group-item\"\n                                dnd-sortable [sortableIndex]=\"x\" [dragEnabled]=\"!dragOperation\"\n                                [dragData]=\"widget\"\u003e{{widget.name}}\u003c/li\u003e\n                        \u003c/ul\u003e\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"col-sm-6\"\u003e\n        \u003cdiv class=\"panel panel-info\"\u003e\n            \u003cdiv class=\"panel-heading\"\u003eWidgets\u003c/div\u003e\n            \u003cdiv class=\"panel-body\" dnd-droppable (onDropSuccess)=\"addTo($event)\" [dropZones]=\"['widget-dropZone']\"\u003e\n                \u003cdiv *ngFor=\"let widget of widgets\" class=\"panel panel-default\"\u003e\n                    \u003cdiv class=\"panel-body\"\u003e\n                        {{widget.name}}\n                    \u003c/div\u003e\n                \u003c/div\u003e\n            \u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/div\u003e`\n})\nexport class EmbeddedSortableComponent {\n    dragOperation: boolean = false;\n\n    containers: Array\u003cContainer\u003e = [\n        new Container(1, 'Container 1', [new Widget('1'), new Widget('2')]),\n        new Container(2, 'Container 2', [new Widget('3'), new Widget('4')]),\n        new Container(3, 'Container 3', [new Widget('5'), new Widget('6')])\n    ];\n\n    widgets: Array\u003cWidget\u003e = [];\n    addTo($event: any) {\n        if ($event) {\n            this.widgets.push($event.dragData);\n        }\n    }\n}\n\nclass Container {\n  constructor(public id: number, public name: string, public widgets: Array\u003cWidget\u003e) {}\n}\n\nclass Widget {\n  constructor(public name: string) {}\n}\n```\n\n# Credits\n- [Francesco Cina](https://github.com/ufoscout)\n- [Sergey Akopkokhyants](https://github.com/akserg)\n\n# License\n [MIT](/LICENSE)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgnucoop%2Fng2-dnd","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgnucoop%2Fng2-dnd","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgnucoop%2Fng2-dnd/lists"}