aboutsummaryrefslogtreecommitdiff
path: root/frontend/src/app
diff options
context:
space:
mode:
authorDanijel Anđelković <adanijel99@gmail.com>2022-04-29 00:44:09 +0200
committerDanijel Anđelković <adanijel99@gmail.com>2022-04-29 00:44:09 +0200
commit9d73bc044eaea6176556935a81db8e654476e6f1 (patch)
treee7a5b8f2ff85d14933df73c1a30ef47ac2a13973 /frontend/src/app
parent1b9e3a2470d1123b362ad47725bd76b2eb7b39eb (diff)
Promenio liniju u grafu modela na bezier krivu, dodao ispis ulazne kolone / aktivacione funkcije sloja na hoveru preko cvora.
Diffstat (limited to 'frontend/src/app')
-rw-r--r--frontend/src/app/_data/Model.ts2
-rw-r--r--frontend/src/app/_elements/folder/folder.component.html2
-rw-r--r--frontend/src/app/_elements/folder/folder.component.ts9
-rw-r--r--frontend/src/app/_elements/form-model/form-model.component.html4
-rw-r--r--frontend/src/app/_elements/form-model/form-model.component.ts44
-rw-r--r--frontend/src/app/_elements/graph/graph.component.css17
-rw-r--r--frontend/src/app/_elements/graph/graph.component.html9
-rw-r--r--frontend/src/app/_elements/graph/graph.component.ts53
8 files changed, 92 insertions, 48 deletions
diff --git a/frontend/src/app/_data/Model.ts b/frontend/src/app/_data/Model.ts
index c1f3d108..6281748c 100644
--- a/frontend/src/app/_data/Model.ts
+++ b/frontend/src/app/_data/Model.ts
@@ -33,7 +33,7 @@ export class Layer {
constructor(
public layerNumber: number = 0,
public activationFunction: ActivationFunction = ActivationFunction.Sigmoid,
- public neurons: number = 1,
+ public neurons: number = 3,
public regularisation: Regularisation = Regularisation.L1,
public regularisationRate: RegularisationRate = RegularisationRate.RR1,
) { }
diff --git a/frontend/src/app/_elements/folder/folder.component.html b/frontend/src/app/_elements/folder/folder.component.html
index b4e90e56..763a82a1 100644
--- a/frontend/src/app/_elements/folder/folder.component.html
+++ b/frontend/src/app/_elements/folder/folder.component.html
@@ -59,7 +59,7 @@
<mat-icon>zoom_out_map</mat-icon>
</button>
</div>
- <app-form-model [model]="fileToDisplay" *ngSwitchCase="FolderType.Model"></app-form-model>
+ <app-form-model [model]="fileToDisplay" [forExperiment]="forExperiment" *ngSwitchCase="FolderType.Model"></app-form-model>
<app-form-dataset *ngSwitchCase="FolderType.Dataset"></app-form-dataset>
</div>
<div *ngSwitchCase="true" class="list-view">
diff --git a/frontend/src/app/_elements/folder/folder.component.ts b/frontend/src/app/_elements/folder/folder.component.ts
index 23a982fb..eb1b9b98 100644
--- a/frontend/src/app/_elements/folder/folder.component.ts
+++ b/frontend/src/app/_elements/folder/folder.component.ts
@@ -1,5 +1,6 @@
import { Component, EventEmitter, Input, OnInit, Output } from '@angular/core';
-import Dataset from 'src/app/_data/Dataset';
+import Dataset, { ColumnInfo } from 'src/app/_data/Dataset';
+import Experiment from 'src/app/_data/Experiment';
import { FolderFile, FolderType } from 'src/app/_data/FolderFile';
import Model from 'src/app/_data/Model';
import { DatasetsService } from 'src/app/_services/datasets.service';
@@ -19,6 +20,8 @@ export class FolderComponent implements OnInit {
@Input() type: FolderType = FolderType.Dataset;
+ @Input() forExperiment?: Experiment;
+
newFileSelected: boolean = true;
selectedFileIndex: number = -1;
@@ -32,10 +35,12 @@ export class FolderComponent implements OnInit {
searchTerm: string = '';
- myDatasets : Dataset[] = [];
+ myDatasets: Dataset[] = [];
constructor(private datasets: DatasetsService) {
//PLACEHOLDER
+ this.forExperiment = new Experiment();
+ this.forExperiment.inputColumns = ['kolona1', 'kol2', '???', 'test'];
this.datasets.getMyDatasets().subscribe((datasets) => {
this.myDatasets = datasets;
diff --git a/frontend/src/app/_elements/form-model/form-model.component.html b/frontend/src/app/_elements/form-model/form-model.component.html
index f11b609d..d5187383 100644
--- a/frontend/src/app/_elements/form-model/form-model.component.html
+++ b/frontend/src/app/_elements/form-model/form-model.component.html
@@ -90,7 +90,7 @@
<!--kraj unosa parametara-->
<hr>
<div class="m-2">
- <app-graph [model]="newModel" [inputCols]="newModel.inputColNum"></app-graph>
+ <app-graph [model]="newModel" [inputColumns]="forExperiment?.inputColumns"></app-graph>
</div>
<div class="ns-row">
@@ -121,7 +121,7 @@
<div class="ns-col">
<mat-form-field appearance="fill" class="mat-fix">
<mat-label>Broj Neurona svih slojeva</mat-label>
- <input matInput type="number" [(ngModel)]="selectedNumberOfNeurons" (change)="changeAllNumberOfNeurons()">
+ <input matInput type="number" min="1" max="18" [(ngModel)]="selectedNumberOfNeurons" (change)="changeAllNumberOfNeurons()">
</mat-form-field>
</div>
<div class="break-2"></div>
diff --git a/frontend/src/app/_elements/form-model/form-model.component.ts b/frontend/src/app/_elements/form-model/form-model.component.ts
index 062c380e..e58d1764 100644
--- a/frontend/src/app/_elements/form-model/form-model.component.ts
+++ b/frontend/src/app/_elements/form-model/form-model.component.ts
@@ -60,7 +60,7 @@ export class FormModelComponent implements AfterViewInit {
showMyModels: boolean = true;
updateGraph() {
- console.log(this.newModel.layers);
+ //console.log(this.newModel.layers);
this.graph.update();
}
@@ -73,7 +73,7 @@ export class FormModelComponent implements AfterViewInit {
}
addLayer() {
if (this.newModel.hiddenLayers < 128) {
- this.newModel.layers.push(new Layer(this.newModel.layers.length));
+ this.newModel.layers.push(new Layer(this.newModel.layers.length, this.selectedActivation, this.selectedNumberOfNeurons, this.selectedRegularisation, this.selectedRegularisationRate));
this.newModel.hiddenLayers += 1;
this.updateGraph();
@@ -106,37 +106,33 @@ export class FormModelComponent implements AfterViewInit {
selectedActivation: ActivationFunction = ActivationFunction.Sigmoid;
selectedRegularisationRate: RegularisationRate = RegularisationRate.RR1;
selectedRegularisation: Regularisation = Regularisation.L1;
- selectedNumberOfNeurons:number=1;
+ selectedNumberOfNeurons: number = 3;
+
+ changeAllActivation() {
+ for (let i = 0; i < this.newModel.layers.length; i++) {
+ this.newModel.layers[i].activationFunction = this.selectedActivation;
- changeAllActivation(){
- for(let i=0;i<this.newModel.layers.length;i++)
- {
- this.newModel.layers[i].activationFunction=this.selectedActivation;
-
}
-
+
}
- changeAllRegularisation(){
- for(let i=0;i<this.newModel.layers.length;i++)
- {
- this.newModel.layers[i].regularisation=this.selectedRegularisation;
+ changeAllRegularisation() {
+ for (let i = 0; i < this.newModel.layers.length; i++) {
+ this.newModel.layers[i].regularisation = this.selectedRegularisation;
}
}
- changeAllRegularisationRate(){
+ changeAllRegularisationRate() {
- for(let i=0;i<this.newModel.layers.length;i++)
- {
- this.newModel.layers[i].regularisationRate=this.selectedRegularisationRate;
+ for (let i = 0; i < this.newModel.layers.length; i++) {
+ this.newModel.layers[i].regularisationRate = this.selectedRegularisationRate;
}
}
- changeAllNumberOfNeurons(){
- for(let i=0;i<this.newModel.layers.length;i++)
- {
- this.newModel.layers[i].neurons=this.selectedNumberOfNeurons;
+ changeAllNumberOfNeurons() {
+ for (let i = 0; i < this.newModel.layers.length; i++) {
+ this.newModel.layers[i].neurons = this.selectedNumberOfNeurons;
this.updateGraph();
}
}
-
-
-
+
+
+
}
diff --git a/frontend/src/app/_elements/graph/graph.component.css b/frontend/src/app/_elements/graph/graph.component.css
index e69de29b..361e7249 100644
--- a/frontend/src/app/_elements/graph/graph.component.css
+++ b/frontend/src/app/_elements/graph/graph.component.css
@@ -0,0 +1,17 @@
+.node-text {
+ position: absolute;
+ color: transparent;
+ width: 100px;
+ height: 40px;
+ text-align: center;
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ justify-content: center;
+ /*border: 1px solid red;*/
+ transform: translate(-50%, -50%);
+}
+
+.node-text:hover {
+ color: var(--offwhite);
+} \ No newline at end of file
diff --git a/frontend/src/app/_elements/graph/graph.component.html b/frontend/src/app/_elements/graph/graph.component.html
index b8220115..19e5c14a 100644
--- a/frontend/src/app/_elements/graph/graph.component.html
+++ b/frontend/src/app/_elements/graph/graph.component.html
@@ -1,3 +1,8 @@
-<div #graphWrapper class="w-100" style="height: 14rem;">
+<div #graphWrapper class="w-100 position-relative" style="height: 14rem;">
+ <ng-container *ngFor="let layer of layers; let i = index">
+ <div class="node-text" *ngFor="let node of layer; let j = index" [style.left.%]="node.x * 99.4" [style.top.%]="node.y * 100">
+ {{ i == 0 ? (inputColumns ? inputColumns[j] : 'nepoznato') : (i > 0 && i
+ < layers.length - 1 ? model!.layers[i-1].activationFunction : (i==layers.length - 1 ? 'out' : '')) }} </div>
+ </ng-container>
<canvas #graphCanvas></canvas>
-</div> \ No newline at end of file
+ </div> \ No newline at end of file
diff --git a/frontend/src/app/_elements/graph/graph.component.ts b/frontend/src/app/_elements/graph/graph.component.ts
index 5dec3152..31814c2c 100644
--- a/frontend/src/app/_elements/graph/graph.component.ts
+++ b/frontend/src/app/_elements/graph/graph.component.ts
@@ -1,5 +1,6 @@
import { AfterViewInit, Component, ElementRef, Input, OnInit, ViewChild } from '@angular/core';
-import Dataset from 'src/app/_data/Dataset';
+import { RgbColor } from '@syncfusion/ej2-angular-heatmap';
+import Dataset, { ColumnInfo } from 'src/app/_data/Dataset';
import Model, { Layer } from 'src/app/_data/Model';
@Component({
@@ -15,18 +16,19 @@ export class GraphComponent implements AfterViewInit {
canvas!: ElementRef;
@Input() model?: Model;
- @Input() inputCols: number = 1;
+ //@Input() inputCols: number = 1;
@Input() lineThickness: number = 2;
@Input() nodeRadius: number = 15;
- @Input() lineColor: string = '#00a8e8';
+ @Input() lineColor1: RgbColor = new RgbColor(0, 168, 232);
+ @Input() lineColor2: RgbColor = new RgbColor(0, 70, 151);
@Input() nodeColor: string = '#222277';
@Input() borderColor: string = '#00a8e8';
@Input() inputNodeColor: string = '#00a8e8';
@Input() outputNodeColor: string = '#dfd7d7';
private ctx!: CanvasRenderingContext2D;
- @Input() inputNeurons: number = 1;
+ @Input() inputColumns?: string[] = [];
constructor() { }
@@ -43,16 +45,16 @@ export class GraphComponent implements AfterViewInit {
this.resize();
}
- layers?: Node[][];
+ layers: Node[][] = [];
update() {
- this.layers = [];
+ this.layers.length = 0;
let inputNodeIndex = 0;
const inputLayer: Node[] = [];
- while (inputNodeIndex < this.inputCols) {
+ while (this.inputColumns && inputNodeIndex < this.inputColumns.length) {
const x = 0.5 / (this.model!.hiddenLayers + 2);
- const y = (inputNodeIndex + 0.5) / this.inputCols;
+ const y = (inputNodeIndex + 0.5) / this.inputColumns.length;
const node = new Node(x, y, this.inputNodeColor);
inputLayer.push(node);
inputNodeIndex += 1;
@@ -94,27 +96,36 @@ export class GraphComponent implements AfterViewInit {
}
for (let layer of this.layers!) {
- for (let node of layer) {
- this.drawNode(node);
- }
+ layer.forEach((node, index) => {
+ this.drawNode(node, 0.5 / layer.length + 0.5);
+ });
}
}
+ bezierOffset = 5;
+
drawLine(node1: Node, node2: Node) {
- this.ctx.strokeStyle = this.lineColor;
+ const lineColor: RgbColor = this.lerpColor(this.lineColor1, this.lineColor2, node1.y);
+ this.ctx.strokeStyle = `rgb(${lineColor.R}, ${lineColor.G}, ${lineColor.B})`;
this.ctx.lineWidth = this.lineThickness;
this.ctx.beginPath();
this.ctx.moveTo(node1.x * this.width, node1.y * this.height);
- this.ctx.lineTo(node2.x * this.width, node2.y * this.height);
+ //this.ctx.lineTo(node2.x * this.width, node2.y * this.height);
+ const middle = (node1.x + (node2.x - node1.x) / 2) * this.width;
+ this.ctx.bezierCurveTo(
+ middle, node1.y * this.height,
+ middle, node2.y * this.height,
+ node2.x * this.width, node2.y * this.height);
this.ctx.stroke();
}
- drawNode(node: Node) {
+ drawNode(node: Node, sizeMult: number) {
+ const lineColor: RgbColor = this.lerpColor(this.lineColor1, this.lineColor2, node.y);
+ this.ctx.strokeStyle = `rgb(${lineColor.R}, ${lineColor.G}, ${lineColor.B})`;
this.ctx.fillStyle = node.color;
- this.ctx.strokeStyle = this.borderColor;
this.ctx.lineWidth = this.lineThickness;
this.ctx.beginPath();
- this.ctx.arc(node.x * this.width, node.y * this.height, this.nodeRadius, 0, 2 * Math.PI);
+ this.ctx.arc(node.x * this.width, node.y * this.height, this.nodeRadius * sizeMult, 0, 2 * Math.PI);
this.ctx.fill();
this.ctx.stroke();
}
@@ -135,6 +146,16 @@ export class GraphComponent implements AfterViewInit {
this.draw();
}
+
+ lerpColor(value1: RgbColor, value2: RgbColor, amount: number): RgbColor {
+ const newColor = new RgbColor(0, 0, 0);
+ amount = amount < 0 ? 0 : amount;
+ amount = amount > 1 ? 1 : amount;
+ newColor.R = value1.R + (value2.R - value1.R) * amount;
+ newColor.G = value1.G + (value2.G - value1.G) * amount;
+ newColor.B = value1.B + (value2.B - value1.B) * amount;
+ return newColor;
+ };
}
class Node {