740 lines
21 KiB
JavaScript
740 lines
21 KiB
JavaScript
mapboxgl.accessToken = 'pk.eyJ1Ijoib3V0ZG9vcm1hcHBpbmdjb21wYW55IiwiYSI6ImNqYmh3cDdjYzNsMnozNGxsYzlvMmk2bTYifQ.QqcZ4LVoLWnXafXdjZxnZg';
|
||
const map = new mapboxgl.Map({
|
||
container: 'map',
|
||
center: [20, 80],
|
||
zoom: 4
|
||
});
|
||
|
||
import * as turf from "@turf/turf";
|
||
|
||
import { getArrowPolygon } from "./Arrow.js";
|
||
import { ARROW_BODY_STYLE_CONSTANT, ARROW_BODY_STYLE_LINEAR, ARROW_BODY_STYLE_EXPONENTIAL } from "./Arrow.js";
|
||
import { getCirclePolygon } from "./BasicShapes.js";
|
||
import { getRectanglePolygon } from "./BasicShapes.js";
|
||
import { getFrontline } from "./Frontline.js";
|
||
import { LEFT_SIDE, RIGHT_SIDE, BOTH_SIDES } from "./Frontline.js";
|
||
// Polygon merge using Turf library
|
||
import {mergeTurfPolygons} from "./Polygon.js";
|
||
import {addTurfPolygonToMerge} from "./Polygon.js";
|
||
import {toTurfPolygon} from "./Polygon.js";
|
||
|
||
const circleCenter = {x:320, y:180};
|
||
const circleRadius = 70;
|
||
const circleDensity = 15;
|
||
|
||
const circleCenterB = {x:400, y:280};
|
||
const circleRadiusB = 70;
|
||
const circleDensityB = 15;
|
||
|
||
const rectangleCenter= {x:100, y:300};
|
||
const rectangleSideA = 70;
|
||
const rectangleSideB = 200;
|
||
const rectangleRotation = 40;
|
||
|
||
const frontlinePointsA = [
|
||
{ x: 120, y: 400 },
|
||
{ x: 200, y: 100 },
|
||
{ x: 350, y: 200 },
|
||
{ x: 350, y: 400 },
|
||
{ x: 450, y: 480 },
|
||
{ x: 550, y: 440 },
|
||
{ x: 600, y: 300 },
|
||
];
|
||
|
||
const frontlinePointsB = [
|
||
{ x: 420, y: 280 },
|
||
{ x: 430, y: 380 },
|
||
{ x: 500, y: 400 },
|
||
{ x: 520, y: 300 },
|
||
];
|
||
|
||
const frontlinePointsC = [
|
||
{ x: 450, y: 200 },
|
||
{ x: 500, y: 250 },
|
||
{ x: 550, y: 250 },
|
||
{ x: 550, y: 200 }
|
||
];
|
||
|
||
|
||
const frontlineDataA = {
|
||
points: frontlinePointsA,
|
||
splineStep: 0.08,
|
||
spacing: 10,
|
||
offsetDistance: 10,
|
||
protrusionLength: 15,
|
||
protrusionStartSize: 5,
|
||
protrusionEndSize: 2,
|
||
protrusionGap: 20,
|
||
style: LEFT_SIDE,
|
||
};
|
||
|
||
const frontlineDataB = {
|
||
points: frontlinePointsB,
|
||
splineStep: 0.02,
|
||
spacing: 10,
|
||
offsetDistance: 10,
|
||
protrusionLength: 15,
|
||
protrusionStartSize: 5,
|
||
protrusionEndSize: 5,
|
||
protrusionGap: 20,
|
||
style: RIGHT_SIDE,
|
||
};
|
||
|
||
const frontlineDataC = {
|
||
points: frontlinePointsC,
|
||
splineStep: 0.02,
|
||
spacing: 10,
|
||
offsetDistance: 10,
|
||
protrusionLength: 15,
|
||
protrusionStartSize: 5,
|
||
protrusionEndSize: 0,
|
||
protrusionGap: 20,
|
||
style: BOTH_SIDES,
|
||
};
|
||
|
||
/*
|
||
const arrowPolygonA = getArrowPolygon(arrowDataA, styleA, arrowHeadDataA);
|
||
const arrowPolygonB = getArrowPolygon(arrowDataB, styleB, arrowHeadDataB);
|
||
const arrowPolygonC = getArrowPolygon(arrowDataC, styleC);
|
||
|
||
const circlePolygon = getCirclePolygon(circleCenter, circleRadius, circleDensity);
|
||
const circlePolygonB = getCirclePolygon(circleCenterB, circleRadiusB, circleDensityB);
|
||
const rectanglePolygon = getRectanglePolygon(rectangleCenter, rectangleSideA, rectangleSideB, rectangleRotation);
|
||
|
||
const mergedTurfPoly = mergeTurfPolygons(arrowPolygonA, arrowPolygonC);
|
||
const mergedTurfPolyAll = addTurfPolygonToMerge(mergedTurfPoly, arrowPolygonB);
|
||
|
||
const mergedTurfPolyRectangle = addTurfPolygonToMerge(mergedTurfPolyAll, rectanglePolygon);
|
||
const mergedRectangle = mergeTurfPolygons(circlePolygon, circlePolygonB);
|
||
|
||
const rectanglePoly = getRectanglePolygon(circleCenter, rectangleSideA, rectangleSideB, rectangleRotation*-1);
|
||
const rectangleToTurfPoly = toTurfPolygon(rectanglePoly);
|
||
|
||
const frontlinePolygonA = getFrontline(frontlineDataA);
|
||
let frontlinePolygonMergedA = mergeTurfPolygons(frontlinePolygonA.body,frontlinePolygonA.protrusions[0]);
|
||
for (let i = 1; i < frontlinePolygonA.protrusions.length; i++)
|
||
{
|
||
frontlinePolygonMergedA = addTurfPolygonToMerge(frontlinePolygonMergedA, frontlinePolygonA.protrusions[i]);
|
||
}
|
||
|
||
const frontlinePolygonB = getFrontline(frontlineDataB);
|
||
let frontlinePolygonMergedB = mergeTurfPolygons(frontlinePolygonB.body,frontlinePolygonB.protrusions[0]);
|
||
for (let i = 1; i < frontlinePolygonB.protrusions.length; i++)
|
||
{
|
||
frontlinePolygonMergedB = addTurfPolygonToMerge(frontlinePolygonMergedB, frontlinePolygonB.protrusions[i]);
|
||
}
|
||
|
||
const frontlinePolygonC = getFrontline(frontlineDataC);
|
||
|
||
let frontlinePolygonMergedLeft = mergeTurfPolygons(frontlinePolygonC.bodyLeft, frontlinePolygonC.protrusionsLeft[0]);
|
||
for (let i = 1; i < frontlinePolygonC.protrusionsLeft.length; i++) {
|
||
frontlinePolygonMergedLeft = addTurfPolygonToMerge(frontlinePolygonMergedLeft, frontlinePolygonC.protrusionsLeft[i]);
|
||
}
|
||
|
||
let frontlinePolygonMergedRight = mergeTurfPolygons(frontlinePolygonC.bodyRight, frontlinePolygonC.protrusionsRight[0]);
|
||
for (let i = 1; i < frontlinePolygonC.protrusionsRight.length; i++) {
|
||
frontlinePolygonMergedRight = addTurfPolygonToMerge(frontlinePolygonMergedRight, frontlinePolygonC.protrusionsRight[i]);
|
||
}*/
|
||
|
||
//const circleGeoJSON = getCircleGeoJSON({x: 20, y: 80}, 2, 50, map);
|
||
|
||
const pointsB = [
|
||
{ x: 70, y: 38 },
|
||
{ x: 71, y: 45},
|
||
{ x: 65, y: 50 },
|
||
{ x: 70, y: 53}
|
||
];
|
||
|
||
const arrowDataB = {
|
||
points: pointsB,
|
||
splineStep: 0.01,
|
||
spacing: 0.01,
|
||
offsetDistance: 1
|
||
};
|
||
const styleB = {
|
||
calculation: ARROW_BODY_STYLE_LINEAR,
|
||
range: 1,
|
||
minValue: 0.1
|
||
};
|
||
const arrowHeadDataB = {
|
||
widthArrow: 1,
|
||
lengthArrow: 1
|
||
};
|
||
|
||
const arrowPolygonB = getArrowPolygon(arrowDataB, styleB, arrowHeadDataB);
|
||
const pointsC= [
|
||
{ x: 50, y: 38 },
|
||
{ x: 51, y: 45},
|
||
{ x: 45, y: 50 },
|
||
{ x: 48, y: 55}
|
||
];
|
||
|
||
const arrowDataC = {
|
||
points: pointsC,
|
||
splineStep: 0.02,
|
||
spacing: 1,
|
||
offsetDistance: 1
|
||
};
|
||
const styleC = {
|
||
calculation: ARROW_BODY_STYLE_LINEAR,
|
||
range: 1,
|
||
minValue: 0.1
|
||
};
|
||
const arrowHeadDataC = {
|
||
widthArrow: 1,
|
||
lengthArrow: 1
|
||
};
|
||
|
||
const arrowPolygonC = getArrowPolygon(arrowDataC, styleC, arrowHeadDataC);
|
||
|
||
const points = [
|
||
{ x: 80, y: 20 },
|
||
{ x: 81, y: 22},
|
||
{ x: 82, y: 28 },
|
||
{ x: 81, y: 30},
|
||
{ x: 80, y: 20}
|
||
];
|
||
|
||
// Turf polygon
|
||
const turfPolygon = turf.polygon([[
|
||
[20, 80],
|
||
[22, 81],
|
||
[28, 82],
|
||
[30, 81],
|
||
[20, 80]
|
||
]]);
|
||
|
||
const pointsA= [
|
||
{ x: 80, y: 38 },
|
||
{ x: 81, y: 45},
|
||
{ x: 75, y: 50 },
|
||
{ x: 78, y: 55}
|
||
];
|
||
|
||
const arrowDataA = {
|
||
points: pointsA,
|
||
splineStep: 0.2,
|
||
spacing: 3,
|
||
offsetDistance: 1
|
||
};
|
||
const styleA = {
|
||
calculation: ARROW_BODY_STYLE_LINEAR,
|
||
range: 1,
|
||
minValue: 0.1
|
||
};
|
||
const arrowHeadDataA = {
|
||
widthArrow: 1,
|
||
lengthArrow: 1
|
||
};
|
||
|
||
const arrowPolygonA = getArrowPolygon(arrowDataA, styleA, arrowHeadDataA);
|
||
|
||
const latLonGrid = generateLatLonGrid(5);
|
||
|
||
|
||
function createIsoscelesTriangle(center, baseLengthMeters, heightMeters, bearing = 0) {
|
||
const halfBase = baseLengthMeters / 2;
|
||
|
||
// Výpočet bodů základny (levý a pravý bod)
|
||
const leftBase = turf.destination(center, halfBase, bearing - 90, { units: 'meters' });
|
||
const rightBase = turf.destination(center, halfBase, bearing + 90, { units: 'meters' });
|
||
|
||
// Výpočet vrcholu trojúhelníku – směr daný bearing (nahoru např. 0°)
|
||
const apex = turf.destination(center, heightMeters, bearing, { units: 'meters' });
|
||
|
||
const triangle = turf.polygon([[
|
||
leftBase.geometry.coordinates,
|
||
rightBase.geometry.coordinates,
|
||
apex.geometry.coordinates,
|
||
leftBase.geometry.coordinates // Uzavření polygonu
|
||
]]);
|
||
|
||
return triangle;
|
||
}
|
||
|
||
|
||
|
||
|
||
|
||
function cubicInterpolate(p, x) {
|
||
return p[1] + 0.5 * x * (p[2] - p[0] + x * (2.0 * p[0] - 5.0 * p[1] + 4.0 * p[2] - p[3] + x * (3.0 * (p[1] - p[2]) + p[3] - p[0])));
|
||
}
|
||
|
||
function interpolatePointsCatmullRom(points, segments = 10) {
|
||
if (points.length < 2) return points;
|
||
|
||
const extended = [points[0], ...points, points[points.length - 1]];
|
||
const interpolated = [];
|
||
|
||
for (let i = 1; i < extended.length - 2; i++) {
|
||
for (let j = 0; j < segments; j++) {
|
||
const t = j / segments;
|
||
const lon = cubicInterpolate([extended[i - 1][0], extended[i][0], extended[i + 1][0], extended[i + 2][0]], t);
|
||
const lat = cubicInterpolate([extended[i - 1][1], extended[i][1], extended[i + 1][1], extended[i + 2][1]], t);
|
||
interpolated.push([lon, lat]);
|
||
}
|
||
}
|
||
interpolated.push(points[points.length - 1]);
|
||
return interpolated;
|
||
}
|
||
function computeSideOffsets(points, offsetMeters) {
|
||
const left = [];
|
||
const right = [];
|
||
|
||
for (let i = 1; i < points.length; i++) {
|
||
const prev = points[i - 1];
|
||
const curr = points[i];
|
||
const bearing = turf.bearing(turf.point(prev), turf.point(curr));
|
||
|
||
const leftOffset = turf.destination(turf.point(curr), offsetMeters, bearing - 90, { units: 'meters' });
|
||
const rightOffset = turf.destination(turf.point(curr), offsetMeters, bearing + 90, { units: 'meters' });
|
||
|
||
left.push(leftOffset.geometry.coordinates);
|
||
right.push(rightOffset.geometry.coordinates);
|
||
}
|
||
|
||
return { left, right };
|
||
}
|
||
|
||
function createIsoscelesTriangleCoords(center, baseLengthMeters, heightMeters, bearing) {
|
||
const halfBase = baseLengthMeters / 2;
|
||
const left = turf.destination(center, halfBase, bearing - 90, { units: 'meters' }).geometry.coordinates;
|
||
const right = turf.destination(center, halfBase, bearing + 90, { units: 'meters' }).geometry.coordinates;
|
||
const tip = turf.destination(center, heightMeters, bearing, { units: 'meters' }).geometry.coordinates;
|
||
console.log("Aktuální bod:", left);
|
||
console.log("Aktuální bod:", right);
|
||
console.log("Aktuální bod:", tip);
|
||
return [left, right, tip];
|
||
}
|
||
|
||
function drawArrowPolygon(map, basePoints, offset = 10000) {
|
||
const smooth = interpolatePointsCatmullRom(basePoints, 20);
|
||
const { leftSidePoints, rightSidePoints } = computeSidesWGS84(smooth, offset);
|
||
|
||
console.log("Aktuální bod:", tip);
|
||
const end = smooth[smooth.length - 1];
|
||
const prev = smooth[smooth.length - 2];
|
||
const bearing = turf.bearing(turf.point(prev), turf.point(end));
|
||
|
||
const triangleCoords = createIsoscelesTriangleCoords(turf.point(end), offset * 2, offset * 3, bearing);
|
||
|
||
const polygonCoords = [
|
||
...leftSidePoints,
|
||
...triangleCoords,
|
||
...rightSidePoints.reverse(),
|
||
leftSidePoints[0]
|
||
];
|
||
|
||
const fullPolygon = turf.polygon([[...polygonCoords]]);
|
||
|
||
map.addSource("arrow-shape", {
|
||
type: "geojson",
|
||
data: fullPolygon
|
||
});
|
||
|
||
map.addLayer({
|
||
id: "arrow-shape",
|
||
type: "fill",
|
||
source: "arrow-shape",
|
||
paint: {
|
||
"fill-color": "#ff0000",
|
||
"fill-opacity": 0.7
|
||
}
|
||
});
|
||
}
|
||
|
||
function computeSidesWGS84(points, offsetDistanceMeters = 1000) {
|
||
const leftSidePoints = [];
|
||
const rightSidePoints = [];
|
||
|
||
|
||
for (let i = 1; i < points.length; i++) {
|
||
const prev = points[i - 1];
|
||
const curr = points[i];
|
||
|
||
const bearing = turf.bearing(turf.point(prev), turf.point(curr));
|
||
const leftBearing = bearing - 90;
|
||
const rightBearing = bearing + 90;
|
||
|
||
const leftPoint = turf.destination(turf.point(curr), offsetDistanceMeters, leftBearing, { units: 'meters' });
|
||
const rightPoint = turf.destination(turf.point(curr), offsetDistanceMeters, rightBearing, { units: 'meters' });
|
||
|
||
leftSidePoints.push(leftPoint.geometry.coordinates);
|
||
rightSidePoints.push(rightPoint.geometry.coordinates);
|
||
}
|
||
|
||
// První bod
|
||
const first = points[0];
|
||
const second = points[1];
|
||
const initialBearing = turf.bearing(turf.point(first), turf.point(second));
|
||
const leftInitial = turf.destination(turf.point(first), offsetDistanceMeters, initialBearing - 90, { units: 'meters' });
|
||
const rightInitial = turf.destination(turf.point(first), offsetDistanceMeters, initialBearing + 90, { units: 'meters' });
|
||
|
||
leftSidePoints.unshift(leftInitial.geometry.coordinates);
|
||
rightSidePoints.unshift(rightInitial.geometry.coordinates);
|
||
|
||
console.log("Aktuální bod:", leftSidePoints);
|
||
console.log("Aktuální bod:", rightSidePoints);
|
||
return {
|
||
leftSidePoints,
|
||
rightSidePoints
|
||
};
|
||
}
|
||
|
||
function drawSideLines(map, sides, prefix = "arrow-side") {
|
||
map.addSource(`${prefix}-left`, {
|
||
type: "geojson",
|
||
data: turf.lineString(sides.leftSidePoints)
|
||
});
|
||
|
||
map.addLayer({
|
||
id: `${prefix}-left`,
|
||
type: "line",
|
||
source: `${prefix}-left`,
|
||
paint: {
|
||
"line-color": "blue",
|
||
"line-width": 2
|
||
}
|
||
});
|
||
|
||
map.addSource(`${prefix}-right`, {
|
||
type: "geojson",
|
||
data: turf.lineString(sides.rightSidePoints)
|
||
});
|
||
|
||
map.addLayer({
|
||
id: `${prefix}-right`,
|
||
type: "line",
|
||
source: `${prefix}-right`,
|
||
paint: {
|
||
"line-color": "green",
|
||
"line-width": 2
|
||
}
|
||
});
|
||
}
|
||
|
||
function drawSmoothLineThroughPoints(map, points, lineId = "smooth-line") {
|
||
const smoothPoints = interpolatePointsCatmullRom(points, 20);
|
||
const line = turf.lineString(smoothPoints);
|
||
|
||
map.addSource(lineId, {
|
||
type: "geojson",
|
||
data: line
|
||
});
|
||
|
||
map.addLayer({
|
||
id: lineId,
|
||
type: "line",
|
||
source: lineId,
|
||
paint: {
|
||
"line-color": "red",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
|
||
// Boční linie
|
||
const sides = computeSidesWGS84(smoothPoints, 10000); // 10 km offset
|
||
drawSideLines(map, sides, lineId + "-sides");
|
||
|
||
// Šipka na konci
|
||
const lastPoint = smoothPoints[smoothPoints.length - 1];
|
||
const secondLastPoint = smoothPoints[smoothPoints.length - 2];
|
||
const bearing = turf.bearing(turf.point(secondLastPoint), turf.point(lastPoint));
|
||
|
||
const triangle = createIsoscelesTriangle(turf.point(lastPoint), 60000, 80000, bearing); // 20km základna, 30km výška
|
||
|
||
map.addSource(lineId + "-arrow", {
|
||
type: "geojson",
|
||
data: triangle
|
||
});
|
||
|
||
map.addLayer({
|
||
id: lineId + "-arrow",
|
||
type: "fill",
|
||
source: lineId + "-arrow",
|
||
paint: {
|
||
"fill-color": "#ff0000",
|
||
"fill-opacity": 0.7
|
||
}
|
||
});
|
||
}
|
||
|
||
map.on('load', () => {
|
||
|
||
const points = [
|
||
[14.42076, 50.08804], // Praha
|
||
[15.0, 50.0],
|
||
[16.3725, 48.2082], // Vídeň
|
||
[17.0, 49.0],
|
||
[13.4050, 52.52] // Berlín
|
||
];
|
||
|
||
|
||
|
||
|
||
function createIsoscelesTriangle(center, baseLengthMeters, heightMeters, bearing = 0) {
|
||
const halfBase = baseLengthMeters / 2;
|
||
|
||
const leftBase = turf.destination(center, halfBase, bearing - 90, { units: 'meters' });
|
||
const rightBase = turf.destination(center, halfBase, bearing + 90, { units: 'meters' });
|
||
const apex = turf.destination(center, heightMeters, bearing, { units: 'meters' });
|
||
|
||
return turf.polygon([[
|
||
leftBase.geometry.coordinates,
|
||
rightBase.geometry.coordinates,
|
||
apex.geometry.coordinates,
|
||
leftBase.geometry.coordinates
|
||
]]);
|
||
}
|
||
|
||
|
||
|
||
|
||
|
||
const center = turf.point([52.95, 69.95]); // výchozí střed základny
|
||
|
||
// Vytvoř polygon trojúhelníku
|
||
const triangle = createIsoscelesTriangle(center, 40000, 100000, 10); // 2 km základna, 1 km výška, směr 0° (na sever)
|
||
|
||
map.addSource("triangle", {
|
||
type: "geojson",
|
||
data: triangle
|
||
});
|
||
|
||
map.addLayer({
|
||
id: "triangle",
|
||
type: "fill",
|
||
source: "triangle",
|
||
paint: {
|
||
"fill-color": "purple",
|
||
"fill-opacity": 0.5
|
||
}
|
||
});
|
||
|
||
map.addLayer({
|
||
id: "triangle-outline",
|
||
type: "line",
|
||
source: "triangle",
|
||
paint: {
|
||
"line-color": "#000",
|
||
"line-width": 2
|
||
}
|
||
});
|
||
|
||
map.addSource("latLonGrid", {
|
||
type: "geojson",
|
||
data: latLonGrid
|
||
});
|
||
|
||
map.addLayer({
|
||
id: "latLonGrid",
|
||
type: "line",
|
||
source: "latLonGrid",
|
||
layout: {},
|
||
paint: {
|
||
"line-color": "#888",
|
||
"line-width": 1,
|
||
"line-opacity": 0.5
|
||
}
|
||
});
|
||
|
||
// Generuj GeoJSON pro kruh
|
||
const circleGeoJSON = getCirclePolygon([20, 80], 120, 20);
|
||
const circle = turf.circle([20, 80], 120000, { units: "meters", steps: 64 });
|
||
const rectangleGeoJSON = getRectanglePolygon([20, 80], 2200, 2200);
|
||
const fsdafds = toTurfPolygon(points);
|
||
const arrowBGeoJSON = toTurfPolygon(arrowPolygonB);
|
||
const arrowCGeoJSON = toTurfPolygon(arrowPolygonC);
|
||
const arrowAGeoJSON = toTurfPolygon(arrowPolygonA);
|
||
|
||
//console.log(JSON.stringify(arrowAGeoJSON, null, 2));
|
||
// Arrow
|
||
// Přidání GeoJSON jako zdroj
|
||
map.addSource("arrowPolygonA", {
|
||
type: "geojson",
|
||
data: arrowAGeoJSON
|
||
});
|
||
|
||
// Vrstva pro výplň polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonA",
|
||
type: "fill",
|
||
source: "arrowPolygonA",
|
||
layout: {},
|
||
paint: {
|
||
"fill-color": "pink",
|
||
"fill-opacity": 0.6
|
||
}
|
||
});
|
||
|
||
// Vrstva pro obrys polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonA-outline",
|
||
type: "line",
|
||
source: "arrowPolygonA",
|
||
paint: {
|
||
"line-color": "#000",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
|
||
// Arrow
|
||
// Přidání GeoJSON jako zdroj
|
||
map.addSource("arrowPolygonB", {
|
||
type: "geojson",
|
||
data: arrowBGeoJSON
|
||
});
|
||
|
||
// Vrstva pro výplň polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonB",
|
||
type: "fill",
|
||
source: "arrowPolygonB",
|
||
layout: {},
|
||
paint: {
|
||
"fill-color": "yellow",
|
||
"fill-opacity": 0.6
|
||
}
|
||
});
|
||
|
||
// Vrstva pro obrys polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonB-outline",
|
||
type: "line",
|
||
source: "arrowPolygonB",
|
||
paint: {
|
||
"line-color": "#000",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
|
||
// Arrow
|
||
// Přidání GeoJSON jako zdroj
|
||
map.addSource("arrowPolygonC", {
|
||
type: "geojson",
|
||
data: arrowCGeoJSON
|
||
});
|
||
|
||
// Vrstva pro výplň polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonC",
|
||
type: "fill",
|
||
source: "arrowPolygonC",
|
||
layout: {},
|
||
paint: {
|
||
"fill-color": "yellow",
|
||
"fill-opacity": 0.6
|
||
}
|
||
});
|
||
|
||
// Vrstva pro obrys polygonu
|
||
map.addLayer({
|
||
id: "arrowPolygonC-outline",
|
||
type: "line",
|
||
source: "arrowPolygonC",
|
||
paint: {
|
||
"line-color": "#000",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
|
||
// CIRCLE
|
||
// Přidání GeoJSON jako zdroj
|
||
map.addSource("circlePolygon", {
|
||
"type": "geojson",
|
||
"data": circleGeoJSON
|
||
});
|
||
|
||
// Přidání vrstvy pro vykreslení polygonu
|
||
map.addLayer({
|
||
"id": "circlePolygon",
|
||
"type": "fill",
|
||
"source": "circlePolygon",
|
||
"layout": {},
|
||
"paint": {
|
||
"fill-color": "blue",
|
||
"fill-opacity": 0.6
|
||
}
|
||
});
|
||
|
||
// Přidání outline pro polygon
|
||
map.addLayer({
|
||
"id": "circlePolygon-outline",
|
||
"type": "line",
|
||
"source": "circlePolygon",
|
||
"paint": {
|
||
"line-color": "#000",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
|
||
// RECTANGLE
|
||
map.addSource("rectanglePolygon", {
|
||
"type": "geojson",
|
||
"data": rectangleGeoJSON
|
||
});
|
||
|
||
// Přidání vrstvy pro vykreslení polygonu
|
||
map.addLayer({
|
||
"id": "rectanglePolygon",
|
||
"type": "fill",
|
||
"source": "rectanglePolygon",
|
||
"layout": {},
|
||
"paint": {
|
||
"fill-color": "red",
|
||
"fill-opacity": 0.6
|
||
}
|
||
});
|
||
|
||
// Přidání outline pro polygon
|
||
map.addLayer({
|
||
"id": "rectanglePolygon-outline",
|
||
"type": "line",
|
||
"source": "rectanglePolygon",
|
||
"paint": {
|
||
"line-color": "#000",
|
||
"line-width": 3
|
||
}
|
||
});
|
||
});
|
||
|
||
|
||
|
||
function generateLatLonGrid(step = 10) {
|
||
const features = [];
|
||
|
||
// Rovnoběžky (latitudes)
|
||
for (let lat = -80; lat <= 80; lat += step) {
|
||
features.push({
|
||
type: "Feature",
|
||
geometry: {
|
||
type: "LineString",
|
||
coordinates: Array.from({ length: 37 }, (_, i) => [-180 + i * 10, lat])
|
||
},
|
||
properties: {
|
||
type: "latitude",
|
||
value: lat
|
||
}
|
||
});
|
||
}
|
||
|
||
// Poledníky (longitudes)
|
||
for (let lon = -180; lon <= 180; lon += step) {
|
||
features.push({
|
||
type: "Feature",
|
||
geometry: {
|
||
type: "LineString",
|
||
coordinates: Array.from({ length: 17 }, (_, i) => [lon, -80 + i * 10])
|
||
},
|
||
properties: {
|
||
type: "longitude",
|
||
value: lon
|
||
}
|
||
});
|
||
}
|
||
|
||
return {
|
||
type: "FeatureCollection",
|
||
features
|
||
};
|
||
} |