10 import {CompositionGraphGeneralUtils} from "../composition-graph/utils/composition-graph-general-utils";
11 import {EventListenerService} from "app/services";
12 import {ResourceType, GRAPH_EVENTS, EVENTS, ComponentInstanceFactory, ModalsHandler} from "app/utils";
13 import 'sdc-angular-dragdrop';
14 import {LeftPaletteLoaderService} from "../../../services/components/utils/composition-left-palette-service";
16 interface IPaletteScope {
17 components:Array<LeftPaletteComponent>;
18 currentComponent:Component;
20 displaySortedCategories:any;
21 expandedSection:string;
24 event:JQueryEventObject,
25 components:LeftPaletteComponent,
29 sectionClick:(section:string)=>void;
30 searchComponents:(searchText:string)=>void;
31 onMouseOver:(displayComponent:LeftPaletteComponent)=>void;
32 onMouseOut:(displayComponent:LeftPaletteComponent)=>void;
33 dragStartCallback:(event:JQueryEventObject, ui, displayComponent:LeftPaletteComponent)=>void;
34 dragStopCallback:()=>void;
35 onDragCallback:(event:JQueryEventObject) => void;
37 setElementTemplate:(e:JQueryEventObject)=>void;
45 export class Palette implements ng.IDirective {
46 constructor(private $log:ng.ILogService,
47 private LeftPaletteLoaderService: LeftPaletteLoaderService,
49 private ComponentFactory,
50 private ComponentInstanceFactory:ComponentInstanceFactory,
51 private NodesFactory:NodesFactory,
52 private CompositionGraphGeneralUtils:CompositionGraphGeneralUtils,
53 private EventListenerService:EventListenerService,
54 private sdcMenu:IAppMenu,
55 private ModalsHandler:ModalsHandler) {
59 private fetchingComponentFromServer:boolean = false;
60 private nodeHtmlSubstitute:JQuery;
63 currentComponent: '=',
68 template = require('./palette.html');
70 link = (scope:IPaletteScope, el:JQuery) => {
71 this.nodeHtmlSubstitute = $('<div class="node-substitute"><span></span><img /></div>');
72 el.append(this.nodeHtmlSubstitute);
73 this.registerEventListenerForLeftPalette(scope);
74 // this.LeftPaletteLoaderService.loadLeftPanel(scope.currentComponent.componentType);
76 this.initComponents(scope);
77 this.initEvents(scope);
78 this.initDragEvents(scope);
79 this._initExpandedSection(scope, '');
80 el.on('$destroy', ()=> {
81 //remove listener of download event
82 this.unRegisterEventListenerForLeftPalette(scope);
86 private registerEventListenerForLeftPalette = (scope:IPaletteScope):void => {
87 if (scope.currentComponent.isResource()) {
88 this.EventListenerService.registerObserverCallback(EVENTS.RESOURCE_LEFT_PALETTE_UPDATE_EVENT, () => {
89 this.updateLeftPanelDisplay(scope);
92 if (scope.currentComponent.isService()) {
93 this.EventListenerService.registerObserverCallback(EVENTS.SERVICE_LEFT_PALETTE_UPDATE_EVENT, () => {
94 this.updateLeftPanelDisplay(scope);
97 if (scope.currentComponent.isProduct()) {
98 this.EventListenerService.registerObserverCallback(EVENTS.PRODUCT_LEFT_PALETTE_UPDATE_EVENT, () => {
99 this.updateLeftPanelDisplay(scope);
104 private unRegisterEventListenerForLeftPalette = (scope:IPaletteScope):void => {
105 if (scope.currentComponent.isResource()) {
106 this.EventListenerService.unRegisterObserver(EVENTS.RESOURCE_LEFT_PALETTE_UPDATE_EVENT);
108 if (scope.currentComponent.isService()) {
109 this.EventListenerService.unRegisterObserver(EVENTS.SERVICE_LEFT_PALETTE_UPDATE_EVENT);
111 if (scope.currentComponent.isProduct()) {
112 this.EventListenerService.unRegisterObserver(EVENTS.PRODUCT_LEFT_PALETTE_UPDATE_EVENT);
116 private leftPanelResourceFilter(resourcesNotAbstract:Array<LeftPaletteComponent>, resourceFilterTypes:Array<string>):Array<LeftPaletteComponent> {
117 let filterResources = _.filter(resourcesNotAbstract, (component) => {
118 return resourceFilterTypes.indexOf(component.getComponentSubType()) > -1;
120 return filterResources;
123 private initLeftPanel(leftPanelComponents:Array<LeftPaletteComponent>, resourceFilterTypes:Array<string>):LeftPanelModel {
124 let leftPanelModel = new LeftPanelModel();
126 if (resourceFilterTypes && resourceFilterTypes.length) {
127 leftPanelComponents = this.leftPanelResourceFilter(leftPanelComponents, resourceFilterTypes);
129 leftPanelModel.numberOfElements = leftPanelComponents && leftPanelComponents.length || 0;
131 if (leftPanelComponents && leftPanelComponents.length) {
133 let categories:any = _.groupBy(leftPanelComponents, 'mainCategory');
134 for (let category in categories)
135 categories[category] = _.groupBy(categories[category], 'subCategory');
137 leftPanelModel.sortedCategories = categories;
139 return leftPanelModel;
143 private initEvents(scope:IPaletteScope) {
148 scope.sectionClick = (section:string) => {
149 if (section === scope.expandedSection) {
150 scope.expandedSection = '';
153 scope.expandedSection = section;
156 scope.onMouseOver = (displayComponent:LeftPaletteComponent) => {
157 if (scope.isOnDrag) {
160 scope.isOnDrag = true;
162 this.EventListenerService.notifyObservers(GRAPH_EVENTS.ON_PALETTE_COMPONENT_HOVER_IN, displayComponent);
163 this.$log.debug('palette::onMouseOver:: fired');
165 // if (this.CompositionGraphGeneralUtils.componentRequirementsAndCapabilitiesCaching.containsKey(displayComponent.uniqueId)) {
166 // this.$log.debug(`palette::onMouseOver:: component id ${displayComponent.uniqueId} found in cache`);
167 // let cacheComponent:Component = this.CompositionGraphGeneralUtils.componentRequirementsAndCapabilitiesCaching.getValue(displayComponent.uniqueId);
169 // //TODO: Danny: fire event to highlight matching nodes
170 // //showMatchingNodes(cacheComponent);
174 // this.$log.debug(`palette::onMouseOver:: component id ${displayComponent.uniqueId} not found in cache, initiating server get`);
175 // // This will bring the component from the server including requirements and capabilities
176 // // Check that we do not fetch many times, because only in the success we add the component to componentRequirementsAndCapabilitiesCaching
177 // if (this.fetchingComponentFromServer) {
181 // this.fetchingComponentFromServer = true;
182 // this.ComponentFactory.getComponentFromServer(displayComponent.componentSubType, displayComponent.uniqueId)
183 // .then((component:Component) => {
184 // this.$log.debug(`palette::onMouseOver:: component id ${displayComponent.uniqueId} fetch success`);
185 // // this.LeftPaletteLoaderService.updateSpecificComponentLeftPalette(component, scope.currentComponent.componentType);
186 // this.CompositionGraphGeneralUtils.componentRequirementsAndCapabilitiesCaching.setValue(component.uniqueId, component);
187 // this.fetchingComponentFromServer = false;
189 // //TODO: Danny: fire event to highlight matching nodes
190 // //showMatchingNodes(component);
193 // this.$log.debug('palette::onMouseOver:: component id fetch error');
194 // this.fetchingComponentFromServer = false;
200 scope.onMouseOut = () => {
201 scope.isOnDrag = false;
202 this.EventListenerService.notifyObservers(GRAPH_EVENTS.ON_PALETTE_COMPONENT_HOVER_OUT);
206 private initComponents(scope:IPaletteScope) {
207 scope.searchComponents = (searchText:any):void => {
208 scope.displaySortedCategories = this._searchComponents(searchText, scope.model.sortedCategories);
209 this._initExpandedSection(scope, searchText);
212 scope.isDragable = scope.currentComponent.isComplex();
213 this.updateLeftPanelDisplay(scope);
216 private updateLeftPanelDisplay(scope:IPaletteScope) {
217 let entityType:string = scope.currentComponent.componentType.toLowerCase();
218 let resourceFilterTypes:Array<string> = this.sdcConfig.resourceTypesFilter[entityType];
219 scope.components = this.LeftPaletteLoaderService.getLeftPanelComponentsForDisplay(scope.currentComponent.componentType);
220 scope.model = this.initLeftPanel(scope.components, resourceFilterTypes);
221 scope.displaySortedCategories = angular.copy(scope.model.sortedCategories);
224 private _initExpandedSection(scope:IPaletteScope, searchText:string):void {
225 if (searchText == '') {
226 let isContainingCategory:boolean = false;
227 let categoryToExpand:string;
228 if (scope.currentComponent && scope.currentComponent.categories && scope.currentComponent.categories[0]) {
229 categoryToExpand = this.sdcMenu.categoriesDictionary[scope.currentComponent.categories[0].name];
230 for (let category in scope.model.sortedCategories) {
231 if (categoryToExpand == category) {
232 isContainingCategory = true;
237 isContainingCategory ? scope.expandedSection = categoryToExpand : scope.expandedSection = 'Generic';
240 scope.expandedSection = Object.keys(scope.displaySortedCategories).sort()[0];
244 private initDragEvents(scope:IPaletteScope) {
245 scope.dragStartCallback = (event:IDragDropEvent, ui, displayComponent:LeftPaletteComponent):void => {
246 if (scope.isLoading || !scope.isDragable || scope.isViewOnly) {
250 let component = _.find(this.LeftPaletteLoaderService.getLeftPanelComponentsForDisplay(scope.currentComponent.componentType), (componentFullData:LeftPaletteComponent) => {
251 return displayComponent.uniqueId === componentFullData.uniqueId;
253 this.EventListenerService.notifyObservers(GRAPH_EVENTS.ON_PALETTE_COMPONENT_DRAG_START, scope.dragElement, component);
255 scope.isOnDrag = true;
257 // this.graphUtils.showMatchingNodes(component, myDiagram, scope.sdcConfig.imagesPath);
258 // document.addEventListener('mousemove', moveOnDocument);
259 event.dataTransfer.component = component;
262 scope.dragStopCallback = () => {
263 scope.isOnDrag = false;
266 scope.onDragCallback = (event:IDragDropEvent):void => {
267 this.EventListenerService.notifyObservers(GRAPH_EVENTS.ON_PALETTE_COMPONENT_DRAG_ACTION, event);
269 scope.setElementTemplate = (e) => {
270 let dragComponent:LeftPaletteComponent = _.find(this.LeftPaletteLoaderService.getLeftPanelComponentsForDisplay(scope.currentComponent.componentType),
271 (fullComponent:LeftPaletteComponent) => {
272 return (<any>angular.element(e.currentTarget).scope()).component.uniqueId === fullComponent.uniqueId;
274 let componentInstance:ComponentInstance = this.ComponentInstanceFactory.createComponentInstanceFromComponent(dragComponent);
275 let node:CompositionCiNodeBase = this.NodesFactory.createNode(componentInstance);
277 // myDiagram.dragFromPalette = node;
278 this.nodeHtmlSubstitute.find("img").attr('src', node.img);
279 scope.dragElement = this.nodeHtmlSubstitute.clone().show();
281 return scope.dragElement;
285 private _searchComponents = (searchText:string, categories:any):void => {
286 let displaySortedCategories = angular.copy(categories);
287 if (searchText != '') {
288 angular.forEach(categories, function (category:any, categoryKey) {
290 angular.forEach(category, function (subcategory:Array<LeftPaletteComponent>, subcategoryKey) {
291 let filteredResources = [];
292 angular.forEach(subcategory, function (component:LeftPaletteComponent) {
294 let resourceFilterTerm:string = component.searchFilterTerms;
295 if (resourceFilterTerm.indexOf(searchText.toLowerCase()) >= 0) {
296 filteredResources.push(component);
299 if (filteredResources.length > 0) {
300 displaySortedCategories[categoryKey][subcategoryKey] = filteredResources;
303 delete displaySortedCategories[categoryKey][subcategoryKey];
306 if (!(Object.keys(displaySortedCategories[categoryKey]).length > 0)) {
307 delete displaySortedCategories[categoryKey];
312 return displaySortedCategories;
315 public static factory = ($log,
316 LeftPaletteLoaderService,
319 ComponentInstanceFactory,
321 CompositionGraphGeneralUtils,
322 EventListenerService,
325 return new Palette($log,
326 LeftPaletteLoaderService,
329 ComponentInstanceFactory,
331 CompositionGraphGeneralUtils,
332 EventListenerService,
338 Palette.factory.$inject = [
340 'LeftPaletteLoaderService',
343 'ComponentInstanceFactory',
345 'CompositionGraphGeneralUtils',
346 'EventListenerService',