artem-mangilev / ngx-vflow

An open source library to build node-based UI with Angular 16+
https://www.ngx-vflow.org/
MIT License
155 stars 10 forks source link

Dynamic handle type of custom nodes #66

Closed chethan1095 closed 4 months ago

chethan1095 commented 4 months ago
<vflow [nodes]="nodes" [edges]="edges" background="ghostwhite" [connection]="connectionSettings"
          (onConnect)="createEdge($event)" view="auto" cli
           (onNodesChange.select.single)="handleNodeSelectChange($event)">
          <ng-template nodeHtml let-ctx>
            <div class="custom-node" [class.custom-node_selected]="ctx.selected()">

              <div class="inline-row">
                <i class="bi bi-usb-symbol custom-icon"></i>
                &nbsp;&nbsp;&nbsp; {{ ctx.node.data.ip }}
              </div>

              <span>{{ ctx.node.data.text }}</span>

              <!-- {{ ctx.node.data.text }} -->

              <handle type="source" position="right" />
            </div>
          </ng-template>
        </vflow>

Hi I am creating a dynamic nodes where I need to update handle type to source or target dynamically . How to add this in ngx-vflow for angular. Here <handle type="source" position="right" /> I need to get type from a json of nodes just like how i am getting text

muccijacopo commented 4 months ago

@chethan1095 data binding doesn't work? <handle [type]="ctx.node.data.type" position="right" />

chethan1095 commented 4 months ago

@muccijacopo Thanks...… data binding is working . Can you please help me with another I need to trigger a event when I double click on any Node and also I need to delete the line connected after drawing it by mistake

artem-mangilev commented 4 months ago

@muccijacopo many thanks for help to @chethan1095!

artem-mangilev commented 4 months ago

@chethan1095

  1. You can solve the task with double-click by using custom nodes. Custom nodes are controlled by you, allowing you to add handling for double-click or any other event. See: Custom Nodes Example.
  2. Node deletion should also be implemented by you. I have provided an example of a deletion implementation (select an edge and press backspace): Delete Selected Example.
chethan1095 commented 4 months ago

Hi @artem-mangilev , Thanks for your reply got the solution for above. I need one more favor from you I need to dynamically create nodes I am doing like below.

createNode(text: any, x: any, y: any) {
    const node = {
      id: this.nodeId,
      point: { x: x, y: y },
      type: 'html-template',
      data: {
        text: text,
      }
    };
    this.nodeId++;
    return node;
  }

I am able to create nodes dynamically but its not reflecting the nodes. Requesting you to please help me with the issue

artem-mangilev commented 4 months ago

Hi @chethan1095,

To create new nodes, you should append them to the nodes array. It's important to create a new array for Angular to detect this change.

...

this.nodes = []

createNode(text: string, x: number, y: number) {
  this.nodes = [...this.nodes, {
    id: this.nodeId,
    point: { x: x, y: y },
    type: 'html-template',
    data: {
      text: text,
    }
  }]

  this.nodeId++
}
...

I will create a page with dynamic node creation in the documentation later.

chethan1095 commented 4 months ago

@artem-mangilev , I am pushing array the same way but nodes are not getting updated in template but nodes array is getting updated

artem-mangilev commented 4 months ago

Could you please provide some code sandbox (stackblitz for example) with what you are trying to implement? I'll try to help based on this sandbox

chethan1095 commented 4 months ago

I am not able to create sandbox with ngx-vflow package but here's how I am pushing node to array.

component.html

<vflow [nodes]="nodes" [edges]="edges" background="ghostwhite" [connection]="connectionSettings"
          (onConnect)="createEdge($event)" view="auto" (onNodesChange.select)="handleNodeSelect($event)"
          (onNodesChange.select.single)="handleNodeSelectChange($event)" >
          <ng-template nodeHtml let-ctx>
            <div class="custom-node" (dblclick)="onNodeSelected(ctx.node.data)"
              [class.custom-node_selected]="ctx.selected()">

              <div class="inline-row">
                <i class="bi bi-usb-symbol custom-icon"></i>
                &nbsp;&nbsp;&nbsp;
                <!-- {{ ctx.node.data.ip }} -->
              </div>

              <span>{{ ctx.node.data.text }}</span>

              <handle type="source" position="right" />
              <handle type="target" position="left" />

            </div>
          </ng-template>
        </vflow>

component.ts

 this.nodes: Node[] = [];

drop(event: any) {
 const draggedDevice = this.availableDevices[event.previousIndex];
    console.log('Dragged Device:', draggedDevice);
 let x, y = 0;
    if (draggedDevice == "RU") {
      x = 10;
      y = 175
    } else if (draggedDevice == "DU") {
      x = 200;
      y = 25
    } else if (draggedDevice == "MXG") {
      x = 450;
      y = 100
    } else if (draggedDevice == "VSA") {
      x = 450;
      y = 275
    } else if (draggedDevice == "RFSW-1") {
      x = 200;
      y = 325
    } else if (draggedDevice == "RFSW-2") {
      x = 250;
      y = 175
    }

    let node = this.createNode(draggedDevice, x, y);
    console.log(node);
    console.log(this.nodes);
    this.nodes.push(node);
    console.log(this.nodes); // nodes are getting updated in to array
    this.cdr.detectChanges();
}

  createNode(text: any, x: any, y: any) {
    const node = {
      id: this.nodeId,
      point: { x: x, y: y },
      type: 'html-template',
      data: {
        text: text,
      }
    };
    this.nodeId++;
    return node;
  }
artem-mangilev commented 4 months ago

Well, yes, I said earlier the problem in this part (Angular does not detect changes inside vflow because input reference was not changed):

this.nodes.push(node);
console.log(this.nodes); // nodes are getting updated in to array
this.cdr.detectChanges();

You should re-create an array and add here your new node:

this.nodes = [...this.nodes, node]
chethan1095 commented 4 months ago

@artem-mangilev Thanks for the solution. This is one the best library and very easy to use great work.