mirror of
https://github.com/gpxstudio/gpx.studio.git
synced 2025-08-30 23:30:04 +00:00
highway, sac_scale and mtb:scale coloring
This commit is contained in:
@@ -25,40 +25,137 @@ export const surfaceColors: { [key: string]: string } = {
|
||||
"stone": "#ffd991",
|
||||
};
|
||||
|
||||
export function getSurfaceColor(surface: string): string {
|
||||
return surfaceColors[surface] ? surfaceColors[surface] : surfaceColors.missing;
|
||||
}
|
||||
|
||||
export const highwayColors: { [key: string]: string } = {
|
||||
"missing": "#d1d1d1",
|
||||
"residential": "#73b2ff",
|
||||
"service": "#b3b3cc",
|
||||
"track": "#946f43",
|
||||
"unclassified": "#e0e0e0",
|
||||
"footway": "#a3c989",
|
||||
"tertiary": "#ffdd7f",
|
||||
"path": "#a3c989",
|
||||
"secondary": "#ffd75f",
|
||||
"primary": "#ff6e5c",
|
||||
"cycleway": "#ffbb6e",
|
||||
"trunk": "#ff5e4d",
|
||||
"living_street": "#9de2ff",
|
||||
"motorway": "#ff4d33",
|
||||
"motorway_link": "#ff947f",
|
||||
"steps": "#8d91a2",
|
||||
"road": "#e0e0e0",
|
||||
"pedestrian": "#c1c8e4",
|
||||
"motorway_link": "#ff4d33",
|
||||
"trunk": "#ff5e4d",
|
||||
"trunk_link": "#ff947f",
|
||||
"primary_link": "#ff8d7b",
|
||||
"secondary_link": "#ffcb66",
|
||||
"tertiary_link": "#ffdd8b",
|
||||
"primary": "#ff6e5c",
|
||||
"primary_link": "#ff6e5c",
|
||||
"secondary": "#ff8d7b",
|
||||
"secondary_link": "#ff8d7b",
|
||||
"tertiary": "#ffd75f",
|
||||
"tertiary_link": "#ffd75f",
|
||||
"unclassified": "#f1f2a5",
|
||||
"road": "#f1f2a5",
|
||||
"residential": "#73b2ff",
|
||||
"living_street": "#73b2ff",
|
||||
"service": "#9c9cd9",
|
||||
"track": "#a8e381",
|
||||
"footway": "#a8e381",
|
||||
"path": "#a8e381",
|
||||
"pedestrian": "#a8e381",
|
||||
"cycleway": "#9de2ff",
|
||||
"construction": "#e09a4a",
|
||||
"bridleway": "#a3c989",
|
||||
"platform": "#c4c4c4",
|
||||
"proposed": "#e0e0e0",
|
||||
"bridleway": "#946f43",
|
||||
"raceway": "#ff0000",
|
||||
"rest_area": "#73b2ff",
|
||||
"abandoned": "#e0e0e0",
|
||||
"services": "#ffe066",
|
||||
"corridor": "#c4c4c4",
|
||||
"bus_stop": "#ffe6e6",
|
||||
"busway": "#ffe6e6",
|
||||
"elevator": "#c4c4c4",
|
||||
"via_ferrata": "#8d91a2"
|
||||
};
|
||||
"rest_area": "#9c9cd9",
|
||||
"services": "#9c9cd9",
|
||||
"corridor": "#474747",
|
||||
"elevator": "#474747",
|
||||
"steps": "#474747",
|
||||
"bus_stop": "#8545a3",
|
||||
"busway": "#8545a3",
|
||||
"via_ferrata": "#474747"
|
||||
};
|
||||
|
||||
export const sacScaleColors: { [key: string]: string } = {
|
||||
"hiking": "#007700",
|
||||
"mountain_hiking": "#1843ad",
|
||||
"demanding_mountain_hiking": "#ffff00",
|
||||
"alpine_hiking": "#ff9233",
|
||||
"demanding_alpine_hiking": "#ff0000",
|
||||
"difficult_alpine_hiking": "#000000",
|
||||
};
|
||||
|
||||
export const mtbScaleColors: { [key: string]: string } = {
|
||||
"0-": "#007700",
|
||||
"0": "#007700",
|
||||
"0+": "#007700",
|
||||
"1-": "#1843ad",
|
||||
"1": "#1843ad",
|
||||
"1+": "#1843ad",
|
||||
"2-": "#ffff00",
|
||||
"2": "#ffff00",
|
||||
"2+": "#ffff00",
|
||||
"3": "#ff0000",
|
||||
"4": "#00ff00",
|
||||
"5": "#000000",
|
||||
"6": "#b105eb",
|
||||
};
|
||||
|
||||
function createPattern(backgroundColor: string, sacScaleColor: string | undefined, mtbScaleColor: string | undefined, size: number = 16, lineWidth: number = 4) {
|
||||
let canvas = document.createElement('canvas');
|
||||
canvas.width = size;
|
||||
canvas.height = size;
|
||||
let ctx = canvas.getContext('2d');
|
||||
if (ctx) {
|
||||
ctx.fillStyle = backgroundColor;
|
||||
ctx.fillRect(0, 0, size, size);
|
||||
ctx.lineWidth = lineWidth;
|
||||
|
||||
const halfSize = size / 2;
|
||||
const halfLineWidth = lineWidth / 2;
|
||||
if (sacScaleColor) {
|
||||
ctx.strokeStyle = sacScaleColor;
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(halfSize - halfLineWidth, - halfLineWidth);
|
||||
ctx.lineTo(size + halfLineWidth, halfSize + halfLineWidth);
|
||||
ctx.stroke();
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(- halfLineWidth, halfSize - halfLineWidth);
|
||||
ctx.lineTo(halfSize + halfLineWidth, size + halfLineWidth);
|
||||
ctx.stroke();
|
||||
}
|
||||
if (mtbScaleColor) {
|
||||
ctx.strokeStyle = mtbScaleColor;
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(halfSize - halfLineWidth, size + halfLineWidth);
|
||||
ctx.lineTo(size + halfLineWidth, halfSize - halfLineWidth);
|
||||
ctx.stroke();
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(- halfLineWidth, halfSize + halfLineWidth);
|
||||
ctx.lineTo(halfSize + halfLineWidth, - halfLineWidth);
|
||||
ctx.stroke();
|
||||
}
|
||||
}
|
||||
return ctx?.createPattern(canvas, 'repeat') || backgroundColor;
|
||||
}
|
||||
|
||||
const patterns: Record<string, string | CanvasPattern> = {};
|
||||
export function getHighwayColor(highway: string, sacScale: string | undefined, mtbScale: string | undefined) {
|
||||
let backgroundColor = highwayColors[highway] ? highwayColors[highway] : highwayColors.missing;
|
||||
let sacScaleColor = sacScale ? sacScaleColors[sacScale] : undefined;
|
||||
let mtbScaleColor = mtbScale ? mtbScaleColors[mtbScale] : undefined;
|
||||
if (sacScale || mtbScale) {
|
||||
let patternId = `${backgroundColor}-${[sacScale, mtbScale].filter(x => x).join('-')}`;
|
||||
if (!patterns[patternId]) {
|
||||
patterns[patternId] = createPattern(backgroundColor, sacScaleColor, mtbScaleColor);
|
||||
}
|
||||
return patterns[patternId];
|
||||
}
|
||||
return backgroundColor;
|
||||
}
|
||||
|
||||
const maxSlope = 20;
|
||||
export function getSlopeColor(slope: number): string {
|
||||
if (slope > maxSlope) {
|
||||
slope = maxSlope;
|
||||
} else if (slope < -maxSlope) {
|
||||
slope = -maxSlope;
|
||||
}
|
||||
|
||||
let v = slope / maxSlope;
|
||||
v = 1 / (1 + Math.exp(-6 * v));
|
||||
v = v - 0.5;
|
||||
|
||||
let hue = ((0.5 - v) * 120).toString(10);
|
||||
let lightness = 90 - Math.abs(v) * 70;
|
||||
|
||||
return `hsl(${hue},70%,${lightness}%)`;
|
||||
}
|
@@ -19,7 +19,7 @@
|
||||
ChartNoAxesColumn,
|
||||
Construction
|
||||
} from 'lucide-svelte';
|
||||
import { surfaceColors, highwayColors } from '$lib/assets/colors';
|
||||
import { getSlopeColor, getSurfaceColor, getHighwayColor } from '$lib/assets/colors';
|
||||
import { _, locale } from 'svelte-i18n';
|
||||
import {
|
||||
getCadenceWithUnits,
|
||||
@@ -443,33 +443,20 @@
|
||||
chart.update();
|
||||
}
|
||||
|
||||
let maxSlope = 20;
|
||||
function slopeFillCallback(context) {
|
||||
let slope = context.p0.raw.slope.segment;
|
||||
if (slope > maxSlope) {
|
||||
slope = maxSlope;
|
||||
} else if (slope < -maxSlope) {
|
||||
slope = -maxSlope;
|
||||
}
|
||||
|
||||
let v = slope / maxSlope;
|
||||
v = 1 / (1 + Math.exp(-6 * v));
|
||||
v = v - 0.5;
|
||||
|
||||
let hue = ((0.5 - v) * 120).toString(10);
|
||||
let lightness = 90 - Math.abs(v) * 70;
|
||||
|
||||
return ['hsl(', hue, ',70%,', lightness, '%)'].join('');
|
||||
return getSlopeColor(context.p0.raw.slope.segment);
|
||||
}
|
||||
|
||||
function surfaceFillCallback(context) {
|
||||
let surface = context.p0.raw.extensions.surface;
|
||||
return surfaceColors[surface] ? surfaceColors[surface] : surfaceColors.missing;
|
||||
return getSurfaceColor(context.p0.raw.extensions.surface);
|
||||
}
|
||||
|
||||
function highwayFillCallback(context) {
|
||||
let highway = context.p0.raw.extensions.highway;
|
||||
return highwayColors[highway] ? highwayColors[highway] : highwayColors.missing;
|
||||
return getHighwayColor(
|
||||
context.p0.raw.extensions.highway,
|
||||
context.p0.raw.extensions.sac_scale,
|
||||
context.p0.raw.extensions['mtb:scale']
|
||||
);
|
||||
}
|
||||
|
||||
$: if (chart) {
|
||||
|
Reference in New Issue
Block a user