Skip to content
This repository has been archived by the owner on Aug 8, 2023. It is now read-only.

Reimplement style values atop NSExpression #10726

Merged
merged 28 commits into from
Jan 24, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
7baade3
[core] Added accessors for various expression parameters
1ec5 Dec 17, 2017
f6b91fb
[ios, macos] Import headers, not implementation files
1ec5 Dec 14, 2017
68e893f
[ios, macos] Silenced warning in test of error condition
1ec5 Dec 21, 2017
0d8a811
[ios, macos] Made MGLSphericalPosition boxable
1ec5 Jan 20, 2018
354b521
[ios, macos] Implemented array enumeration during conversion
1ec5 Dec 21, 2017
bdb8452
[ios, macos] Temporarily ignore heatmap layer type
1ec5 Dec 20, 2017
9eb5d6d
[ios, macos] Migrated MGLSymbolStyleLayer.text to NSExpression
1ec5 Dec 13, 2017
8966dcf
[ios, macos] Implemented string coercion
1ec5 Dec 14, 2017
7e13882
[ios, macos] Color literals
1ec5 Dec 14, 2017
ee2d452
[ios, macos] Convert colors, offsets, padding in expressions to JSON …
1ec5 Dec 21, 2017
2f08c70
[ios, macos] Null constant expressions
1ec5 Dec 15, 2017
87728b4
[ios, macos] Convert dictionary literals
1ec5 Dec 15, 2017
3fcd6be
[ios, macos] Interpolation expressions
1ec5 Dec 15, 2017
3f04220
[ios, macos] to-boolean, to-number, get from object
1ec5 Dec 16, 2017
12b1227
[ios, macos] Variable expressions
1ec5 Dec 17, 2017
40398f3
[ios, macos] Expression-based style property getters
1ec5 Dec 17, 2017
7ea0d6e
[ios, macos] Consolidated property value–expression conversion in MGL…
1ec5 Dec 18, 2017
984addb
[ios, macos] Predicate and expression guide
1ec5 Dec 18, 2017
febdb30
[ios, macos] Updated style authoring guide
1ec5 Dec 18, 2017
10708fa
[ios, macos] Migrated codegen templates to expressions
1ec5 Dec 18, 2017
fdfc869
[ios, macos] Applied expression changes via codegen
1ec5 Dec 18, 2017
9c66dd7
[ios, macos] Updated changelogs
1ec5 Dec 21, 2017
29fd6d2
[ios, macos] Eviscerated style function tests
1ec5 Dec 21, 2017
3b6745a
[ios, macos] Updated style function guide
1ec5 Dec 21, 2017
33cd2fd
[macos] Migrated macosapp to expressions
1ec5 Dec 20, 2017
bd53c84
[ios] Migrated iosapp to expressions
1ec5 Dec 21, 2017
9e79949
[ios, macos] Exposed JSON conversion methods publicly
1ec5 Jan 17, 2018
18d50f1
[ios, macos] Removed MGLStyleValue, MGLStyleFunction
1ec5 Jan 20, 2018
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions include/mbgl/style/expression/interpolate.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -70,13 +70,20 @@ class InterpolateBase : public Expression {
{}

const std::unique_ptr<Expression>& getInput() const { return input; }
const Interpolator& getInterpolator() const { return interpolator; }

void eachChild(const std::function<void(const Expression&)>& visit) const override {
visit(*input);
for (const auto& stop : stops) {
visit(*stop.second);
}
}

void eachStop(const std::function<void(double, const Expression&)>& visit) const {
for (const auto& stop : stops) {
visit(stop.first, *stop.second);
}
}

// Return the smallest range of stops that covers the interval [lower, upper]
Range<float> getCoveringStops(const double lower, const double upper) const {
Expand Down
1 change: 1 addition & 0 deletions include/mbgl/style/expression/step.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ class Step : public Expression {

EvaluationResult evaluate(const EvaluationContext& params) const override;
void eachChild(const std::function<void(const Expression&)>& visit) const override;
void eachStop(const std::function<void(double, const Expression&)>& visit) const;

const std::unique_ptr<Expression>& getInput() const { return input; }
Range<float> getCoveringStops(const double lower, const double upper) const;
Expand Down
4 changes: 3 additions & 1 deletion include/mbgl/style/function/camera_function.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,9 @@ class CameraFunction {
}

bool useIntegerZoom = false;


const expression::Expression& getExpression() const { return *expression; }

// retained for compatibility with pre-expression function API
Stops stops;

Expand Down
2 changes: 2 additions & 0 deletions include/mbgl/style/function/composite_function.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,8 @@ class CompositeFunction {
return *lhs.expression == *rhs.expression;
}

const expression::Expression& getExpression() const { return *expression; }

std::string property;
Stops stops;
optional<T> defaultValue;
Expand Down
2 changes: 2 additions & 0 deletions include/mbgl/style/function/source_function.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,8 @@ class SourceFunction {

bool useIntegerZoom = false;

const expression::Expression& getExpression() const { return *expression; }

// retained for compatibility with pre-expression function API
std::string property;
Stops stops;
Expand Down
11 changes: 11 additions & 0 deletions include/mbgl/util/unitbezier.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,17 @@ struct UnitBezier {
, ay(1.0 - (3.0 * p1y) - (3.0 * (p2y - p1y) - (3.0 * p1y))) {
}

std::pair<double, double> getP1() const {
return { cx / 3.0, cy / 3.0 };
}

std::pair<double, double> getP2() const {
return {
(bx + (3.0 * cx / 3.0) + cx) / 3.0,
(by + (3.0 * cy / 3.0) + cy) / 3.0,
};
}

double sampleCurveX(double t) const {
// `ax t^3 + bx t^2 + cx t' expanded using Horner's rule.
return ((ax * t + bx) * t + cx) * t;
Expand Down
127 changes: 85 additions & 42 deletions platform/darwin/docs/guides/For Style Authors.md.ejs
Original file line number Diff line number Diff line change
Expand Up @@ -263,12 +263,16 @@ In style JSON | In Objective-C | In Swift
## Setting attribute values

Each property representing a layout or paint attribute is set to an
`MGLStyleValue` object, which is either an `MGLConstantStyleValue` object (for
constant values) or an `MGLStyleFunction` object (for style functions). The
style value object is a container for the raw value or function parameters that
you want the attribute to be set to.
`NSExpression` object. `NSExpression` objects play the same role as
[expressions in the Mapbox Style Specification](https://www.mapbox.com/mapbox-gl-js/style-spec/#expressions),
but you create the former using a very different syntax. `NSExpression`’s format
string syntax is reminiscent of a spreadsheet formula or an expression in a
database query. See the
“[Predicates and Expressions](Predicates and Expressions.md)” guide for an
overview of the expression support in this SDK. This SDK no longer supports
style functions; use expressions instead.

### Constant style values
### Constant values in expressions

In contrast to the JSON type that the style specification defines for each
layout or paint property, the style value object often contains a more specific
Expand All @@ -279,10 +283,10 @@ or set.
In style JSON | In Objective-C | In Swift
--------------|-----------------------|---------
Color | `<%- cocoaPrefix %>Color` | `<%- cocoaPrefix %>Color`
Enum | `NSValue` (see `NSValue(MGLAdditions)`) | `NSValue` (see `NSValue(MGLAdditions)`)
Enum | `NSString` | `String`
String | `NSString` | `String`
Boolean | `NSNumber.boolValue` | `Bool`
Number | `NSNumber.floatValue` | `Float`
Boolean | `NSNumber.boolValue` | `NSNumber.boolValue`
Number | `NSNumber.floatValue` | `NSNumber.floatValue`
Array (`-dasharray`) | `NSArray<NSNumber>` | `[Float]`
Array (`-font`) | `NSArray<NSString>` | `[String]`
<% if (iOS) { -%>
Expand Down Expand Up @@ -312,38 +316,77 @@ translation downward. This is the reverse of how `CGVector` is interpreted on
iOS.

<% } -%>
### Style functions

A _style function_ allows you to vary the value of a layout or paint attribute
based on the zoom level, data provided by content sources, or both. For more
information about style functions, see “[Using Style Functions at Runtime](using-style-functions-at-runtime.html)”.

Each kind of style function is represented by a distinct class, but you
typically create style functions as you create any other style value, using
class methods on `MGLStyleValue`:

In style specification | SDK class | SDK factory method
---------------------------|-----------------------------|-------------------
zoom function | `MGLCameraStyleFunction` | `+[MGLStyleValue valueWithInterpolationMode:cameraStops:options:]`
property function | `MGLSourceStyleFunction` | `+[MGLStyleValue valueWithInterpolationMode:sourceStops:attributeName:options:]`
zoom-and-property function | `MGLCompositeStyleFunction` | `+[MGLStyleValue valueWithInterpolationMode:compositeStops:attributeName:options:]`

The documentation for each individual style layer property indicates the kinds
of style functions that are enabled for that property.

When you create a style function, you specify an _interpolation mode_ and a
series of _stops_. Each stop determines the effective value displayed at a
particular zoom level (for camera functions) or the effective value on features
with a particular attribute value in the content source (for source functions).
The interpolation mode tells the SDK how to calculate the effective value
between any two stops:

In style specification | In the SDK
-----------------------------|-----------
`exponential` | `MGLInterpolationModeExponential`
`interval` | `MGLInterpolationModeInterval`
`categorical` | `MGLInterpolationModeCategorical`
`identity` | `MGLInterpolationModeIdentity`
### Expression operators

In style specification | Method, function, or predicate type | Format string syntax
-----------------------|-------------------------------------|---------------------
`array` | |
`boolean` | |
`literal` | `+[NSExpression expressionForConstantValue:]` | `%@` representing `NSArray` or `NSDictionary`
`number` | |
`string` | |
`to-boolean` | `boolValue` |
`to-color` | |
`to-number` | `mgl_numberWithFallbackValues:` |
`to-string` | `stringValue` |
`typeof` | |
`geometry-type` | |
`id` | |
`properties` | |
`at` | |
`get` | `+[NSExpression expressionForKeyPath:]` | Key path
`has` | |
`length` | `count:` | `count({1, 2, 2, 3, 4, 7, 9})`
`!` | `NSNotPredicateType` | `NOT (p0 OR … OR pn)`
`!=` | `NSNotEqualToPredicateOperatorType` | `key != value`
`<` | `NSLessThanPredicateOperatorType` | `key < value`
`<=` | `NSLessThanOrEqualToPredicateOperatorType` | `key <= value`
`==` | `NSEqualToPredicateOperatorType` | `key == value`
`>` | `NSGreaterThanPredicateOperatorType` | `key > value`
`>=` | `NSGreaterThanOrEqualToPredicateOperatorType` | `key >= value`
`all` | `NSAndPredicateType` | `p0 AND … AND pn`
`any` | `NSOrPredicateType` | `p0 OR … OR pn`
`case` | `+[NSExpression expressionForConditional:trueExpression:falseExpression:]` | `TERNARY(condition, trueExpression, falseExpression)`
`coalesce` | |
`match` | |
`interpolate` | `mgl_interpolateWithCurveType:parameters:stops:` |
`step` | `mgl_stepWithMinimum:stops:` |
`let` | `mgl_expressionWithContext:` |
`var` | `+[NSExpression expressionForVariable:]` | `$variable`
`concat` | `stringByAppendingString:` |
`downcase` | `lowercase:` | `lowercase('DOWNTOWN')`
`upcase` | `uppercase:` | `uppercase('Elysian Fields')`
<% if (macOS) { -%>
`rgb` | `+[NSColor colorWithCalibratedRed:green:blue:alpha:]` |
`rgba` | `+[NSColor colorWithCalibratedRed:green:blue:alpha:]` |
<% } else { %>
`rgb` | `+[UIColor colorWithRed:green:blue:alpha:]` |
`rgba` | `+[UIColor colorWithRed:green:blue:alpha:]` |
<% } -%>
`to-rgba` | |
`-` | `from:subtract:` | `2 - 1`
`*` | `multiply:by:` | `1 * 2`
`/` | `divide:by:` | `1 / 2`
`%` | `modulus:by:` |
`^` | `raise:toPower:` | `2 ** 2`
`+` | `add:to:` | `1 + 2`
`acos` | |
`asin` | |
`atan` | |
`cos` | |
`e` | | `%@` representing `NSNumber` containing `M_E`
`ln` | `ln:` | `ln(2)`
`ln2` | | `%@` representing `NSNumber` containing `M_LN2`
`log10` | `log:` | `log(1)`
`log2` | |
`max` | `max:` | `max({1, 2, 2, 3, 4, 7, 9})`
`min` | `min:` | `min({1, 2, 2, 3, 4, 7, 9})`
`pi` | | `%@` representing `NSNumber` containing `M_PI`
`sin` | |
`sqrt` | `sqrt:` | `sqrt(2)`
`tan` | |
`zoom` | | `$zoom`
`heatmap-density` | | `$heatmapDensity`

## Filtering sources

Expand All @@ -368,5 +411,5 @@ In style JSON | In the format string
`["any", f0, …, fn]` | `p0 OR … OR pn`
`["none", f0, …, fn]` | `NOT (p0 OR … OR pn)`

See the `MGLVectorStyleLayer.predicate` documentation for a full description of
the supported operators and operand types.
See the “[Predicates and Expressions](Predicates and Expressions.md)” guide for
a full description of the supported operators and operand types.
Loading