deck.gl предоставляет многослойную систему визуализации, где стилизация геометрии и цвета строится вокруг концепции слоёв (layers) и функций-аксессоров (accessors). Цвет и внешний вид объектов определяются не декларативными CSS-правилами, а вычисляются на уровне данных и WebGL-пайплайна, что обеспечивает высокую производительность при работе с большими наборами данных.
В большинстве слоёв используется RGBA-представление цвета:
[R, G, B, A]0–255 для RGB и 0–255
или 0–255 для alpha (в зависимости от слоя и версии)opacityПример базового цвета:
const color = [30, 144, 255, 200];
Цвет может задаваться:
Каждый слой имеет набор стандартных свойств, отвечающих за визуальное представление:
Определяет цвет заливки объектов.
new ScatterplotLayer({
id: 'points',
data,
getPosition: d => d.coordinates,
getFillColor: [255, 0, 0, 180]
});
Используется для линий и контуров.
new PathLayer({
id: 'paths',
data,
getPath: d => d.path,
getLineColor: [0, 255, 0, 200],
getWidth: 2
});
В некоторых слоях (например, ColumnLayer,
HexagonLayer) используется единый accessor:
new ColumnLayer({
id: 'columns',
data,
getPosition: d => d.position,
getElevation: d => d.value,
getFillColor: d => d.value > 100 ? [255, 0, 0] : [0, 0, 255]
});
Ключевая особенность deck.gl — возможность вычислять цвет на основе данных.
getFillColor: d => [
Math.min(255, d.value * 2),
100,
255 - d.value,
180
]
Такой подход позволяет:
const categoryColor = {
A: [255, 99, 132, 200],
B: [54, 162, 235, 200],
C: [255, 206, 86, 200]
};
getFillColor: d => categoryColor[d.type] || [200, 200, 200, 200]
Цвет часто используется как визуальный код состояния данных.
getFillColor: d => {
if (d.status === 'active') return [0, 200, 0, 180];
if (d.status === 'warning') return [255, 165, 0, 180];
return [200, 0, 0, 180];
}
Такой подход применяется в:
При работе с числовыми данными часто используется нормализация.
const lerpColor = (t) => [
255 * t,
100,
255 * (1 - t),
200
];
getFillColor: d => lerpColor(d.value / maxValue)
Более сложные варианты включают:
Альфа-канал определяет прозрачность и влияет на наложение объектов.
getFillColor: [0, 128, 255, 120]
Важно учитывать:
Некоторые слои используют additive blending для эффектов свечения.
Для линий и границ используется отдельная логика стилизации:
new GeoJsonLayer({
id: 'geojson',
data,
stroked: true,
filled: true,
getFillColor: [100, 150, 255, 100],
getLineColor: [0, 0, 0, 255],
getLineWidth: 2
});
Параметры:
stroked — включение обводкиgetLineWidth — толщина линииgetLineColor — цвет контураНекоторые слои поддерживают физически корректное освещение.
new ColumnLayer({
id: 'columns',
data,
material: {
ambient: 0.35,
diffuse: 0.6,
shininess: 32
}
});
Параметры материала:
Эта модель особенно важна для 3D-слоёв (ColumnLayer,
GridLayer, TerrainLayer).
Для максимального контроля используется переопределение шейдеров:
new ScatterplotLayer({
id: 'custom',
data,
getFillColor: d => d.color,
vs: `
attribute vec3 positions;
attribute vec4 colors;
varying vec4 vColor;
void main() {
vColor = colors;
gl_Position = project_position_to_clipspace(positions);
}
`,
fs: `
varying vec4 vColor;
void main() {
gl_FragColor = vColor;
}
`
});
На этом уровне можно реализовать:
const palette = {
primary: [0, 120, 255, 200],
danger: [255, 60, 60, 200],
neutral: [180, 180, 180, 200]
};
const getThemeColor = (theme, value) => {
return theme === 'dark'
? [255 - value, 255 - value, 255, 200]
: [value, 100, 255, 200];
};
При динамических цветах важно контролировать пересчёт атрибутов:
new ScatterplotLayer({
id: 'optimized',
data,
getFillColor: d => colorScale(d.value),
updateTriggers: {
getFillColor: [colorScale]
}
});
Это предотвращает лишние перерасчёты GPU-буферов и повышает производительность.
Визуализация часто требует согласованных палитр:
Пример последовательной шкалы:
const sequential = [
[237, 248, 251, 255],
[179, 205, 227, 255],
[140, 150, 198, 255],
[136, 65, 157, 255]
];
Применение:
getFillColor: d => sequential[Math.floor(d.value * 3)]
В сложных сценах стиль распределяется между слоями:
const layers = [
new ScatterplotLayer({
id: 'points',
getFillColor: [255, 0, 0, 180]
}),
new PathLayer({
id: 'lines',
getLineColor: [0, 0, 0, 255]
})
];
Так формируется многослойная визуальная композиция, где каждый слой отвечает за свой визуальный канал: цвет, глубину, прозрачность и структуру данных.