summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChris Loer <chris.loer@gmail.com>2017-07-11 11:22:39 -0700
committerChris Loer <chris.loer@mapbox.com>2017-07-12 14:14:09 -0700
commite8657becc56c2aee5b070357092da028e752d461 (patch)
tree21a877d6adacfc468b4d2c0223bffec49ea3f5dc /src
parentaf10e2d3be5f24c1887622c63332a3cf67bc19d5 (diff)
downloadqtlocation-mapboxgl-e8657becc56c2aee5b070357092da028e752d461.tar.gz
[core] Update shaders.
Implements 'icon-pitch-alignment' (issue #9345) Fixes issue #9456 (map-aligned point label regression)
Diffstat (limited to 'src')
-rw-r--r--src/mbgl/layout/symbol_layout.cpp5
-rw-r--r--src/mbgl/programs/symbol_program.cpp7
-rw-r--r--src/mbgl/programs/symbol_program.hpp10
-rw-r--r--src/mbgl/renderer/layers/render_symbol_layer.cpp2
-rw-r--r--src/mbgl/shaders/symbol_icon.cpp17
-rw-r--r--src/mbgl/shaders/symbol_sdf.cpp19
-rw-r--r--src/mbgl/style/layers/symbol_layer.cpp16
-rw-r--r--src/mbgl/style/layers/symbol_layer_properties.hpp6
8 files changed, 75 insertions, 7 deletions
diff --git a/src/mbgl/layout/symbol_layout.cpp b/src/mbgl/layout/symbol_layout.cpp
index e308da618f..956ba770dd 100644
--- a/src/mbgl/layout/symbol_layout.cpp
+++ b/src/mbgl/layout/symbol_layout.cpp
@@ -75,10 +75,13 @@ SymbolLayout::SymbolLayout(const BucketParameters& parameters,
}
}
- // If unspecified `text-pitch-alignment` inherits `text-rotation-alignment`
+ // If unspecified `*-pitch-alignment` inherits `*-rotation-alignment`
if (layout.get<TextPitchAlignment>() == AlignmentType::Auto) {
layout.get<TextPitchAlignment>() = layout.get<TextRotationAlignment>();
}
+ if (layout.get<IconPitchAlignment>() == AlignmentType::Auto) {
+ layout.get<IconPitchAlignment>() = layout.get<IconRotationAlignment>();
+ }
const bool hasText = has<TextField>(layout) && !layout.get<TextFont>().empty();
const bool hasIcon = has<IconImage>(layout);
diff --git a/src/mbgl/programs/symbol_program.cpp b/src/mbgl/programs/symbol_program.cpp
index 8790adcc63..58174ff8a7 100644
--- a/src/mbgl/programs/symbol_program.cpp
+++ b/src/mbgl/programs/symbol_program.cpp
@@ -52,6 +52,11 @@ Values makeValues(const bool isText,
const float pixelsToTileUnits = tile.id.pixelsToTileUnits(1.0, state.getZoom());
const bool pitchWithMap = values.pitchAlignment == style::AlignmentType::Map;
const bool rotateWithMap = values.rotationAlignment == style::AlignmentType::Map;
+
+ // Line label rotation happens in `updateLineLabels`
+ // Pitched point labels are automatically rotated by the labelPlaneMatrix projection
+ // Unpitched point labels need to have their rotation applied after projection
+ const bool rotateInShader = rotateWithMap && !pitchWithMap && !alongLine;
mat4 labelPlaneMatrix;
if (alongLine) {
@@ -84,6 +89,8 @@ Values makeValues(const bool isText,
uniforms::u_pitch::Value{ state.getPitch() },
uniforms::u_pitch_with_map::Value{ pitchWithMap },
uniforms::u_max_camera_distance::Value{ values.maxCameraDistance },
+ uniforms::u_rotate_symbol::Value{ rotateInShader },
+ uniforms::u_aspect_ratio::Value{ state.getSize().aspectRatio() },
std::forward<Args>(args)...
};
}
diff --git a/src/mbgl/programs/symbol_program.hpp b/src/mbgl/programs/symbol_program.hpp
index 79a961ad21..c74837b121 100644
--- a/src/mbgl/programs/symbol_program.hpp
+++ b/src/mbgl/programs/symbol_program.hpp
@@ -41,6 +41,8 @@ MBGL_DEFINE_UNIFORM_SCALAR(bool, u_is_size_feature_constant);
MBGL_DEFINE_UNIFORM_SCALAR(float, u_size_t);
MBGL_DEFINE_UNIFORM_SCALAR(float, u_size);
MBGL_DEFINE_UNIFORM_SCALAR(float, u_max_camera_distance);
+MBGL_DEFINE_UNIFORM_SCALAR(bool, u_rotate_symbol);
+MBGL_DEFINE_UNIFORM_SCALAR(float, u_aspect_ratio);
} // namespace uniforms
struct SymbolLayoutAttributes : gl::Attributes<
@@ -348,7 +350,9 @@ class SymbolIconProgram : public SymbolProgram<
uniforms::u_camera_to_center_distance,
uniforms::u_pitch,
uniforms::u_pitch_with_map,
- uniforms::u_max_camera_distance>,
+ uniforms::u_max_camera_distance,
+ uniforms::u_rotate_symbol,
+ uniforms::u_aspect_ratio>,
style::IconPaintProperties>
{
public:
@@ -387,6 +391,8 @@ class SymbolSDFProgram : public SymbolProgram<
uniforms::u_pitch,
uniforms::u_pitch_with_map,
uniforms::u_max_camera_distance,
+ uniforms::u_rotate_symbol,
+ uniforms::u_aspect_ratio,
uniforms::u_gamma_scale,
uniforms::u_is_halo>,
PaintProperties>
@@ -409,6 +415,8 @@ public:
uniforms::u_pitch,
uniforms::u_pitch_with_map,
uniforms::u_max_camera_distance,
+ uniforms::u_rotate_symbol,
+ uniforms::u_aspect_ratio,
uniforms::u_gamma_scale,
uniforms::u_is_halo>,
PaintProperties>;
diff --git a/src/mbgl/renderer/layers/render_symbol_layer.cpp b/src/mbgl/renderer/layers/render_symbol_layer.cpp
index 2fe6dd971e..2af7b2f7ca 100644
--- a/src/mbgl/renderer/layers/render_symbol_layer.cpp
+++ b/src/mbgl/renderer/layers/render_symbol_layer.cpp
@@ -82,7 +82,7 @@ style::TextPaintProperties::PossiblyEvaluated RenderSymbolLayer::textPaintProper
style::SymbolPropertyValues RenderSymbolLayer::iconPropertyValues(const style::SymbolLayoutProperties::PossiblyEvaluated& layout_) const {
return style::SymbolPropertyValues {
- layout_.get<style::IconRotationAlignment>(), // icon-pitch-alignment is not yet implemented; inherit the rotation alignment
+ layout_.get<style::IconPitchAlignment>(),
layout_.get<style::IconRotationAlignment>(),
layout_.get<style::IconKeepUpright>(),
evaluated.get<style::IconTranslate>(),
diff --git a/src/mbgl/shaders/symbol_icon.cpp b/src/mbgl/shaders/symbol_icon.cpp
index cb00cdad05..c0e3a0ac01 100644
--- a/src/mbgl/shaders/symbol_icon.cpp
+++ b/src/mbgl/shaders/symbol_icon.cpp
@@ -19,6 +19,8 @@ uniform highp float u_size_t; // used to interpolate between zoom stops when siz
uniform highp float u_size; // used when size is both zoom and feature constant
uniform highp float u_camera_to_center_distance;
uniform highp float u_pitch;
+uniform bool u_rotate_symbol;
+uniform highp float u_aspect_ratio;
uniform highp float u_collision_y_stretch;
@@ -83,8 +85,19 @@ void main() {
float fontScale = u_is_text ? size / 24.0 : size;
- highp float angle_sin = sin(segment_angle);
- highp float angle_cos = cos(segment_angle);
+ highp float symbol_rotation = 0.0;
+ if (u_rotate_symbol) {
+ // See comments in symbol_sdf.vertex
+ vec4 offsetProjectedPoint = u_matrix * vec4(a_pos + vec2(1, 0), 0, 1);
+
+ vec2 a = projectedPoint.xy / projectedPoint.w;
+ vec2 b = offsetProjectedPoint.xy / offsetProjectedPoint.w;
+
+ symbol_rotation = atan((b.y - a.y) / u_aspect_ratio, b.x - a.x);
+ }
+
+ highp float angle_sin = sin(segment_angle + symbol_rotation);
+ highp float angle_cos = cos(segment_angle + symbol_rotation);
mat2 rotation_matrix = mat2(angle_cos, -1.0 * angle_sin, angle_sin, angle_cos);
vec4 projected_pos = u_label_plane_matrix * vec4(a_projected_pos.xy, 0.0, 1.0);
diff --git a/src/mbgl/shaders/symbol_sdf.cpp b/src/mbgl/shaders/symbol_sdf.cpp
index b4158bacc5..2050886957 100644
--- a/src/mbgl/shaders/symbol_sdf.cpp
+++ b/src/mbgl/shaders/symbol_sdf.cpp
@@ -73,6 +73,8 @@ uniform mat4 u_gl_coord_matrix;
uniform bool u_is_text;
uniform bool u_pitch_with_map;
uniform highp float u_pitch;
+uniform bool u_rotate_symbol;
+uniform highp float u_aspect_ratio;
uniform highp float u_camera_to_center_distance;
uniform highp float u_collision_y_stretch;
@@ -151,8 +153,21 @@ void main() {
float fontScale = u_is_text ? size / 24.0 : size;
- highp float angle_sin = sin(segment_angle);
- highp float angle_cos = cos(segment_angle);
+ highp float symbol_rotation = 0.0;
+ if (u_rotate_symbol) {
+ // Point labels with 'rotation-alignment: map' are horizontal with respect to tile units
+ // To figure out that angle in projected space, we draw a short horizontal line in tile
+ // space, project it, and measure its angle in projected space.
+ vec4 offsetProjectedPoint = u_matrix * vec4(a_pos + vec2(1, 0), 0, 1);
+
+ vec2 a = projectedPoint.xy / projectedPoint.w;
+ vec2 b = offsetProjectedPoint.xy / offsetProjectedPoint.w;
+
+ symbol_rotation = atan((b.y - a.y) / u_aspect_ratio, b.x - a.x);
+ }
+
+ highp float angle_sin = sin(segment_angle + symbol_rotation);
+ highp float angle_cos = cos(segment_angle + symbol_rotation);
mat2 rotation_matrix = mat2(angle_cos, -1.0 * angle_sin, angle_sin, angle_cos);
vec4 projected_pos = u_label_plane_matrix * vec4(a_projected_pos.xy, 0.0, 1.0);
diff --git a/src/mbgl/style/layers/symbol_layer.cpp b/src/mbgl/style/layers/symbol_layer.cpp
index 182b4b0a48..c102c64a94 100644
--- a/src/mbgl/style/layers/symbol_layer.cpp
+++ b/src/mbgl/style/layers/symbol_layer.cpp
@@ -332,6 +332,22 @@ void SymbolLayer::setIconOffset(DataDrivenPropertyValue<std::array<float, 2>> va
baseImpl = std::move(impl_);
observer->onLayerChanged(*this);
}
+PropertyValue<AlignmentType> SymbolLayer::getDefaultIconPitchAlignment() {
+ return IconPitchAlignment::defaultValue();
+}
+
+PropertyValue<AlignmentType> SymbolLayer::getIconPitchAlignment() const {
+ return impl().layout.get<IconPitchAlignment>();
+}
+
+void SymbolLayer::setIconPitchAlignment(PropertyValue<AlignmentType> value) {
+ if (value == getIconPitchAlignment())
+ return;
+ auto impl_ = mutableImpl();
+ impl_->layout.get<IconPitchAlignment>() = value;
+ baseImpl = std::move(impl_);
+ observer->onLayerChanged(*this);
+}
PropertyValue<AlignmentType> SymbolLayer::getDefaultTextPitchAlignment() {
return TextPitchAlignment::defaultValue();
}
diff --git a/src/mbgl/style/layers/symbol_layer_properties.hpp b/src/mbgl/style/layers/symbol_layer_properties.hpp
index f7ceaecdaa..4b2bff01b8 100644
--- a/src/mbgl/style/layers/symbol_layer_properties.hpp
+++ b/src/mbgl/style/layers/symbol_layer_properties.hpp
@@ -87,6 +87,11 @@ struct IconOffset : DataDrivenLayoutProperty<std::array<float, 2>> {
static std::array<float, 2> defaultValue() { return {{ 0, 0 }}; }
};
+struct IconPitchAlignment : LayoutProperty<AlignmentType> {
+ static constexpr const char * key = "icon-pitch-alignment";
+ static AlignmentType defaultValue() { return AlignmentType::Auto; }
+};
+
struct TextPitchAlignment : LayoutProperty<AlignmentType> {
static constexpr const char * key = "text-pitch-alignment";
static AlignmentType defaultValue() { return AlignmentType::Auto; }
@@ -254,6 +259,7 @@ class SymbolLayoutProperties : public Properties<
IconPadding,
IconKeepUpright,
IconOffset,
+ IconPitchAlignment,
TextPitchAlignment,
TextRotationAlignment,
TextField,