Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
GeoInt_SIDT
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Mario Chirinos Colunga
GeoInt_SIDT
Commits
72ad25cd
Commit
72ad25cd
authored
Jun 03, 2019
by
Ulises Morales Ramírez
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
fix report
parent
492f3714
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
207 additions
and
200 deletions
+207
-200
minimap.js
reports/static/reports/js/minimap.js
+207
-200
No files found.
reports/static/reports/js/minimap.js
View file @
72ad25cd
...
@@ -5,51 +5,51 @@ FIRST_IMAGE_LAYER_INDEX = 2;
...
@@ -5,51 +5,51 @@ FIRST_IMAGE_LAYER_INDEX = 2;
// create wkt polygon
// create wkt polygon
const
wktFormat
=
new
ol
.
format
.
WKT
();
const
wktFormat
=
new
ol
.
format
.
WKT
();
const
polygonFeature
=
wktFormat
.
readFeature
(
polygon
,
{
const
polygonFeature
=
wktFormat
.
readFeature
(
polygon
,
{
dataProjection
:
'EPSG:4326'
,
dataProjection
:
'EPSG:4326'
,
featureProjection
:
'EPSG:3857'
featureProjection
:
'EPSG:3857'
});
});
// Create layers
// Create layers
const
light
=
new
ol
.
layer
.
Tile
({
const
light
=
new
ol
.
layer
.
Tile
({
name
:
'mapbox'
,
name
:
'mapbox'
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
url
:
'https://api.tiles.mapbox.com/v4/mapbox.light/{z}/{x}/{y}.png?access_token='
+
MAPBOX_ACCESS_TOKEN
url
:
'https://api.tiles.mapbox.com/v4/mapbox.light/{z}/{x}/{y}.png?access_token='
+
MAPBOX_ACCESS_TOKEN
})
})
});
});
const
streets
=
new
ol
.
layer
.
Tile
({
const
streets
=
new
ol
.
layer
.
Tile
({
name
:
'mapbox'
,
name
:
'mapbox'
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
url
:
'http://tile.openstreetmap.org/{z}/{x}/{y}.png'
url
:
'http://tile.openstreetmap.org/{z}/{x}/{y}.png'
})
})
});
});
const
night
=
new
ol
.
layer
.
Tile
({
const
night
=
new
ol
.
layer
.
Tile
({
name
:
'mapbox'
,
name
:
'mapbox'
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
url
:
'https://api.mapbox.com/styles/v1/mapbox/navigation-guidance-night-v2/tiles/256/{z}/{x}/{y}?access_token='
+
MAPBOX_ACCESS_TOKEN
url
:
'https://api.mapbox.com/styles/v1/mapbox/navigation-guidance-night-v2/tiles/256/{z}/{x}/{y}?access_token='
+
MAPBOX_ACCESS_TOKEN
})
})
});
});
const
polygonLayer
=
new
ol
.
layer
.
Vector
({
const
polygonLayer
=
new
ol
.
layer
.
Vector
({
name
:
'polygon'
,
name
:
'polygon'
,
source
:
new
ol
.
source
.
Vector
({
source
:
new
ol
.
source
.
Vector
({
features
:
[
polygonFeature
]
features
:
[
polygonFeature
]
})
})
});
});
const
layers
=
new
Map
();
const
layers
=
new
Map
();
// create map
// create map
const
map
=
new
ol
.
Map
({
const
map
=
new
ol
.
Map
({
target
:
'minimap'
,
target
:
'minimap'
,
layers
:
[
light
,
polygonLayer
],
layers
:
[
light
,
polygonLayer
],
view
:
new
ol
.
View
({
view
:
new
ol
.
View
({
center
:
ol
.
proj
.
fromLonLat
([
-
99.19
,
19.61
]),
center
:
ol
.
proj
.
fromLonLat
([
-
99.19
,
19.61
]),
zoom
:
4
,
zoom
:
4
,
minZoom
:
4
minZoom
:
4
})
})
});
});
// fit (zoom) to polygon
// fit (zoom) to polygon
...
@@ -58,76 +58,78 @@ map.getView().fit(polygonFeature.getGeometry());
...
@@ -58,76 +58,78 @@ map.getView().fit(polygonFeature.getGeometry());
// show first layer date
// show first layer date
let
currentDate
=
labels
[
0
];
let
currentDate
=
labels
[
0
];
addImageLayer
({
addImageLayer
({
layerDate
:
currentDate
layerDate
:
currentDate
});
});
// main function to change layers
// main function to change layers
// data = { layerDate: to change all layers by date }
// data = { layerDate: to change all layers by date }
// data = { layerName: to add single layer }
// data = { layerName: to add single layer }
function
addImageLayer
(
data
)
{
function
addImageLayer
(
data
)
{
if
(
data
.
layerDate
)
{
if
(
data
.
layerDate
)
{
currentDate
=
data
.
layerDate
;
currentDate
=
data
.
layerDate
;
}
$
.
ajax
({
type
:
'POST'
,
dataType
:
"json"
,
data
:
{
'purchase_id'
:
purchase_id
,
'report'
:
zone
,
'date'
:
currentDate
},
url
:
'/reports/tiles/tileinfo'
,
success
:
response
=>
{
changeLayers
(
data
.
layerName
);
setOpacity
(
$
(
'#opacitySlide'
).
val
());
map
.
getView
().
setMinZoom
(
response
.
zoom
.
min
);
map
.
getView
().
setMaxZoom
(
response
.
zoom
.
max
);
}
}
});
$
.
ajax
({
type
:
'POST'
,
dataType
:
"json"
,
data
:
{
'purchase_id'
:
purchase_id
,
'report'
:
zone
,
'date'
:
currentDate
},
url
:
'/reports/tiles/tileinfo'
,
success
:
response
=>
{
changeLayers
(
data
.
layerName
);
setOpacity
(
$
(
'#opacitySlide'
).
val
());
map
.
getView
().
setMinZoom
(
response
.
zoom
.
min
);
map
.
getView
().
setMaxZoom
(
response
.
zoom
.
max
);
}
});
}
}
// remove old layers and add layers with new date
// remove old layers and add layers with new date
function
changeLayers
(
especific_layerName
)
{
function
changeLayers
(
especific_layerName
)
{
const
layersToChance
=
especific_layerName
?
especific_layerName
.
split
()
:
getSelectedLayersName
();
const
layersToChance
=
especific_layerName
?
especific_layerName
.
split
()
:
getSelectedLayersName
();
removeLayer
(
especific_layerName
);
removeLayer
(
especific_layerName
);
layersToChance
.
forEach
(
layerName
=>
{
layersToChance
.
forEach
(
layerName
=>
{
const
xyz
=
new
ol
.
layer
.
Tile
({
const
xyz
=
new
ol
.
layer
.
Tile
({
name
:
layerName
,
name
:
layerName
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
projection
:
'EPSG:3857'
,
projection
:
'EPSG:3857'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layerName
+
'/'
+
currentDate
+
'/{z}/{x}/{-y}.png'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layerName
+
'/'
+
currentDate
+
'/{z}/{x}/{-y}.png'
,
tilePixelRatio
:
2
tilePixelRatio
:
2
})
})
});
if
(
layerName
===
'TCI'
)
{
map
.
getLayers
().
insertAt
(
FIRST_IMAGE_LAYER_INDEX
,
xyz
);
}
else
{
map
.
addLayer
(
xyz
);
}
layers
.
set
(
layerName
,
xyz
);
});
});
if
(
layerName
===
'TCI'
)
{
map
.
getLayers
().
insertAt
(
FIRST_IMAGE_LAYER_INDEX
,
xyz
);
}
else
{
map
.
addLayer
(
xyz
);
}
layers
.
set
(
layerName
,
xyz
);
});
}
}
// remove all if there isn't layername
// remove all if there isn't layername
function
removeLayer
(
layerName
)
{
function
removeLayer
(
layerName
)
{
if
(
!
layerName
)
{
if
(
!
layerName
)
{
layers
.
forEach
(
layer
=>
{
map
.
removeLayer
(
layer
);
});
layers
.
forEach
(
layer
=>
{
layers
.
clear
();
map
.
removeLayer
(
layer
);
return
;
});
}
layers
.
clear
();
return
;
map
.
removeLayer
(
layers
.
get
(
layerName
));
}
layers
.
delete
(
layerName
);
map
.
removeLayer
(
layers
.
get
(
layerName
));
layers
.
delete
(
layerName
);
}
}
// set opacity to layers
// set opacity to layers
function
setOpacity
(
value
)
{
function
setOpacity
(
value
)
{
layers
.
forEach
(
layer
=>
{
layers
.
forEach
(
layer
=>
{
if
(
layer
.
get
(
'name'
)
!=
'TCI'
)
{
if
(
layer
.
get
(
'name'
)
!=
'TCI'
)
{
layer
.
setOpacity
(
value
)
layer
.
setOpacity
(
value
)
}
}
})
})
}
}
...
@@ -136,16 +138,16 @@ function setOpacity(value) {
...
@@ -136,16 +138,16 @@ function setOpacity(value) {
//vigila cuando se cierra el menu de comparar y cuando se cierra desactiva la comparacion (si la clase de compare incluye menu-open está abierto)
//vigila cuando se cierra el menu de comparar y cuando se cierra desactiva la comparacion (si la clase de compare incluye menu-open está abierto)
var
compareMenu
=
document
.
getElementById
(
'compare'
);
var
compareMenu
=
document
.
getElementById
(
'compare'
);
var
observer
=
new
MutationObserver
(
function
(
mutations
)
{
var
observer
=
new
MutationObserver
(
function
(
mutations
)
{
mutations
.
forEach
(
function
(
mutation
)
{
mutations
.
forEach
(
function
(
mutation
)
{
if
(
mutation
.
attributeName
==
'class'
)
{
if
(
mutation
.
attributeName
==
'class'
)
{
if
(
compareMenu
.
className
.
indexOf
(
"open"
)
===
-
1
)
{
//se cerró el menu de comparacion
if
(
compareMenu
.
className
.
indexOf
(
"open"
)
===
-
1
)
{
//se cerró el menu de comparacion
exitCompare
();
exitCompare
();
}
}
}
}
});
});
});
});
observer
.
observe
(
compareMenu
,
{
attributes
:
true
,
attributeOldValue
:
true
,
attributeFilter
:
[
'class'
],
subtree
:
true
});
observer
.
observe
(
compareMenu
,
{
attributes
:
true
,
attributeOldValue
:
true
,
attributeFilter
:
[
'class'
],
subtree
:
true
});
//crea el control swipe, que sirve para comparar
//crea el control swipe, que sirve para comparar
var
ctrl
=
new
ol
.
control
.
Swipe
();
var
ctrl
=
new
ol
.
control
.
Swipe
();
...
@@ -153,119 +155,124 @@ var ctrl = new ol.control.Swipe();
...
@@ -153,119 +155,124 @@ var ctrl = new ol.control.Swipe();
//funcion que inicia la comparacion
//funcion que inicia la comparacion
//recibe la lista de fechas y por default compara la primera y la ultima
//recibe la lista de fechas y por default compara la primera y la ultima
function
compare
(
labels
)
{
function
compare
(
labels
)
{
var
swipeControl
=
false
;
var
swipeControl
=
false
;
map
.
getControls
().
forEach
(
function
(
control
)
{
//checa si ya se añadio el control de comparacion (swipe), si no lo tiene, lo agrega
if
(
control
instanceof
ol
.
control
.
Swipe
)
{
//si ya tiene el control agregado
swipeControl
=
true
;
}
});
if
(
swipeControl
==
true
)
{
//si ya tiene el comparador no hace nada, ya esta en modo comparacion
//map.removeControl(swipeControlObj);
}
else
{
//si no tiene el comparador lo agrega
//removeImageLayers();
map
.
addControl
(
ctrl
);
ctrl
.
set
(
'position'
,
0.5
);
//console.log(map.controls)
var
labelDateLeft
=
labels
[
0
]
//por default compara la primera y ultima fecha
var
labelDateRight
=
labels
[
labels
.
length
-
1
]
//pone las fechas por default en los selectores de fechas
//document.getElementById("selectLeftCompare").value = labelDateLeft;
//document.getElementById("selectRightCompare").value = labelDateRight;
//agrega las capas izquierda/derecha
selectLeft
(
labelDateLeft
);
selectRight
(
labelDateRight
);
//muestra los selectores de fechas y oculta la linea de tiempo
document
.
getElementById
(
"selectLeft"
).
style
.
display
=
"block"
;
document
.
getElementById
(
"selectRight"
).
style
.
display
=
"block"
;
document
.
getElementById
(
"timeLine"
).
style
.
display
=
"none"
;
map
.
getControls
().
forEach
(
function
(
control
)
{
//checa si ya se añadio el control de comparacion (swipe), si no lo tiene, lo agrega
if
(
control
instanceof
ol
.
control
.
Swipe
){
//si ya tiene el control agregado
swipeControl
=
true
;
}
}
});
if
(
swipeControl
==
true
)
{
//si ya tiene el comparador no hace nada, ya esta en modo comparacion
//map.removeControl(swipeControlObj);
}
else
{
//si no tiene el comparador lo agrega
//removeImageLayers();
map
.
addControl
(
ctrl
);
ctrl
.
set
(
'position'
,
0.5
);
//console.log(map.controls)
var
labelDateLeft
=
labels
[
0
]
//por default compara la primera y ultima fecha
var
labelDateRight
=
labels
[
labels
.
length
-
1
]
//pone las fechas por default en los selectores de fechas
document
.
getElementById
(
"selectLeftCompare"
).
value
=
labelDateLeft
;
document
.
getElementById
(
"selectRightCompare"
).
value
=
labelDateRight
;
//agrega las capas izquierda/derecha
selectLeft
(
labelDateLeft
);
selectRight
(
labelDateRight
);
//muestra los selectores de fechas y oculta la linea de tiempo
document
.
getElementById
(
"selectLeft"
).
style
.
display
=
"block"
;
document
.
getElementById
(
"selectRight"
).
style
.
display
=
"block"
;
document
.
getElementById
(
"timeLine"
).
style
.
display
=
"none"
;
}
}
}
//sale del modo comparacion
//sale del modo comparacion
function
exitCompare
()
{
function
exitCompare
()
{
map
.
getControls
().
forEach
(
function
(
control
)
{
//checa si ya se añadio el control de comparacion (swipe)
map
.
getControls
().
forEach
(
function
(
control
)
{
//checa si ya se añadio el control de comparacion (swipe)
if
(
control
instanceof
ol
.
control
.
Swipe
)
{
//ya tiene el control agregado lo quita
if
(
control
instanceof
ol
.
control
.
Swipe
)
{
//ya tiene el control agregado lo quita
map
.
removeControl
(
control
);
map
.
removeControl
(
control
);
}
}
});
});
//quita las capas de comparacion izquierda/derecha
//quita las capas de comparacion izquierda/derecha
var
imageLayers
=
map
.
getLayers
().
getArray
().
slice
();
var
imageLayers
=
map
.
getLayers
().
getArray
().
slice
();
imageLayers
.
forEach
(
layer
=>
{
imageLayers
.
forEach
(
layer
=>
{
if
(
layer
.
get
(
'name'
)
===
'left'
||
layer
.
get
(
'name'
)
===
'right'
)
{
if
(
layer
.
get
(
'name'
)
===
'left'
||
layer
.
get
(
'name'
)
===
'right'
)
{
map
.
removeLayer
(
layer
)
map
.
removeLayer
(
layer
)
}
}
})
})
//oculta los selectores de fechas y muestra la linea de tiempo
//oculta los selectores de fechas y muestra la linea de tiempo
document
.
getElementById
(
"selectLeft"
).
style
.
display
=
"none"
;
document
.
getElementById
(
"selectLeft"
).
style
.
display
=
"none"
;
document
.
getElementById
(
"selectRight"
).
style
.
display
=
"none"
;
document
.
getElementById
(
"selectRight"
).
style
.
display
=
"none"
;
document
.
getElementById
(
"timeLine"
).
style
.
display
=
"block"
;
document
.
getElementById
(
"timeLine"
).
style
.
display
=
"block"
;
}
}
//selecciona el lado izquierdo para comparar
//selecciona el lado izquierdo para comparar
function
selectLeft
(
date
)
{
function
selectLeft
(
date
)
{
var
labelDateLeft
=
date
;
var
labelDateLeft
=
date
;
var
layer_type
=
'TCI'
;
var
layer_type
=
'TCI'
;
const
left
=
new
ol
.
layer
.
Tile
({
const
left
=
new
ol
.
layer
.
Tile
({
name
:
'left'
,
name
:
'left'
,
opacity
:
1
,
opacity
:
1
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
projection
:
'EPSG:3857'
,
projection
:
'EPSG:3857'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layer_type
+
'/'
+
labelDateLeft
+
'/{z}/{x}/{-y}.png'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layer_type
+
'/'
+
labelDateLeft
+
'/{z}/{x}/{-y}.png'
,
tilePixelRatio
:
2
,
tilePixelRatio
:
2
,
minZoom
:
10
,
minZoom
:
10
,
maxZoom
:
15
maxZoom
:
15
})
})
});
});
map
.
addLayer
(
left
);
map
.
addLayer
(
left
);
ctrl
.
addLayer
(
left
);
ctrl
.
addLayer
(
left
);
}
}
//selecciona el lado derecho para comparar
//selecciona el lado derecho para comparar
function
selectRight
(
date
){
function
selectRight
(
date
)
{
console
.
log
(
"---------"
);
console
.
log
(
"---------"
);
console
.
log
(
date
)
console
.
log
(
date
)
console
.
log
(
"---------"
);
console
.
log
(
"---------"
);
var
labelDateRight
=
date
;
var
labelDateRight
=
date
;
var
layer_type
=
'TCI'
;
var
layer_type
=
'TCI'
;
const
right
=
new
ol
.
layer
.
Tile
({
const
right
=
new
ol
.
layer
.
Tile
({
name
:
'right'
,
name
:
'right'
,
opacity
:
1
,
opacity
:
1
,
source
:
new
ol
.
source
.
XYZ
({
source
:
new
ol
.
source
.
XYZ
({
projection
:
'EPSG:3857'
,
projection
:
'EPSG:3857'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layer_type
+
'/'
+
labelDateRight
+
'/{z}/{x}/{-y}.png'
,
url
:
'/reports/tiles/'
+
purchase_id
+
'/'
+
zone
+
'/'
+
layer_type
+
'/'
+
labelDateRight
+
'/{z}/{x}/{-y}.png'
,
tilePixelRatio
:
2
,
tilePixelRatio
:
2
,
minZoom
:
10
,
minZoom
:
10
,
maxZoom
:
15
maxZoom
:
15
})
})
});
});
map
.
addLayer
(
right
);
map
.
addLayer
(
right
);
ctrl
.
addLayer
(
right
,
true
);
ctrl
.
addLayer
(
right
,
true
);
}
}
//selecciona comparacion vertical u horizontal
//selecciona comparacion vertical u horizontal
function
setCompareDirection
(
direction
){
function
setCompareDirection
(
direction
)
{
ctrl
.
set
(
'orientation'
,
direction
)
ctrl
.
set
(
'orientation'
,
direction
)
//mueve los selectores de fechas
//mueve los selectores de fechas
if
(
direction
===
'horizontal'
)
{
if
(
direction
===
'horizontal'
)
{
document
.
getElementById
(
"selectLeft"
).
style
.
bottom
=
"70%"
;
document
.
getElementById
(
"selectLeft"
).
style
.
bottom
=
"70%"
;
document
.
getElementById
(
"selectLeft"
).
style
.
left
=
"15%"
;
document
.
getElementById
(
"selectLeft"
).
style
.
left
=
"15%"
;
document
.
getElementById
(
"selectRight"
).
style
.
left
=
"15%"
;
document
.
getElementById
(
"selectRight"
).
style
.
left
=
"15%"
;
}
}
else
{
else
{
document
.
getElementById
(
"selectLeft"
).
style
.
bottom
=
"50px"
;
document
.
getElementById
(
"selectLeft"
).
style
.
bottom
=
"50px"
;
document
.
getElementById
(
"selectLeft"
).
style
.
left
=
"30%"
;
document
.
getElementById
(
"selectLeft"
).
style
.
left
=
"30%"
;
document
.
getElementById
(
"selectRight"
).
style
.
left
=
"75%"
;
document
.
getElementById
(
"selectRight"
).
style
.
left
=
"75%"
;
}
}
}
}
// Fin funciones de comparacion
// Fin funciones de comparacion
//******************************
//******************************
...
@@ -273,36 +280,36 @@ function setCompareDirection(direction){
...
@@ -273,36 +280,36 @@ function setCompareDirection(direction){
let
currentMap
=
light
;
let
currentMap
=
light
;
function
changeMap
(
selectedMap
)
{
function
changeMap
(
selectedMap
)
{
map
.
getLayers
().
getArray
().
forEach
(
function
(
layer
)
{
map
.
getLayers
().
getArray
().
forEach
(
function
(
layer
)
{
if
(
layer
.
values_
.
name
==
"mapbox"
)
{
if
(
layer
.
values_
.
name
==
"mapbox"
)
{
map
.
removeLayer
(
layer
)
map
.
removeLayer
(
layer
)
}
})
$
(
'#'
+
selectedMap
).
prop
(
'checked'
,
true
);
switch
(
selectedMap
)
{
case
'light'
:
map
.
getLayers
().
insertAt
(
0
,
light
);
currentMap
=
light
;
break
;
case
'streets'
:
map
.
getLayers
().
insertAt
(
0
,
streets
);
currentMap
=
streets
;
break
;
case
'night'
:
map
.
getLayers
().
insertAt
(
0
,
night
);
currentMap
=
night
;
break
;
}
}
})
$
(
'#'
+
selectedMap
).
prop
(
'checked'
,
true
);
switch
(
selectedMap
)
{
case
'light'
:
map
.
getLayers
().
insertAt
(
0
,
light
);
currentMap
=
light
;
break
;
case
'streets'
:
map
.
getLayers
().
insertAt
(
0
,
streets
);
currentMap
=
streets
;
break
;
case
'night'
:
map
.
getLayers
().
insertAt
(
0
,
night
);
currentMap
=
night
;
break
;
}
}
}
function
showControlMap
(){
function
showControlMap
()
{
if
(
$
(
'#showControlMap'
).
is
(
':visible'
))
{
if
(
$
(
'#showControlMap'
).
is
(
':visible'
))
{
$
(
"#showControlMap"
).
hide
();
$
(
"#showControlMap"
).
hide
();
$
(
"#hideControlMap"
).
show
();
$
(
"#hideControlMap"
).
show
();
$
(
".mapControl"
).
show
();
$
(
".mapControl"
).
show
();
}
else
{
}
else
{
$
(
"#showControlMap"
).
show
();
$
(
"#showControlMap"
).
show
();
$
(
"#hideControlMap"
).
hide
();
$
(
"#hideControlMap"
).
hide
();
$
(
".mapControl"
).
hide
();
$
(
".mapControl"
).
hide
();
}
}
}
}
\ No newline at end of file
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment