Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
vig
Sublinear Algorithms for VA
pseudo
Commits
9726baff
Commit
9726baff
authored
Mar 30, 2021
by
Kruyff,D.L.W. (Dylan)
Browse files
Last tweaks and experiments
Former-commit-id:
2b44deb8
parent
b89119be
Changes
104
Expand all
Hide whitespace changes
Inline
Side-by-side
AngularApp/prototype/src/app/api.service.ts
View file @
9726baff
...
...
@@ -15,6 +15,11 @@ export interface LshData {
average_table
:
{[
bucket
:
string
]:
number
[]};
samples
:
number
[];
hash_functions
:
number
[][];
prototype
:
{
average
:
number
[][];
min
:
number
[][];
max
:
number
[][];
};
parameters
?:
number
[];
}
...
...
@@ -114,8 +119,15 @@ export class ApiService {
/**
* Calculate the LSH parameters
*/
async
getParameters
():
Promise
<
number
[]
>
{
const
response
=
await
fetch
(
'
http://127.0.0.1:5000/get-lsh-parameters
'
);
async
getParameters
(
windowsize
):
Promise
<
number
[]
>
{
const
response
=
await
fetch
(
'
http://127.0.0.1:5000/get-lsh-parameters
'
,
{
method
:
'
POST
'
,
headers
:
{
'
Accept
'
:
'
application/json
'
,
'
Content-Type
'
:
'
application/json
'
},
body
:
new
Blob
(
[
JSON
.
stringify
({
windowsize
})
],
{
type
:
'
text/plain
'
}
)
});
return
await
response
.
json
();
}
...
...
AngularApp/prototype/src/app/labeling-window/labeling-window.component.ts
View file @
9726baff
...
...
@@ -17,7 +17,11 @@ export class LabelingWindowComponent implements OnInit {
ngOnInit
():
void
{
this
.
state
.
onNewLshData
.
subscribe
(()
=>
this
.
showSamples
());
this
.
state
.
onNewSelection
.
subscribe
(()
=>
{
this
.
updateChannels
();
});
this
.
state
.
onNewSelection
.
subscribe
(()
=>
{
if
(
this
.
topk
)
{
this
.
updateChannels
();
}
});
}
public
labelCorrect
(
index
:
number
)
{
...
...
AngularApp/prototype/src/app/main/main.component.css
View file @
9726baff
...
...
@@ -83,13 +83,14 @@ mat-tab-group {
}
.channel_header
{
height
:
20
px
;
height
:
18
px
;
background-color
:
lightblue
;
border-bottom
:
1px
solid
lightgray
;
color
:
black
;
font-weight
:
400
;
color
:
white
;
text-align
:
center
;
vertical-align
:
middle
;
font-weight
:
bold
;
padding
:
2px
;
}
app-overview-window
{
...
...
AngularApp/prototype/src/app/main/main.component.html
View file @
9726baff
<div
class=
"container"
>
<as-split
direction=
"vertical"
>
<as-split-area
[size]=
"
35
"
>
<as-split-area
[size]=
"
40
"
>
<as-split
direction=
"horizontal"
>
<as-split-area
[size]=
"70"
>
...
...
@@ -18,7 +18,7 @@
</as-split>
</as-split-area>
<as-split-area
[size]=
"6
5
"
>
<as-split-area
[size]=
"6
0
"
>
<as-split
direction=
"horizontal"
>
<as-split-area
[size]=
"62"
>
...
...
AngularApp/prototype/src/app/overview-window/overview-window.component.css
View file @
9726baff
...
...
@@ -108,13 +108,13 @@ path {
}
.channel_header
{
height
:
20px
;
background-color
:
lightblue
;
border-bottom
:
1px
solid
lightgray
;
color
:
black
;
font-weight
:
400
;
color
:
white
;
text-align
:
center
;
vertical-align
:
middle
;
font-weight
:
bold
;
padding
:
2px
;
}
.container
{
...
...
AngularApp/prototype/src/app/overview-window/overview-window.component.html
View file @
9726baff
...
...
@@ -23,18 +23,18 @@
<div
class=
"toolbar"
>
<label
class=
"small-margin"
for=
"min"
>
Start
</label><br>
<input
class=
"small-margin"
id=
"min"
[(ngModel)]=
"minx"
>
<input
type=
"number"
class=
"small-margin"
id=
"min"
[(ngModel)]=
"minx"
>
<label
class=
"small-margin"
for=
"max"
>
End
</label><br>
<input
class=
"small-margin"
[(ngModel)]=
"maxx"
id=
"max"
>
<input
type=
"number"
class=
"small-margin"
[(ngModel)]=
"maxx"
id=
"max"
>
<label
class=
"small-margin"
for=
"w"
>
Window Size
</label><br>
<input
class=
"small-margin"
[
disabled]=
"true"
[value]=
"maxx - minx
"
id=
"w"
>
<input
type=
"number"
class=
"small-margin"
[
(ngModel)]=
"windowsize
"
id=
"w"
>
<button
(click)=
"setquery()"
>
Set as query
</button>
</div>
<div
class=
"overview"
id=
"overview"
>
<div
class=
"overview"
id=
"overview"
(wheel)=
"scroll($event)"
>
<!-- <zingchart-angular #chart [id]="id" (wheel)="scroll($event)" [height]="height"></zingchart-angular>-->
</div>
</as-split-area>
...
...
AngularApp/prototype/src/app/overview-window/overview-window.component.ts
View file @
9726baff
...
...
@@ -24,6 +24,7 @@ export class OverviewWindowComponent implements OnInit {
private
_minx
;
private
_maxx
;
public
currentSelection
;
private
showingCandidates
=
false
;
public
data
;
public
layout
;
...
...
@@ -36,85 +37,28 @@ export class OverviewWindowComponent implements OnInit {
this
.
initialHeight
=
this
.
el
.
nativeElement
.
offsetHeight
;
// this.state.onNewData.subscribe(() => this.dostuff3());
this
.
state
.
onNewData
.
subscribe
(()
=>
this
.
initializePlot
());
this
.
state
.
onNewLshData
.
subscribe
(()
=>
this
.
updatePlot
());
this
.
state
.
onNewLshData
.
subscribe
(()
=>
{
this
.
showingCandidates
=
false
;
this
.
updatePlot
();
});
this
.
state
.
onNewSelection
.
subscribe
(()
=>
{
this
.
currentSelection
=
this
.
state
.
selection
;
this
.
updateChannels
();
if
(
this
.
showingCandidates
)
{
this
.
updateCandidates
();
}
});
this
.
state
.
onNewSlider
.
subscribe
(()
=>
this
.
updateCandidates
());
}
dostuff3
()
{
let
y_val
=
0
;
let
N
=
200000
;
let
values
=
d3
.
range
(
N
).
map
(
function
(
x
,
i
,
arr
)
{
y_val
+=
Math
.
random
()
-
0.5
;
return
{
x
:
x
,
y
:
y_val
,
id
:
i
};
this
.
state
.
onNewSlider
.
subscribe
(()
=>
{
this
.
showingCandidates
=
true
;
this
.
updateCandidates
();
});
let
margin
=
{
top
:
30
,
right
:
30
,
bottom
:
30
,
left
:
20
};
let
width
=
600
-
margin
.
left
-
margin
.
right
;
let
height
=
150
-
margin
.
top
-
margin
.
bottom
;
const
svg
=
d3
.
select
(
'
.test
'
)
.
append
(
"
svg
"
)
.
attr
(
"
width
"
,
width
+
margin
.
left
+
margin
.
right
)
.
attr
(
"
height
"
,
height
+
margin
.
top
+
margin
.
bottom
)
.
append
(
"
g
"
)
.
attr
(
"
transform
"
,
"
translate(
"
+
margin
.
left
+
"
,
"
+
margin
.
top
+
"
)
"
);
let
xscale
=
d3
.
scaleLinear
().
domain
([
0
,
N
]).
range
([
0
,
N
]);
const
x2
=
xscale
.
copy
();
// reference.
const
yscale
=
d3
.
scaleLinear
().
domain
([
-
10
,
10
]).
range
([
height
,
0
]);
const
line
=
d3
.
line
()
.
x
(
function
(
d
:
any
)
{
return
xscale
(
d
.
x
);
})
.
y
(
function
(
d
:
any
)
{
return
yscale
(
d
.
y
);
})
const
axis
=
d3
.
axisBottom
(
xscale
);
const
axis_G
=
svg
.
append
(
"
g
"
)
.
attr
(
"
transform
"
,
"
translate(0,
"
+
height
+
"
)
"
)
.
call
(
axis
);
const
axis_left
=
svg
.
append
(
"
g
"
)
.
call
(
d3
.
axisLeft
(
yscale
));
const
lines
=
svg
.
append
(
'
g
'
)
.
data
([
values
])
.
append
(
'
path
'
)
.
attr
(
"
fill
"
,
"
none
"
)
.
attr
(
"
stroke
"
,
"
steelblue
"
)
.
attr
(
"
stroke-width
"
,
1.5
)
.
attr
(
'
class
'
,
'
data
'
)
.
attr
(
'
d
'
,
(
d
:
any
)
=>
line
(
d
));
const
zoomed
=
function
()
{
const
transform
=
d3
.
event
.
transform
;
// lines.attr("transform", d3.event.transform);
xscale
=
transform
.
rescaleX
(
x2
);
axis
.
scale
(
xscale
);
axis_G
.
call
(
axis
);
svg
.
select
(
'
.data
'
).
attr
(
'
d
'
,
(
d
:
any
)
=>
{
return
d3
.
line
()
.
x
(
function
(
d
:
any
)
{
return
transform
.
applyX
(
xscale
(
d
.
x
));
})
.
y
(
function
(
d
:
any
)
{
return
yscale
(
d
.
y
);
})(
d
);
});
};
const
zoom
=
d3
.
zoom
()
.
scaleExtent
([
1
,
10000
])
.
on
(
'
zoom
'
,
zoomed
);
svg
.
call
(
zoom
);
}
async
initializePlot
()
{
this
.
allChannels
=
[...
Array
(
this
.
state
.
rawData
.
length
).
keys
()];
this
.
state
.
queryWindow
=
undefined
;
console
.
log
(
this
.
state
.
rawData
[
0
].
values
.
length
-
1
);
console
.
log
(
this
.
state
.
rawData
[
0
].
index
[
this
.
state
.
rawData
[
0
].
index
.
length
-
1
]);
// this.debugClicked();
this
.
graphset
.
push
({
id
:
'
preview
'
,
...
...
@@ -123,9 +67,11 @@ export class OverviewWindowComponent implements OnInit {
y
:
0
,
scaleX
:
{
zooming
:
true
,
step
:
1
,
minValue
:
0
,
maxValue
:
this
.
state
.
rawData
[
0
].
values
.
length
,
'
auto-fit
'
:
true
,
maxValue
:
this
.
state
.
rawData
[
0
].
values
.
length
-
1
,
// zoomTo: [0, this.state.windowSize],
// 'auto-fit': true,
visible
:
false
,
guide
:
{
visible
:
false
...
...
@@ -153,7 +99,7 @@ export class OverviewWindowComponent implements OnInit {
marker
:
{
backgroundColor
:
'
#4caf50
'
},
zIndex
:
3
,
zIndex
:
10
,
},
{
type
:
'
scatter
'
,
...
...
@@ -162,16 +108,26 @@ export class OverviewWindowComponent implements OnInit {
marker
:
{
backgroundColor
:
'
#f44336
'
},
zIndex
:
2
,
zIndex
:
10
,
},
{
type
:
'
scatter
'
,
values
:
[],
text
:
'
Candidates
'
,
marker
:
{
backgroundColor
:
'
#
b1a343
'
backgroundColor
:
'
#
808080
'
},
zIndex
:
1
,
zIndex
:
10
,
},
{
type
:
'
scatter
'
,
values
:
[[
0
,
1
]],
text
:
'
Bug
'
,
marker
:
{
visible
:
false
,
backgroundColor
:
'
#808080
'
},
zIndex
:
10
,
}
]
});
...
...
@@ -180,28 +136,41 @@ export class OverviewWindowComponent implements OnInit {
this
.
state
.
selection
.
forEach
((
channelIndex
,
index
)
=>
{
const
channel
=
this
.
state
.
rawData
[
channelIndex
];
const
data
=
[];
for
(
let
i
=
0
;
i
<
channel
.
values
.
length
;
i
++
)
{
data
.
push
([
i
,
channel
.
values
[
i
]]);
}
// for (let i = 0; i < channel.values.length; i++) {
// data.push(channel.values[i]);
// }
console
.
log
(
data
);
this
.
graphset
.
push
({
id
:
index
,
x
:
0
,
y
:
`
${
75
*
index
+
5
0
}
px`
,
y
:
`
${
75
*
index
+
10
0
}
px`
,
type
:
'
line
'
,
height
:
'
50px
'
,
scaleX
:
{
zooming
:
true
,
markers
:
[]
},
plot
:
{
exact
:
false
,
smartSampling
:
true
,
sampleStep
:
1
,
// scroll step 1 is not sampling. Setting this this value to 2 will sample every other data point
scrollStepMultiplier
:
5
,
hintTs
:
true
,
// tells the library you have timestamps as keys and activates a small optimization technique
maxNodes
:
150
,
// max nodes to have event listeners for eg) tooltips wont show but crosshair will
maxTrackers
:
150
,
'
min-value
'
:
channel
.
index
[
0
],
step
:
"
6minute
"
,
transform
:
{
type
:
"
date
"
,
all
:
"
%m/%d/%Y<br>%h:%i
"
},
tick
:
{
visible
:
index
===
0
,
},
item
:
{
visible
:
index
===
0
,
},
placement
:
'
top
'
,
},
// plot: {
// exact: false,
// smartSampling: true,
// sampleStep: 1, // scroll step 1 is not sampling. Setting this this value to 2 will sample every other data point
// scrollStepMultiplier: 5,
// hintTs: true, // tells the library you have timestamps as keys and activates a small optimization technique
// maxNodes: 150, // max nodes to have event listeners for eg) tooltips wont show but crosshair will
// maxTrackers: 150,
// },
'
scale-y
'
:
{
zooming
:
false
,
'
auto-fit
'
:
true
...
...
@@ -212,9 +181,7 @@ export class OverviewWindowComponent implements OnInit {
'
margin-bot
'
:
'
0px
'
},
series
:
[{
type
:
'
line
'
,
values
:
data
,
text
:
'
Raw Values
'
,
values
:
channel
.
values
,
zIndex
:
5
,
'
line-color
'
:
this
.
state
.
colors
[
channelIndex
],
marker
:
{
...
...
@@ -237,8 +204,8 @@ export class OverviewWindowComponent implements OnInit {
'
overview
'
,
'
zoomto
'
,
{
graphid
:
`overview-graph-preview`
,
xmin
:
e
.
x
min
,
xmax
:
e
.
x
max
,
xmin
:
this
.
_
min
x
,
xmax
:
this
.
_
max
x
,
stopupdate
:
true
});
}
...
...
@@ -250,8 +217,8 @@ export class OverviewWindowComponent implements OnInit {
'
overview
'
,
'
zoomto
'
,
{
graphid
:
i
,
xmin
:
e
.
x
min
,
xmax
:
e
.
x
max
,
xmin
:
this
.
_
min
x
,
xmax
:
this
.
_
max
x
,
stopupdate
:
true
});
}
...
...
@@ -265,7 +232,7 @@ export class OverviewWindowComponent implements OnInit {
// });
console
.
log
(
"
showing plot
"
);
this
.
_minx
=
0
;
this
.
_maxx
=
this
.
state
.
rawData
[
0
].
values
.
length
/
1
0
;
this
.
_maxx
=
this
.
state
.
rawData
[
0
].
values
.
length
/
1
;
zingchart
.
render
({
id
:
'
overview
'
,
data
:
this
.
config
,
...
...
@@ -285,28 +252,31 @@ export class OverviewWindowComponent implements OnInit {
this
.
graphset
=
this
.
graphset
.
slice
(
0
,
1
);
this
.
state
.
selection
.
forEach
((
channelIndex
,
index
)
=>
{
const
channel
=
this
.
state
.
rawData
[
channelIndex
];
const
data
=
[];
for
(
let
i
=
0
;
i
<
channel
.
values
.
length
;
i
++
)
{
data
.
push
([
i
,
channel
.
values
[
i
]]);
}
//
const data = [];
//
for (let i = 0; i < channel.values.length; i++) {
//
data.push([i, channel.values[i]]);
//
}
this
.
graphset
.
push
({
id
:
channelIndex
,
x
:
0
,
y
:
`
${
75
*
index
+
5
0
}
px`
,
y
:
`
${
75
*
index
+
10
0
}
px`
,
type
:
'
line
'
,
height
:
'
50px
'
,
scaleX
:
{
zooming
:
true
,
markers
:
[]
},
plot
:
{
exact
:
false
,
smartSampling
:
true
,
sampleStep
:
1
,
// scroll step 1 is not sampling. Setting this this value to 2 will sample every other data point
scrollStepMultiplier
:
5
,
hintTs
:
true
,
// tells the library you have timestamps as keys and activates a small optimization technique
maxNodes
:
150
,
// max nodes to have event listeners for eg) tooltips wont show but crosshair will
maxTrackers
:
150
,
'
min-value
'
:
channel
.
index
[
0
],
step
:
"
6minute
"
,
transform
:
{
type
:
"
date
"
,
all
:
"
%m/%d/%Y<br>%h:%i
"
},
tick
:
{
visible
:
index
===
0
,
},
item
:
{
visible
:
index
===
0
,
},
placement
:
'
top
'
,
},
'
scale-y
'
:
{
zooming
:
false
,
...
...
@@ -319,7 +289,7 @@ export class OverviewWindowComponent implements OnInit {
},
series
:
[{
type
:
'
line
'
,
values
:
data
,
values
:
channel
.
values
,
text
:
'
Raw Values
'
,
zIndex
:
5
,
'
line-color
'
:
this
.
state
.
colors
[
channelIndex
],
...
...
@@ -335,17 +305,11 @@ export class OverviewWindowComponent implements OnInit {
graphset
:
this
.
graphset
};
console
.
log
(
"
showing plot
"
);
// this.chart.setdata({
// data: this.config
// });
zingchart
.
exec
(
'
overview
'
,
'
setdata
'
,
{
data
:
this
.
config
}
);
// this.chart.addgraph(this.graphset[4]);
this
.
minx
=
0
;
this
.
maxx
=
120
;
}
async
updatePlot
()
{
...
...
@@ -361,16 +325,16 @@ export class OverviewWindowComponent implements OnInit {
this
.
goodLabels
.
push
([
Number
(
index
),
1
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
"
#4caf50
"
,
});
}
else
{
this
.
badLabels
.
push
([
Number
(
index
),
-
1
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
"
#f44336
"
,
});
}
...
...
@@ -379,9 +343,9 @@ export class OverviewWindowComponent implements OnInit {
this
.
candidateLabels
.
push
([
Number
(
index
),
0
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
backgroundColor
:
'
#
b1a343
'
,
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
'
#
808080
'
,
});
}
console
.
log
(
this
.
markers
);
...
...
@@ -392,6 +356,7 @@ export class OverviewWindowComponent implements OnInit {
channel
.
series
[
0
].
values
=
this
.
goodLabels
;
channel
.
series
[
1
].
values
=
this
.
badLabels
;
channel
.
series
[
2
].
values
=
this
.
candidateLabels
;
channel
.
series
[
2
].
marker
.
backgroundColor
=
'
#808080
'
;
}
}
zingchart
.
exec
(
...
...
@@ -423,16 +388,16 @@ export class OverviewWindowComponent implements OnInit {
this
.
goodLabels
.
push
([
Number
(
index
),
1
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
"
#4caf50
"
,
});
}
else
{
this
.
badLabels
.
push
([
Number
(
index
),
-
1
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
"
#f44336
"
,
});
}
...
...
@@ -441,8 +406,8 @@ export class OverviewWindowComponent implements OnInit {
this
.
candidateLabels
.
push
([
Number
(
index
),
0
]);
this
.
markers
.
push
({
type
:
'
area
'
,
// BUG: For some reason the range values are multiplied by 1
0
range
:
[
Number
(
index
)
/
1
0
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
0
],
// BUG: For some reason the range values are multiplied by 1
range
:
[
Number
(
index
)
/
1
,
(
Number
(
index
)
+
this
.
state
.
windowSize
)
/
1
],
backgroundColor
:
'
#b1a343
'
,
});
}
...
...
@@ -454,6 +419,7 @@ export class OverviewWindowComponent implements OnInit {
channel
.
series
[
0
].
values
=
this
.
goodLabels
;
channel
.
series
[
1
].
values
=
this
.
badLabels
;
channel
.
series
[
2
].
values
=
this
.
candidateLabels
;
channel
.
series
[
2
].
marker
.
backgroundColor
=
'
#b1a343
'
;
}
}
zingchart
.
exec
(
...
...
@@ -463,41 +429,12 @@ export class OverviewWindowComponent implements OnInit {
);
}
// async clicked(clickData) {
// console.log(clickData);
// if (!this.state.querySelectionMode) {
// return;
// }
// this.state.querySelectionMode = false;
// await this.debugClicked();
// return;
// const xyInformation = zingchart.exec('zingchart-ng-1', 'getxyinfo', {
// x: clickData.x,
// y: clickData.y
// });
// const index = Math.floor(xyInformation[0].scalenumvalue / (12000 / 6));
// await this.state.getQueryWindow(index);
// await this.state.lshInitial();
// const temp = {};
// temp[index] = true;
// this.state.labels = temp;
// }
//
// async debugClicked() {
// const index = 6713;
// await this.state.getQueryWindow(index);
// await this.state.lshInitial();
// const temp = {};
// temp[index] = true;
// this.state.labels = temp;
// }
scroll
(
p
)
{
p
.
stopPropagation
();
console
.
log
(
'
mousewheel
'
);
console
.
log
(
p
);
console
.
log
(
p
.
deltaY
);
const
q
=
Math
.
round
((
this
.
_maxx
-
this
.
_minx
)
/
1
0
);
const
q
=
Math
.
round
((
this
.
_maxx
-
this
.
_minx
)
/
1
);
if
(
p
.
deltaY
>
0
)
{
this
.
_minx
=
Math
.
max
(
this
.
_minx
-
q
,
0
);
this
.
_maxx
=
Math
.
max
(
this
.
_maxx
-
q
,
0
);
...
...
@@ -545,11 +482,11 @@ export class OverviewWindowComponent implements OnInit {
}