var __awaiter=this&&this.__awaiter||function(t,e,i,n){return new(i||(i=Promise))(function(o,s){function h(t){try{c(n.next(t))}catch(t){s(t)}}function r(t){try{c(n.throw(t))}catch(t){s(t)}}function c(t){var e;t.done?o(t.value):((e=t.value)instanceof i?e:new i(function(t){t(e)})).then(h,r)}c((n=n.apply(t,e||[])).next())})};import{EventEmitter as t}from"events";import{input as e}from"../components/flow-editor";import{NodeUtilities as i}from"../node-structure";import{SocketTypeMatcher as n}from"../node-structure/socket.type.matcher";export class Project extends t{constructor(){super(),this.nodes=[],this.connections=[],this.existingFlowRuleId=-1,this.existingFlowRuleName=null,this.existingFlowRuleDesc=null,this.isInUnsavedState=!1,this.isConnecting=!1,this.history=[],this.historyIndex=0,this.startConnectionDrag=(t,e,i)=>{this.connectionStartSocket=null,this.connectionEndSocket=null,i?this.connectionEndSocket=e:this.connectionStartSocket=e,this.isConnecting=!0,this.emit("connectionstart",t,e)},this.connectionDragging=t=>{this.emit("connecting",t)},this.endConnectionDrag=(t,e,i)=>{this.isConnecting&&(i?this.connectionEndSocket=e:this.connectionStartSocket=e,this.isConnecting=!1,this.emit("connectionend",t,e),this.connectionEndSocket&&this.connectionStartSocket&&this.createConnection(this.connectionStartSocket.id,this.connectionEndSocket.id))},this.setMaxListeners(1024)}get isCurrentlyConnecting(){return this.isConnecting}set unsavedState(t){this.isInUnsavedState=t,this.emit("unsavedstateset",t)}get unsavedState(){return this.isInUnsavedState}setCurrentProject(t,e,i){this.unsavedState=!1,this.existingFlowRuleId=t,this.existingFlowRuleName=e,this.existingFlowRuleDesc=i,this.history=[],this.emit("projectset",t)}notifyChange(){this.unsavedState=!0,this.emit("changed")}createUndoSnapshot(){this.history=this.history.splice(0,this.historyIndex+1),this.history.push(JSON.parse(JSON.stringify(this.toNodeCollection("","")))),this.historyIndex=this.history.length-1}undo(){return __awaiter(this,void 0,void 0,function*(){0!==this.history.length&&-1!==this.historyIndex&&(this.historyIndex===this.history.length-1&&this.history.push(JSON.parse(JSON.stringify(this.toNodeCollection("","")))),yield this.fromNodeCollection(this.history[this.historyIndex]),this.historyIndex--,this.notifyChange())})}redo(){return __awaiter(this,void 0,void 0,function*(){0===this.history.length||this.historyIndex>=this.history.length-2||(this.historyIndex++,yield this.fromNodeCollection(this.history[this.historyIndex+1]),this.notifyChange())})}fromNodeCollection(t){return __awaiter(this,void 0,void 0,function*(){yield this.clear(),t.nodes.forEach(t=>{this.addNode(t)}),t.connections.forEach(t=>{this.createConnection(t.from,t.to)}),this.emit("nodecollectionloaded",t),this.unsavedState=!1})}toNodeCollection(t,e){return{name:t,description:e,connections:this.connections,nodes:this.nodes}}clear(){return __awaiter(this,arguments,void 0,function*(t=!1){e.clearSelection(),this.nodes.forEach(t=>{this.removeNode(t)}),this.nodes=[],this.connections=[],this.unsavedState=!t,t&&this.setCurrentProject(-1,null,null),this.emit("cleared")})}addNode(t){if(this.nodes.filter(e=>e.id===t.id).length>0)throw Error("Node with identical identity already exists in the project");this.nodes.push(t),this.emit("nodeadded",t)}removeNode(t){e.clearSelection(),this.connections.filter(e=>{let n=i.getSocketFromID(e.from,this.nodes),o=i.getSocketFromID(e.to,this.nodes);return n.nodeId===t.id||o.nodeId===t.id}).forEach(t=>{this.removeConnection(t)}),this.nodes.filter(e=>e.id===t.id).forEach(t=>{this.nodes.splice(this.nodes.indexOf(t),1),this.emit("noderemoved",t)})}removeConnection(t){e.clearSelection(),this.connections.filter(e=>e.from===t.from&&e.to===t.to).forEach(t=>{let e=this.connections.indexOf(t);-1===e?console.warn("attempt to delete nonexistent connection"):(this.connections.splice(e,1),this.emit("connectionremoved",t))})}isValidConnection(t){let e=i.getSocketFromID(t.from,this.nodes),o=i.getSocketFromID(t.to,this.nodes);return!!e&&!!o&&!(!n.match(e.type,o.type)||e.id===o.id||e.nodeId===o.nodeId)}createConnection(t,e){let n={from:t,to:e};if(!this.isValidConnection(n))return!1;if(!i.getSocketFromID(n.to,this.nodes).type.includes("_ARRAY"))for(let t of this.connections.filter(t=>t.to===e))this.removeConnection(t);return this.connections.push(n),this.emit("connectioncreated",t,e),!0}removeInvalidConnections(){for(let t of this.connections.map(t=>this.enrichConnection(t)).filter(t=>!this.isValidConnection(t)))this.removeConnection(t)}enrichConnection(t){var e,n;return{from:null==(e=i.getSocketFromID(t.from,this.nodes))?void 0:e.id,to:null==(n=i.getSocketFromID(t.to,this.nodes))?void 0:n.id}}}