4 * Copyright 2016 RIFT.IO Inc
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
20 * Created by onvelocity on 10/2/15.
24 import UID
from './UniqueId'
25 import SelectionManager
from './SelectionManager'
26 import CatalogItemsActions
from '../actions/CatalogItemsActions'
27 import DescriptorModelFactory
from './model/DescriptorModelFactory'
29 import '../styles/Animations.scss'
34 function onlyUnique(value
, index
, self
) {
35 return self
.indexOf(value
) === index
;
38 function createDeleteEvent(e
, uid
, eventName
= 'cut') {
47 if (window
.CustomEvent
.prototype.initCustomEvent
) {
49 var evt
= document
.createEvent('CustomEvent');
50 evt
.initCustomEvent(eventName
, data
.bubbles
, data
.cancelable
, data
.detail
);
53 return new CustomEvent(eventName
, data
);
56 export default class DeletionManager
{
58 static onDeleteKey(event
) {
59 const target
= event
.target
;
60 if (event
.defaultPrevented
) {
63 if ((event
.which
=== DELETE
|| event
.which
=== BACKSPACE
) && /^BODY|SVG|DIV$/i.test(target
.tagName
)) {
64 event
.preventDefault();
65 DeletionManager
.deleteSelected(event
);
70 static deleteSelected(event
) {
72 // TODO refactor this to be a flux action e.g. move this code into ComposerAppActions.deleteSelected()
74 const selected
= SelectionManager
.getSelections();
76 const canvasPanelDiv
= document
.getElementById('canvasPanelDiv');
78 if (!canvasPanelDiv
) {
82 // get a valid list of items to potentially remove via the cut event handler
83 const removeElementList
= selected
.filter(d
=> d
).filter(onlyUnique
).reduce((r
, uid
) => {
84 const elements
= Array
.from(canvasPanelDiv
.querySelectorAll('[data-uid="' + uid
+ '"]'));
85 return r
.concat(elements
);
86 }, []).filter(d
=> d
);
88 if (removeElementList
.length
=== 0 && selected
.length
> 0) {
89 // something was selected but we did not find any dom elements with data-uid!
90 console
.error(`No valid DescriptorModel instance found on element. Did you forget to put data-uid={m.uid}`,
91 selected
.map(uid
=> Array
.from(canvasPanelDiv
.querySelectorAll(`[data-uid="${uid}"]`))));
94 SelectionManager
.removeOutline();
96 // now actually update the model
97 const invokedEventAlreadyMap
= {};
98 const failedToRemoveList
= removeElementList
.map(element
=> {
100 const uid
= UID
.from(element
);
102 if (invokedEventAlreadyMap
[uid
]) {
107 // https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/dispatchEvent
108 // false means event.preventDefault() was called by one of the handlers
109 const deleteEvent
= createDeleteEvent(event
, uid
);
110 const preventDefault
= (false === element
.dispatchEvent(deleteEvent
));
111 if (preventDefault
) {
112 console
.log('cut event was cancelled', element
);
113 //d3.select(element).classed('-with-animations deleteItemAnimation', false).style({opacity: null});
118 console
.warn(`Exception caught dispatching 'cut' event: ${error}`,
119 selected
.map(uid
=> Array
.from(canvasPanelDiv
.querySelectorAll(`[data-uid="${uid}"]`)))
123 invokedEventAlreadyMap
[uid
] = true;
126 }).filter(d
=> d
).filter(onlyUnique
);
128 SelectionManager
.clearSelectionAndRemoveOutline();
129 failedToRemoveList
.forEach(d
=> SelectionManager
.addSelection(d
));
130 SelectionManager
.refreshOutline();
134 static addEventListeners() {
135 DeletionManager
.removeEventListeners();
136 document
.body
.addEventListener('keydown', DeletionManager
.onDeleteKey
);
139 static removeEventListeners() {
140 document
.body
.removeEventListener('keydown', DeletionManager
.onDeleteKey
);