Commit b164296c authored by Kruyff,D.L.W. (Dylan)'s avatar Kruyff,D.L.W. (Dylan)
Browse files

Fix average calculated + performance boost

parent eb452310
......@@ -50,9 +50,21 @@ export class ApiService {
return await response.json();
}
async getQueryWindow(window) {
const response = await fetch('http://127.0.0.1:5000/query', {
method: 'POST',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify({window})
});
return await response.json();
}
// Return similar windows based on an input query
async getSimilarWindows(query, tables) {
const response = await fetch('http://127.0.0.1:5000/query', {
const response = await fetch('http://127.0.0.1:5000/similarity', {
method: 'POST',
headers: {
'Accept': 'application/json',
......@@ -63,8 +75,20 @@ export class ApiService {
return await response.json();
}
async getAverageWindow(windows): Promise<number[][]> {
const response = await fetch('http://127.0.0.1:5000/average', {
async getAverageProgressWindows(windows): Promise<number[][]> {
const response = await fetch('http://127.0.0.1:5000/average-progress', {
method: 'POST',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify({windows})
});
return await response.json();
}
async getAverageTableWindows(windows): Promise<number[][]> {
const response = await fetch('http://127.0.0.1:5000/average-table', {
method: 'POST',
headers: {
'Accept': 'application/json',
......
......@@ -17,6 +17,7 @@ import { QueryWindowComponent } from './query-window/query-window.component';
import {ZingchartAngularModule} from 'zingchart-angular';
import { ProgressViewComponent } from './progress-view/progress-view.component';
import { MainComponent } from './main/main.component';
import { MatProgressBarModule} from '@angular/material/progress-bar';
PlotlyModule.plotlyjs = PlotlyJS;
......@@ -38,6 +39,7 @@ PlotlyModule.plotlyjs = PlotlyJS;
PlotlyModule,
BrowserAnimationsModule,
MatTabsModule,
MatProgressBarModule,
ZingchartAngularModule
],
providers: [],
......
......@@ -7,6 +7,7 @@ import {ApiService, RawData} from './api.service';
export class CacheService {
public rawValues: number[];
public rawIndices: string[];
public loadingProgress: number = 0;
private _currentTab: number;
private _query = undefined;
......@@ -14,6 +15,7 @@ export class CacheService {
private _tables;
private _windowSimilarity;
private _sliderValue;
private _queryWindow = [];
public windowSize = 500;
public nrOfTables = 10;
......@@ -30,23 +32,27 @@ export class CacheService {
public onNewTab: EventEmitter<void> = new EventEmitter<void>();
public onNewSlider: EventEmitter<void> = new EventEmitter<void>();
public initialized: Promise<void>;
constructor(private api: ApiService) {
this.initialized = this.initialize();
this.initialize();
}
async initialize(): Promise<void> {
this.loadingProgress = 0;
await this.getRawData();
this.loadingProgress = 30;
await this.createWindows();
this.loadingProgress = 60;
await this.createTables();
this.loadingProgress = 100;
}
async reset(): Promise<void> {
this.windowSimilarity = undefined;
this.loadingProgress = 30;
await this.createWindows();
this.loadingProgress = 60;
await this.createTables();
this.loadingProgress = 100;
}
async getRawData(): Promise<void> {
......@@ -65,13 +71,24 @@ export class CacheService {
this.tables = await this.api.createTables(this.parameters);
}
async getSimilarWindows(query): Promise<any> {
this.windowSimilarity = await this.api.getSimilarWindows(query, this.tables);
async getSimilarWindows(): Promise<any> {
this.windowSimilarity = await this.api.getSimilarWindows(this._queryWindow, this.tables);
console.log(this.windowSimilarity);
return this.windowSimilarity;
}
async getAverageWindow(windows): Promise<number[][]> {
return await this.api.getAverageWindow(windows);
async getAverageProgressWindows(windows): Promise<number[][]> {
return await this.api.getAverageProgressWindows(windows);
}
async getAverageTableWindows(windows): Promise<number[][]> {
return await this.api.getAverageTableWindows(windows);
}
async getQueryWindow(queryIndex): Promise<number[]> {
this._queryWindow = await this.api.getQueryWindow(this.rawValues.slice(queryIndex, queryIndex + this.windowSize));
console.log(this._queryWindow);
return this._queryWindow;
}
async updateTables(): Promise<void> {
......@@ -92,7 +109,6 @@ export class CacheService {
}
public set tables(v) {
console.log(v);
this._tables = v;
this.onNewTables.emit();
}
......@@ -112,7 +128,6 @@ export class CacheService {
public set windowSimilarity(v) {
this._windowSimilarity = v;
console.log(v);
this.onNewSimilarity.emit();
}
......@@ -138,6 +153,11 @@ export class CacheService {
return this._sliderValue;
}
public set queryWindow(v) {
this._queryWindow = v;
this.onNewQuery.emit();
}
public get parameters(): {[parameter: string]: any} {
return {
windowsize: this.windowSize,
......
......@@ -7,7 +7,8 @@
<button class="incorrect-button" [class.incorrect-selected]="labels[subplot.index] == false" (click)="labelIncorrect(subplot.index)">X</button>
</div>
</div>
<div class="button-holder">
<button *ngIf="windowSimilarity" (click)="changeTables()" class="label-button">Update tables</button>
</div>
</div>
<div class="button-holder">
<button *ngIf="windowSimilarity" (click)="changeTables()" class="label-button">Update tables</button>
</div>
......@@ -3,7 +3,7 @@
display: none;
width: 100%;
height: 100%;
top: 200px;
top: 0;
left: 0;
right: 0;
bottom: 0;
......@@ -12,6 +12,20 @@
cursor: pointer;
}
.loading-progress {
background-color: white;
z-index: 3;
width: 400px;
height: 200px;
position: absolute;
top:0;
bottom: 0;
left: 0;
right: 0;
margin: auto;
}
.show {
display: block;
}
......@@ -3,8 +3,8 @@
<app-overview-window style="z-index: 10"></app-overview-window>
<mat-tab-group animationDuration="0ms" (selectedTabChange)="changeTab($event)">
<mat-tab label="Training">
<app-labeling-window></app-labeling-window>
<app-table-overview></app-table-overview>
<app-labeling-window></app-labeling-window>
</mat-tab>
<mat-tab label="Labeled data">
<app-labels></app-labels>
......@@ -19,4 +19,12 @@
<app-progress-view></app-progress-view>
</div>
</div>
<div class="overlay" [class.show]="greyOut"></div>
<div class="overlay" [class.show]="greyOut" *ngIf="loadingProgress != 100"></div>
<div class="loading-progress" *ngIf="loadingProgress != 100">
<span *ngIf="loadingProgress == 0">Retrieving data</span>
<span *ngIf="loadingProgress == 30">Creating windows</span>
<span *ngIf="loadingProgress == 60">Creating initial tables</span>
<mat-progress-bar mode="determinate" [value]="loadingProgress">
</mat-progress-bar>
</div>
......@@ -18,4 +18,8 @@ export class MainComponent {
public get greyOut() {
return this.service.querySelectionMode;
}
public get loadingProgress(): number {
return this.service.loadingProgress;
}
}
<div style="overflow: auto">
<!-- <plotly-plot *ngIf="showPlot" [data]="data" [layout]="layout" (plotly_click)="clicked($event)"></plotly-plot>-->
</div>
<!--<div id="overview"></div>-->
<zingchart-angular [id]="id" [config]="config" (mousewheel)="zoom($event)" (click)="clicked($event)" [height]="200" [series]="series"></zingchart-angular>
<zingchart-angular [id]="id" [config]="config" (dblclick)="doubleClick($event)" (mousewheel)="zoom($event)" (click)="clicked($event)" [height]="200"></zingchart-angular>
import { Component} from '@angular/core';
import {Component, OnInit} from '@angular/core';
import { CacheService } from '../cache.service';
import zingchart from 'zingchart/es6';
......@@ -7,11 +7,13 @@ import zingchart from 'zingchart/es6';
templateUrl: './overview-window.component.html',
styleUrls: ['./overview-window.component.css']
})
export class OverviewWindowComponent {
export class OverviewWindowComponent implements OnInit {
public config;
public series;
public showPlot = false;
public id = "overview";
public markers = [];
public series = [];
public goodLabels = [];
public badLabels = [];
public data;
public layout;
......@@ -21,7 +23,6 @@ export class OverviewWindowComponent {
async ngOnInit(): Promise<void> {
this.service.onNewData.subscribe(() => this.initializePlot());
this.service.onNewWindows.subscribe(() => { });
this.service.onNewTables.subscribe(() => {
if (this.service.query) {
this.updatePlot();
......@@ -32,13 +33,39 @@ export class OverviewWindowComponent {
async initializePlot() {
this.service.query = undefined;
// this.data = this.service.rawIndices.map((e, i) => {
// return [e, values[i]];
// });
this.data = [];
for (let i = 0; i < this.service.rawValues.length; i++) {
this.data.push([i, this.service.rawValues[i]]);
}
this.series = [
{
type: 'line',
values: this.data,
text: 'Raw Values',
zIndex: 5,
marker: {
alpha: 0.0,
zIndex: 10
}
},
{
type: 'scatter',
values: [],
text: 'Good labels',
marker: {
backgroundColor: '#4caf50'
},
zIndex: 20,
},
{
type: 'scatter',
values: [],
text: 'Bad labels',
marker: {
backgroundColor: '#f44336'
},
zIndex: 20,
}];
this.config = {
type: "mixed",
preview: {
......@@ -48,58 +75,17 @@ export class OverviewWindowComponent {
"plotarea": {
"margin-top": "10px"
},
'scale-x': {
scaleX: {
zooming: true,
zoomTo: [0, this.service.windowSize],
'auto-fit': true
'auto-fit': true,
markers: this.markers
},
'scale-y': {
// zooming: true,
'auto-fit': true
},
series: [
{
type: 'line',
values: this.data,
text: 'Raw Values',
zIndex: 5,
marker: {
alpha: 0.0,
zIndex: 10
}
},
{
type: 'scatter',
values: [],
text: 'Good labels',
marker: {
backgroundColor: '#4caf50'
},
zIndex: 20,
},
{
type: 'scatter',
values: [],
text: 'Bad labels',
marker: {
backgroundColor: '#f44336'
},
zIndex: 20,
}]
series: this.series
};
// zingchart.render({
// id: 'overview',
// data: this.config,
// height: 200,
// width: '100%'
// });
// zingchart.bind('overview', 'click', (e) => {
// const xyInformation = zingchart.exec('overview', 'getxyinfo', {
// x: e.x,
// y: e.y
// });
// this.clicked({nodeindex: xyInformation[2].nodeidx});
// });
console.log("showing plot");
}
......@@ -112,8 +98,6 @@ export class OverviewWindowComponent {
x: clickData.x,
y: clickData.y
});
console.log('clicked node');
console.log(xyInformation);
const index = Math.floor(xyInformation[2].nodeidx / this.service.stepSize);
this.service.query = index;
const temp = {};
......@@ -123,62 +107,65 @@ export class OverviewWindowComponent {
}
async updatePlot() {
if (this.service.query) {
const windowSimilarity = await this.service.getSimilarWindows(this.service.query);
console.log('updating plot');
if (!this.service.query) {
return;
}
let goodLabels = [];
let badLabels = [];
this.goodLabels = [];
this.badLabels = [];
this.markers = [];
for (const index in this.service.labels) {
if (this.service.labels[index]) {
goodLabels.push(this.data[index]);
this.goodLabels.push(this.data[index]);
this.markers.push({
type: 'area',
// BUG: For some reason the range values are multiplied by 10
range: [this.data[index][0] / 10, (this.data[index][0] + this.service.windowSize) / 10],
backgroundColor: "#4caf50",
});
} else {
badLabels.push(this.data[index]);
this.badLabels.push(this.data[index]);
this.markers.push({
type: 'area',
// BUG: For some reason the range values are multiplied by 10
range: [this.data[index][0] / 10, (this.data[index][0] + this.service.windowSize) / 10],
backgroundColor: "#f44336",
});
}
}
this.series = [
{
type: 'line',
values: this.data,
text: 'Raw Values',
zIndex: 5,
marker: {
alpha: 0.0,
zIndex: 10
}
},
{
type: 'scatter',
values: goodLabels,
text: 'Good labels',
marker: {
backgroundColor: '#4caf50'
},
zIndex: 20,
},
{
type: 'scatter',
values: badLabels,
text: 'Bad labels',
marker: {
backgroundColor: '#f44336'
},
zIndex: 20,
}
];
this.series[1].values = this.goodLabels;
this.series[2].values = this.badLabels;
this.config.scaleX.markers = this.markers;
console.log(this.config);
zingchart.exec("zingchart-ng-1", 'setdata', {
data: this.config
});
console.log('querying');
await this.service.getQueryWindow(this.service.query);
await this.service.getSimilarWindows();
console.log('done');
}
async updateCandidates(sliderIndex) {
console.log("Updating chart");
console.log(this.service.windowSimilarity);
console.log(sliderIndex);
const candidates = this.service.windowSimilarity[sliderIndex.toString()];
let candidates = [];
for (let i = sliderIndex; i < this.service.nrOfTables; i++) {
console.log(i);
candidates = candidates.concat(this.service.windowSimilarity[sliderIndex.toString()]);
}
console.log(candidates);
const labels = [];
const markers = [];
for (const index of candidates) {
labels.push(this.data[index]);
markers.push({
type: 'area',
// BUG: For some reason the range values are multiplied by 10
range: [this.data[index][0] / 10, (this.data[index][0] + this.service.windowSize) / 10],
backgroundColor: "#b1a343",
});
}
console.log(labels);
const newSeries = this.series.slice(0, 3);
const newSeries = this.config.series.slice(0, 3);
newSeries.push({
type: 'scatter',
values: labels,
......@@ -188,15 +175,25 @@ export class OverviewWindowComponent {
},
zIndex: 20,
});
this.series = newSeries;
this.config.series = newSeries;
this.config.scaleX.markers = this.markers.concat(markers);
zingchart.exec("zingchart-ng-1", 'setdata', {
data: this.config
});
}
zoom(p) {
if (!p.ev) {
return;
}
if (p.ev.wheelDelta > 0) {
zingchart.exec("zingchart-ng-1", 'zoomin');
} else if (p.ev.wheelDelta < 0) {
zingchart.exec("zingchart-ng-1", 'zoomout');
}
console.log(p);
}
doubleClick(e) {
zingchart.exec("zingchart-ng-1", 'viewall');
}
}
......@@ -74,12 +74,16 @@ export class ProgressViewComponent implements OnInit {
}
async initializeInfo(): Promise<void> {
const keys = Object.keys(this.similarity).map(a => Number(a)).sort((a, b) => b - a);
const allWindows = [];
for (const key of keys) {
allWindows.push(this.similarity[key]);
const keys = Object.keys(this.similarity);
for (let i = this.cache.nrOfTables; i >= 1; i--) {
if (keys.indexOf(i.toString()) === -1) {
allWindows.push([]);
} else {
allWindows.push(this.similarity[i.toString()]);
}
}
const averages = await this.cache.getAverageWindow(allWindows);
const averages = await this.cache.getAverageProgressWindows(allWindows);
this.plot = this.averagePlot(averages);
}
......
......@@ -9,5 +9,4 @@
.subplot:hover {
cursor: pointer !important;
background-color: #4CAF50;
}
......@@ -7,6 +7,7 @@
<div class="plots">
<div class="subplot" *ngFor="let subplot of averages">
<plotly-plot [data]="subplot.data" [layout]="subplot.layout"></plotly-plot>
<button (click)="setQuery(subplot.data)">Use as query</button>
</div>
</div>
</div>
......@@ -14,7 +14,7 @@ export class TableOverviewComponent implements OnInit {
ngOnInit(): void {
this.service.onNewTables.subscribe(() => this.createPlots());
this.service.onNewQuery.subscribe(() => this.createPlots());
this.service.onNewSimilarity.subscribe(() => this.createPlots());
}
public get tables() {
......@@ -60,6 +60,7 @@ export class TableOverviewComponent implements OnInit {
const queryEntry = Object.keys(table.entries).filter((hash: string) => {
return table.entries[hash].indexOf(this.service.query) > -1;
})[0];
console.log(queryEntry);
listOfWindows.push(table.entries[queryEntry]);
}
this.subplots.push(
......@@ -103,9 +104,13 @@ export class TableOverviewComponent implements OnInit {