[all] Rationalize style::Image
A style has a collection of images, just as it has collections of sources and layers. * Name things appropriately * Use std::unique_ptr
This commit is contained in:
@@ -6,7 +6,7 @@
|
||||
#include <mbgl/gl/headless_backend.hpp>
|
||||
#include <mbgl/gl/offscreen_view.hpp>
|
||||
#include <mbgl/util/default_thread_pool.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/storage/default_file_source.hpp>
|
||||
#include <mbgl/storage/network_status.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
@@ -25,10 +25,8 @@ public:
|
||||
|
||||
map.setStyleJSON(util::read_file("benchmark/fixtures/api/query_style.json"));
|
||||
map.setLatLngZoom({ 40.726989, -73.992857 }, 15); // Manhattan
|
||||
|
||||
auto decoded = decodeImage(util::read_file("benchmark/fixtures/api/default_marker.png"));
|
||||
auto image = std::make_unique<SpriteImage>(std::move(decoded), 1.0);
|
||||
map.addImage("test-icon", std::move(image));
|
||||
map.addImage("test-icon", std::make_unique<style::Image>(
|
||||
decodeImage(util::read_file("benchmark/fixtures/api/default_marker.png")), 1.0));
|
||||
|
||||
mbgl::benchmark::render(map, view);
|
||||
}
|
||||
|
||||
@@ -217,13 +217,11 @@ set(MBGL_CORE_FILES
|
||||
src/mbgl/shaders/symbol_sdf.hpp
|
||||
|
||||
# sprite
|
||||
include/mbgl/sprite/sprite_image.hpp
|
||||
src/mbgl/sprite/sprite_atlas.cpp
|
||||
src/mbgl/sprite/sprite_atlas.hpp
|
||||
src/mbgl/sprite/sprite_atlas_observer.hpp
|
||||
src/mbgl/sprite/sprite_atlas_worker.cpp
|
||||
src/mbgl/sprite/sprite_atlas_worker.hpp
|
||||
src/mbgl/sprite/sprite_image.cpp
|
||||
src/mbgl/sprite/sprite_parser.cpp
|
||||
src/mbgl/sprite/sprite_parser.hpp
|
||||
|
||||
@@ -247,6 +245,7 @@ set(MBGL_CORE_FILES
|
||||
include/mbgl/style/data_driven_property_value.hpp
|
||||
include/mbgl/style/filter.hpp
|
||||
include/mbgl/style/filter_evaluator.hpp
|
||||
include/mbgl/style/image.hpp
|
||||
include/mbgl/style/layer.hpp
|
||||
include/mbgl/style/property_value.hpp
|
||||
include/mbgl/style/query.hpp
|
||||
@@ -264,6 +263,7 @@ set(MBGL_CORE_FILES
|
||||
src/mbgl/style/data_driven_property_evaluator.hpp
|
||||
src/mbgl/style/group_by_layout.cpp
|
||||
src/mbgl/style/group_by_layout.hpp
|
||||
src/mbgl/style/image.cpp
|
||||
src/mbgl/style/layer.cpp
|
||||
src/mbgl/style/layer_impl.cpp
|
||||
src/mbgl/style/layer_impl.hpp
|
||||
|
||||
@@ -43,7 +43,6 @@ set(MBGL_TEST_FILES
|
||||
|
||||
# sprite
|
||||
test/sprite/sprite_atlas.test.cpp
|
||||
test/sprite/sprite_image.test.cpp
|
||||
test/sprite/sprite_parser.test.cpp
|
||||
|
||||
# src/mbgl/test
|
||||
@@ -95,6 +94,7 @@ set(MBGL_TEST_FILES
|
||||
test/style/paint_property.test.cpp
|
||||
test/style/source.test.cpp
|
||||
test/style/style.test.cpp
|
||||
test/style/style_image.test.cpp
|
||||
test/style/style_layer.test.cpp
|
||||
test/style/style_parser.test.cpp
|
||||
test/style/tile_source.test.cpp
|
||||
|
||||
@@ -25,9 +25,9 @@ class Backend;
|
||||
class View;
|
||||
class FileSource;
|
||||
class Scheduler;
|
||||
class SpriteImage;
|
||||
|
||||
namespace style {
|
||||
class Image;
|
||||
class Source;
|
||||
class Layer;
|
||||
} // namespace style
|
||||
@@ -154,9 +154,9 @@ public:
|
||||
LatLng latLngForPixel(const ScreenCoordinate&) const;
|
||||
|
||||
// Annotations
|
||||
void addAnnotationIcon(const std::string&, std::shared_ptr<const SpriteImage>);
|
||||
void removeAnnotationIcon(const std::string&);
|
||||
double getTopOffsetPixelsForAnnotationIcon(const std::string&);
|
||||
void addAnnotationImage(const std::string&, std::unique_ptr<style::Image>);
|
||||
void removeAnnotationImage(const std::string&);
|
||||
double getTopOffsetPixelsForAnnotationImage(const std::string&);
|
||||
|
||||
AnnotationID addAnnotation(const Annotation&);
|
||||
void updateAnnotation(AnnotationID, const Annotation&);
|
||||
@@ -174,10 +174,10 @@ public:
|
||||
void addLayer(std::unique_ptr<style::Layer>, const optional<std::string>& beforeLayerID = {});
|
||||
std::unique_ptr<style::Layer> removeLayer(const std::string& layerID);
|
||||
|
||||
// Add image, bound to the style
|
||||
void addImage(const std::string&, std::unique_ptr<const SpriteImage>);
|
||||
// Images
|
||||
void addImage(const std::string&, std::unique_ptr<style::Image>);
|
||||
void removeImage(const std::string&);
|
||||
const SpriteImage* getImage(const std::string&);
|
||||
const style::Image* getImage(const std::string&);
|
||||
|
||||
// Defaults
|
||||
std::string getStyleName() const;
|
||||
|
||||
@@ -1,18 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#include <mbgl/util/noncopyable.hpp>
|
||||
#include <mbgl/util/geo.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
|
||||
#include <string>
|
||||
#include <memory>
|
||||
#include <cstdint>
|
||||
|
||||
namespace mbgl {
|
||||
namespace style {
|
||||
|
||||
class SpriteImage : private util::noncopyable {
|
||||
class Image {
|
||||
public:
|
||||
SpriteImage(PremultipliedImage&&, float pixelRatio, bool sdf = false);
|
||||
Image(PremultipliedImage&&, float pixelRatio, bool sdf = false);
|
||||
|
||||
PremultipliedImage image;
|
||||
|
||||
@@ -26,4 +21,5 @@ public:
|
||||
float getHeight() const { return image.size.height / pixelRatio; }
|
||||
};
|
||||
|
||||
} // namespace style
|
||||
} // namespace mbgl
|
||||
@@ -25,7 +25,7 @@
|
||||
#include <mbgl/util/logging.hpp>
|
||||
#include <mbgl/util/platform.hpp>
|
||||
#include <mbgl/util/projection.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/filter.hpp>
|
||||
|
||||
// Java -> C++ conversion
|
||||
@@ -735,12 +735,12 @@ void NativeMapView::addAnnotationIcon(JNIEnv& env, jni::String symbol, jint w, j
|
||||
}
|
||||
|
||||
jni::GetArrayRegion(env, *jpixels, 0, size, reinterpret_cast<jbyte*>(premultipliedImage.data.get()));
|
||||
auto iconImage = std::make_shared<mbgl::SpriteImage>(std::move(premultipliedImage), float(scale));
|
||||
map->addAnnotationIcon(symbolName, iconImage);
|
||||
map->addAnnotationImage(symbolName,
|
||||
std::make_unique<mbgl::style::Image>(std::move(premultipliedImage), float(scale)));
|
||||
}
|
||||
|
||||
jdouble NativeMapView::getTopOffsetPixelsForAnnotationSymbol(JNIEnv& env, jni::String symbolName) {
|
||||
return map->getTopOffsetPixelsForAnnotationIcon(jni::Make<std::string>(env, symbolName));
|
||||
return map->getTopOffsetPixelsForAnnotationImage(jni::Make<std::string>(env, symbolName));
|
||||
}
|
||||
|
||||
jlong NativeMapView::getTransitionDuration(JNIEnv&) {
|
||||
@@ -1036,9 +1036,9 @@ void NativeMapView::addImage(JNIEnv& env, jni::String name, jni::jint w, jni::ji
|
||||
}
|
||||
|
||||
jni::GetArrayRegion(env, *pixels, 0, size, reinterpret_cast<jbyte*>(premultipliedImage.data.get()));
|
||||
auto spriteImage = std::make_unique<mbgl::SpriteImage>(std::move(premultipliedImage), float(scale));
|
||||
|
||||
map->addImage(jni::Make<std::string>(env, name), std::move(spriteImage));
|
||||
map->addImage(jni::Make<std::string>(env, name),
|
||||
std::make_unique<mbgl::style::Image>(std::move(premultipliedImage), float(scale)));
|
||||
}
|
||||
|
||||
void NativeMapView::removeImage(JNIEnv& env, jni::String name) {
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
|
||||
#include <mbgl/map/map.hpp>
|
||||
#include <mbgl/util/default_styles.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/layers/fill_layer.hpp>
|
||||
#include <mbgl/style/layers/line_layer.hpp>
|
||||
#include <mbgl/style/layers/symbol_layer.hpp>
|
||||
@@ -538,7 +538,7 @@ static NSURL *MGLStyleURL_emerald;
|
||||
format:@"Cannot assign image %@ to a nil name.", image];
|
||||
}
|
||||
|
||||
self.mapView.mbglMap->addImage([name UTF8String], image.mgl_spriteImage);
|
||||
self.mapView.mbglMap->addImage([name UTF8String], image.mgl_styleImage);
|
||||
}
|
||||
|
||||
- (void)removeImageForName:(NSString *)name
|
||||
@@ -558,8 +558,8 @@ static NSURL *MGLStyleURL_emerald;
|
||||
format:@"Cannot get image with nil name."];
|
||||
}
|
||||
|
||||
auto spriteImage = self.mapView.mbglMap->getImage([name UTF8String]);
|
||||
return spriteImage ? [[MGLImage alloc] initWithMGLSpriteImage:spriteImage] : nil;
|
||||
auto styleImage = self.mapView.mbglMap->getImage([name UTF8String]);
|
||||
return styleImage ? [[MGLImage alloc] initWithMGLStyleImage:styleImage] : nil;
|
||||
}
|
||||
|
||||
#pragma mark Style transitions
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
#include "glfw_view.hpp"
|
||||
|
||||
#include <mbgl/annotation/annotation.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/transition_options.hpp>
|
||||
#include <mbgl/util/logging.hpp>
|
||||
#include <mbgl/util/platform.hpp>
|
||||
@@ -124,7 +124,7 @@ GLFWView::~GLFWView() {
|
||||
|
||||
void GLFWView::setMap(mbgl::Map *map_) {
|
||||
map = map_;
|
||||
map->addAnnotationIcon("default_marker", makeSpriteImage(22, 22, 1));
|
||||
map->addAnnotationImage("default_marker", makeImage(22, 22, 1));
|
||||
}
|
||||
|
||||
void GLFWView::updateAssumedState() {
|
||||
@@ -258,8 +258,8 @@ mbgl::Point<double> GLFWView::makeRandomPoint() const {
|
||||
return { latLng.longitude(), latLng.latitude() };
|
||||
}
|
||||
|
||||
std::shared_ptr<const mbgl::SpriteImage>
|
||||
GLFWView::makeSpriteImage(int width, int height, float pixelRatio) {
|
||||
std::unique_ptr<mbgl::style::Image>
|
||||
GLFWView::makeImage(int width, int height, float pixelRatio) {
|
||||
const int r = 255 * (double(std::rand()) / RAND_MAX);
|
||||
const int g = 255 * (double(std::rand()) / RAND_MAX);
|
||||
const int b = 255 * (double(std::rand()) / RAND_MAX);
|
||||
@@ -284,7 +284,7 @@ GLFWView::makeSpriteImage(int width, int height, float pixelRatio) {
|
||||
}
|
||||
}
|
||||
|
||||
return std::make_shared<mbgl::SpriteImage>(std::move(image), pixelRatio);
|
||||
return std::make_unique<mbgl::style::Image>(std::move(image), pixelRatio);
|
||||
}
|
||||
|
||||
void GLFWView::nextOrientation() {
|
||||
@@ -301,7 +301,7 @@ void GLFWView::addRandomCustomPointAnnotations(int count) {
|
||||
for (int i = 0; i < count; i++) {
|
||||
static int spriteID = 1;
|
||||
const auto name = std::string{ "marker-" } + mbgl::util::toString(spriteID++);
|
||||
map->addAnnotationIcon(name, makeSpriteImage(22, 22, 1));
|
||||
map->addAnnotationImage(name, makeImage(22, 22, 1));
|
||||
spriteIDs.push_back(name);
|
||||
annotationIDs.push_back(map->addAnnotation(mbgl::SymbolAnnotation { makeRandomPoint(), name }));
|
||||
}
|
||||
|
||||
@@ -65,8 +65,7 @@ private:
|
||||
|
||||
mbgl::Color makeRandomColor() const;
|
||||
mbgl::Point<double> makeRandomPoint() const;
|
||||
static std::shared_ptr<const mbgl::SpriteImage>
|
||||
makeSpriteImage(int width, int height, float pixelRatio);
|
||||
static std::unique_ptr<mbgl::style::Image> makeImage(int width, int height, float pixelRatio);
|
||||
|
||||
void nextOrientation();
|
||||
|
||||
|
||||
@@ -8,7 +8,6 @@
|
||||
#include <mbgl/map/map.hpp>
|
||||
#include <mbgl/map/view.hpp>
|
||||
#include <mbgl/annotation/annotation.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/map/camera.hpp>
|
||||
#include <mbgl/map/mode.hpp>
|
||||
#include <mbgl/util/platform.hpp>
|
||||
@@ -16,6 +15,7 @@
|
||||
#include <mbgl/util/default_thread_pool.hpp>
|
||||
#include <mbgl/storage/default_file_source.hpp>
|
||||
#include <mbgl/storage/network_status.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/transition_options.hpp>
|
||||
#include <mbgl/style/layers/custom_layer.hpp>
|
||||
#include <mbgl/map/backend.hpp>
|
||||
@@ -3451,8 +3451,7 @@ public:
|
||||
annotationImage.delegate = self;
|
||||
|
||||
// add sprite
|
||||
std::shared_ptr<mbgl::SpriteImage> sprite(annotationImage.image.mgl_spriteImage);
|
||||
_mbglMap->addAnnotationIcon(iconIdentifier.UTF8String, sprite);
|
||||
_mbglMap->addAnnotationImage(iconIdentifier.UTF8String, annotationImage.image.mgl_styleImage);
|
||||
|
||||
// Create a slop area with a “radius” equal in size to the annotation
|
||||
// image’s alignment rect, allowing the eventual tap to be on any point
|
||||
@@ -4096,7 +4095,7 @@ public:
|
||||
|
||||
// Remove the old icon from the style.
|
||||
if ( ! [iconIdentifier isEqualToString:fallbackIconIdentifier]) {
|
||||
_mbglMap->removeAnnotationIcon(iconIdentifier.UTF8String);
|
||||
_mbglMap->removeAnnotationImage(iconIdentifier.UTF8String);
|
||||
}
|
||||
|
||||
if (annotationImage.image)
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
#import <UIKit/UIKit.h>
|
||||
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface UIImage (MGLAdditions)
|
||||
|
||||
- (nullable instancetype)initWithMGLSpriteImage:(const mbgl::SpriteImage *)spriteImage;
|
||||
- (nullable instancetype)initWithMGLStyleImage:(const mbgl::style::Image *)styleImage;
|
||||
|
||||
- (std::unique_ptr<mbgl::SpriteImage>)mgl_spriteImage;
|
||||
- (std::unique_ptr<mbgl::style::Image>)mgl_styleImage;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@@ -4,16 +4,16 @@
|
||||
|
||||
@implementation UIImage (MGLAdditions)
|
||||
|
||||
- (nullable instancetype)initWithMGLSpriteImage:(const mbgl::SpriteImage *)spriteImage
|
||||
- (nullable instancetype)initWithMGLStyleImage:(const mbgl::style::Image *)styleImage
|
||||
{
|
||||
CGImageRef image = CGImageFromMGLPremultipliedImage(spriteImage->image.clone());
|
||||
CGImageRef image = CGImageFromMGLPremultipliedImage(styleImage->image.clone());
|
||||
if (!image) {
|
||||
return nil;
|
||||
}
|
||||
|
||||
if (self = [self initWithCGImage:image scale:spriteImage->pixelRatio orientation:UIImageOrientationUp])
|
||||
if (self = [self initWithCGImage:image scale:styleImage->pixelRatio orientation:UIImageOrientationUp])
|
||||
{
|
||||
if (spriteImage->sdf)
|
||||
if (styleImage->sdf)
|
||||
{
|
||||
self = [self imageWithRenderingMode:UIImageRenderingModeAlwaysTemplate];
|
||||
}
|
||||
@@ -22,10 +22,10 @@
|
||||
return self;
|
||||
}
|
||||
|
||||
- (std::unique_ptr<mbgl::SpriteImage>)mgl_spriteImage {
|
||||
- (std::unique_ptr<mbgl::style::Image>)mgl_styleImage {
|
||||
BOOL isTemplate = self.renderingMode == UIImageRenderingModeAlwaysTemplate;
|
||||
return std::make_unique<mbgl::SpriteImage>(MGLPremultipliedImageFromCGImage(self.CGImage),
|
||||
float(self.scale), isTemplate);
|
||||
return std::make_unique<mbgl::style::Image>(MGLPremultipliedImageFromCGImage(self.CGImage),
|
||||
float(self.scale), isTemplate);
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
#import <mbgl/util/default_thread_pool.hpp>
|
||||
#import <mbgl/map/backend.hpp>
|
||||
#import <mbgl/map/backend_scope.hpp>
|
||||
#import <mbgl/sprite/sprite_image.hpp>
|
||||
#import <mbgl/style/image.hpp>
|
||||
#import <mbgl/storage/default_file_source.hpp>
|
||||
#import <mbgl/storage/network_status.hpp>
|
||||
#import <mbgl/math/wrap.hpp>
|
||||
@@ -1949,8 +1949,7 @@ public:
|
||||
return;
|
||||
}
|
||||
|
||||
std::shared_ptr<mbgl::SpriteImage> sprite(annotationImage.image.mgl_spriteImage);
|
||||
_mbglMap->addAnnotationIcon(iconIdentifier.UTF8String, sprite);
|
||||
_mbglMap->addAnnotationImage(iconIdentifier.UTF8String, annotationImage.image.mgl_styleImage);
|
||||
|
||||
// Create a slop area with a “radius” equal to the annotation image’s entire
|
||||
// size, allowing the eventual click to be on any point within this image.
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#import <Cocoa/Cocoa.h>
|
||||
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@@ -8,9 +8,9 @@ NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
- (nullable instancetype)initWithMGLPremultipliedImage:(mbgl::PremultipliedImage&&)image;
|
||||
|
||||
- (nullable instancetype)initWithMGLSpriteImage:(const mbgl::SpriteImage *)spriteImage;
|
||||
- (nullable instancetype)initWithMGLStyleImage:(const mbgl::style::Image *)image;
|
||||
|
||||
- (std::unique_ptr<mbgl::SpriteImage>)mgl_spriteImage;
|
||||
- (std::unique_ptr<mbgl::style::Image>)mgl_styleImage;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@@ -15,22 +15,22 @@
|
||||
return self;
|
||||
}
|
||||
|
||||
- (nullable instancetype)initWithMGLSpriteImage:(const mbgl::SpriteImage *)spriteImage {
|
||||
CGImageRef image = CGImageFromMGLPremultipliedImage(spriteImage->image.clone());
|
||||
- (nullable instancetype)initWithMGLStyleImage:(const mbgl::style::Image *)styleImage {
|
||||
CGImageRef image = CGImageFromMGLPremultipliedImage(styleImage->image.clone());
|
||||
if (!image) {
|
||||
return nil;
|
||||
}
|
||||
|
||||
NSBitmapImageRep *rep = [[NSBitmapImageRep alloc] initWithCGImage:image];
|
||||
CGImageRelease(image);
|
||||
if (self = [self initWithSize:NSMakeSize(spriteImage->getWidth(), spriteImage->getHeight())]) {
|
||||
if (self = [self initWithSize:NSMakeSize(styleImage->getWidth(), styleImage->getHeight())]) {
|
||||
[self addRepresentation:rep];
|
||||
[self setTemplate:spriteImage->sdf];
|
||||
[self setTemplate:styleImage->sdf];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (std::unique_ptr<mbgl::SpriteImage>)mgl_spriteImage {
|
||||
- (std::unique_ptr<mbgl::style::Image>)mgl_styleImage {
|
||||
// Create a bitmap image representation from the image, respecting backing
|
||||
// scale factor and any resizing done on the image at runtime.
|
||||
// http://www.cocoabuilder.com/archive/cocoa/82430-nsimage-getting-raw-bitmap-data.html#82431
|
||||
@@ -40,7 +40,7 @@
|
||||
|
||||
mbgl::PremultipliedImage cPremultipliedImage({ static_cast<uint32_t>(rep.pixelsWide), static_cast<uint32_t>(rep.pixelsHigh) });
|
||||
std::copy(rep.bitmapData, rep.bitmapData + cPremultipliedImage.bytes(), cPremultipliedImage.data.get());
|
||||
return std::make_unique<mbgl::SpriteImage>(std::move(cPremultipliedImage),
|
||||
return std::make_unique<mbgl::style::Image>(std::move(cPremultipliedImage),
|
||||
(float)(rep.pixelsWide / self.size.width),
|
||||
[self isTemplate]);
|
||||
}
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
#include <mbgl/style/conversion/source.hpp>
|
||||
#include <mbgl/style/conversion/layer.hpp>
|
||||
#include <mbgl/style/conversion/filter.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/map/backend_scope.hpp>
|
||||
#include <mbgl/map/query.hpp>
|
||||
|
||||
@@ -684,7 +684,7 @@ void NodeMap::AddImage(const Nan::FunctionCallbackInfo<v8::Value>& info) {
|
||||
std::copy(imageDataBuffer, imageDataBuffer + imageLength, data.get());
|
||||
mbgl::PremultipliedImage cPremultipliedImage({ imageWidth, imageHeight}, std::move(data));
|
||||
|
||||
nodeMap->map->addImage(*Nan::Utf8String(info[0]), std::make_unique<mbgl::SpriteImage>(std::move(cPremultipliedImage), pixelRatio));
|
||||
nodeMap->map->addImage(*Nan::Utf8String(info[0]), std::make_unique<mbgl::style::Image>(std::move(cPremultipliedImage), pixelRatio));
|
||||
}
|
||||
|
||||
void NodeMap::RemoveImage(const Nan::FunctionCallbackInfo<v8::Value>& info) {
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
#include <mbgl/style/layers/custom_layer.hpp>
|
||||
#include <mbgl/style/sources/geojson_source.hpp>
|
||||
#include <mbgl/style/transition_options.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/storage/network_status.hpp>
|
||||
#include <mbgl/util/color.hpp>
|
||||
#include <mbgl/util/constants.hpp>
|
||||
@@ -88,7 +88,7 @@ mbgl::Size sanitizedSize(const QSize& size) {
|
||||
};
|
||||
};
|
||||
|
||||
std::unique_ptr<const mbgl::SpriteImage> toSpriteImage(const QImage &sprite) {
|
||||
std::unique_ptr<mbgl::style::Image> toStyleImage(const QImage &sprite) {
|
||||
const QImage swapped = sprite
|
||||
.rgbSwapped()
|
||||
.convertToFormat(QImage::Format_ARGB32_Premultiplied);
|
||||
@@ -96,7 +96,7 @@ std::unique_ptr<const mbgl::SpriteImage> toSpriteImage(const QImage &sprite) {
|
||||
auto img = std::make_unique<uint8_t[]>(swapped.byteCount());
|
||||
memcpy(img.get(), swapped.constBits(), swapped.byteCount());
|
||||
|
||||
return std::make_unique<mbgl::SpriteImage>(
|
||||
return std::make_unique<mbgl::style::Image>(
|
||||
mbgl::PremultipliedImage(
|
||||
{ static_cast<uint32_t>(swapped.width()), static_cast<uint32_t>(swapped.height()) },
|
||||
std::move(img)),
|
||||
@@ -1114,7 +1114,7 @@ void QMapboxGL::addAnnotationIcon(const QString &name, const QImage &icon)
|
||||
{
|
||||
if (icon.isNull()) return;
|
||||
|
||||
d_ptr->mapObj->addAnnotationIcon(name.toStdString(), toSpriteImage(icon));
|
||||
d_ptr->mapObj->addAnnotationImage(name.toStdString(), toStyleImage(icon));
|
||||
}
|
||||
|
||||
/*!
|
||||
@@ -1414,7 +1414,7 @@ void QMapboxGL::addImage(const QString &id, const QImage &image)
|
||||
{
|
||||
if (image.isNull()) return;
|
||||
|
||||
d_ptr->mapObj->addImage(id.toStdString(), toSpriteImage(image));
|
||||
d_ptr->mapObj->addImage(id.toStdString(), toStyleImage(image));
|
||||
}
|
||||
|
||||
/*!
|
||||
|
||||
@@ -208,17 +208,17 @@ void AnnotationManager::removeTile(AnnotationTile& tile) {
|
||||
tiles.erase(&tile);
|
||||
}
|
||||
|
||||
void AnnotationManager::addIcon(const std::string& name, std::shared_ptr<const SpriteImage> sprite) {
|
||||
spriteAtlas.setSprite(name, sprite);
|
||||
void AnnotationManager::addImage(const std::string& id, std::unique_ptr<style::Image> image) {
|
||||
spriteAtlas.addImage(id, std::move(image));
|
||||
}
|
||||
|
||||
void AnnotationManager::removeIcon(const std::string& name) {
|
||||
spriteAtlas.removeSprite(name);
|
||||
void AnnotationManager::removeImage(const std::string& id) {
|
||||
spriteAtlas.removeImage(id);
|
||||
}
|
||||
|
||||
double AnnotationManager::getTopOffsetPixelsForIcon(const std::string& name) {
|
||||
auto sprite = spriteAtlas.getSprite(name);
|
||||
return sprite ? -(sprite->image.size.height / sprite->pixelRatio) / 2 : 0;
|
||||
double AnnotationManager::getTopOffsetPixelsForImage(const std::string& id) {
|
||||
const style::Image* image = spriteAtlas.getImage(id);
|
||||
return image ? -(image->image.size.height / image->pixelRatio) / 2 : 0;
|
||||
}
|
||||
|
||||
} // namespace mbgl
|
||||
|
||||
@@ -20,6 +20,7 @@ class ShapeAnnotationImpl;
|
||||
|
||||
namespace style {
|
||||
class Style;
|
||||
class Image;
|
||||
} // namespace style
|
||||
|
||||
class AnnotationManager : private util::noncopyable {
|
||||
@@ -31,9 +32,9 @@ public:
|
||||
Update updateAnnotation(const AnnotationID&, const Annotation&, const uint8_t maxZoom);
|
||||
void removeAnnotation(const AnnotationID&);
|
||||
|
||||
void addIcon(const std::string& name, std::shared_ptr<const SpriteImage>);
|
||||
void removeIcon(const std::string& name);
|
||||
double getTopOffsetPixelsForIcon(const std::string& name);
|
||||
void addImage(const std::string&, std::unique_ptr<style::Image>);
|
||||
void removeImage(const std::string&);
|
||||
double getTopOffsetPixelsForImage(const std::string&);
|
||||
SpriteAtlas& getSpriteAtlas() { return spriteAtlas; }
|
||||
|
||||
void updateStyle(style::Style&);
|
||||
|
||||
@@ -812,16 +812,16 @@ LatLng Map::latLngForPixel(const ScreenCoordinate& pixel) const {
|
||||
|
||||
#pragma mark - Annotations
|
||||
|
||||
void Map::addAnnotationIcon(const std::string& name, std::shared_ptr<const SpriteImage> sprite) {
|
||||
impl->annotationManager->addIcon(name, sprite);
|
||||
void Map::addAnnotationImage(const std::string& id, std::unique_ptr<style::Image> image) {
|
||||
impl->annotationManager->addImage(id, std::move(image));
|
||||
}
|
||||
|
||||
void Map::removeAnnotationIcon(const std::string& name) {
|
||||
impl->annotationManager->removeIcon(name);
|
||||
void Map::removeAnnotationImage(const std::string& id) {
|
||||
impl->annotationManager->removeImage(id);
|
||||
}
|
||||
|
||||
double Map::getTopOffsetPixelsForAnnotationIcon(const std::string& name) {
|
||||
return impl->annotationManager->getTopOffsetPixelsForIcon(name);
|
||||
double Map::getTopOffsetPixelsForAnnotationImage(const std::string& id) {
|
||||
return impl->annotationManager->getTopOffsetPixelsForImage(id);
|
||||
}
|
||||
|
||||
AnnotationID Map::addAnnotation(const Annotation& annotation) {
|
||||
@@ -951,29 +951,29 @@ std::unique_ptr<Layer> Map::removeLayer(const std::string& id) {
|
||||
return removedLayer;
|
||||
}
|
||||
|
||||
void Map::addImage(const std::string& name, std::unique_ptr<const SpriteImage> image) {
|
||||
void Map::addImage(const std::string& id, std::unique_ptr<style::Image> image) {
|
||||
if (!impl->style) {
|
||||
return;
|
||||
}
|
||||
|
||||
impl->styleMutated = true;
|
||||
impl->style->spriteAtlas->setSprite(name, std::move(image));
|
||||
impl->style->spriteAtlas->addImage(id, std::move(image));
|
||||
impl->onUpdate(Update::Repaint);
|
||||
}
|
||||
|
||||
void Map::removeImage(const std::string& name) {
|
||||
void Map::removeImage(const std::string& id) {
|
||||
if (!impl->style) {
|
||||
return;
|
||||
}
|
||||
|
||||
impl->styleMutated = true;
|
||||
impl->style->spriteAtlas->removeSprite(name);
|
||||
impl->style->spriteAtlas->removeImage(id);
|
||||
impl->onUpdate(Update::Repaint);
|
||||
}
|
||||
|
||||
const SpriteImage* Map::getImage(const std::string& name) {
|
||||
const style::Image* Map::getImage(const std::string& id) {
|
||||
if (impl->style) {
|
||||
return impl->style->spriteAtlas->getSprite(name).get();
|
||||
return impl->style->spriteAtlas->getImage(id);
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
@@ -38,20 +38,20 @@ struct SpriteAtlas::Loader {
|
||||
};
|
||||
|
||||
SpriteAtlasElement::SpriteAtlasElement(Rect<uint16_t> rect_,
|
||||
std::shared_ptr<const SpriteImage> spriteImage,
|
||||
const style::Image& image,
|
||||
Size size_, float pixelRatio)
|
||||
: pos(std::move(rect_)),
|
||||
sdf(spriteImage->sdf),
|
||||
relativePixelRatio(spriteImage->pixelRatio / pixelRatio),
|
||||
width(spriteImage->getWidth()),
|
||||
height(spriteImage->getHeight()) {
|
||||
sdf(image.sdf),
|
||||
relativePixelRatio(image.pixelRatio / pixelRatio),
|
||||
width(image.getWidth()),
|
||||
height(image.getHeight()) {
|
||||
|
||||
const float padding = 1;
|
||||
|
||||
const float w = spriteImage->getWidth() * relativePixelRatio;
|
||||
const float h = spriteImage->getHeight() * relativePixelRatio;
|
||||
const float w = image.getWidth() * relativePixelRatio;
|
||||
const float h = image.getHeight() * relativePixelRatio;
|
||||
|
||||
size = {{ float(spriteImage->getWidth()), spriteImage->getHeight() }};
|
||||
size = {{ float(image.getWidth()), image.getHeight() }};
|
||||
tl = {{ float(pos.x + padding) / size_.width, float(pos.y + padding) / size_.height }};
|
||||
br = {{ float(pos.x + padding + w) / size_.width, float(pos.y + padding + h) / size_.height }};
|
||||
}
|
||||
@@ -116,9 +116,11 @@ void SpriteAtlas::emitSpriteLoadedIfComplete() {
|
||||
// TODO: delete the loader?
|
||||
}
|
||||
|
||||
void SpriteAtlas::onParsed(Sprites&& result) {
|
||||
void SpriteAtlas::onParsed(Images&& result) {
|
||||
markAsLoaded();
|
||||
setSprites(result);
|
||||
for (auto& pair : result) {
|
||||
addImage(pair.first, std::move(pair.second));
|
||||
}
|
||||
observer->onSpriteLoaded();
|
||||
for (auto requestor : requestors) {
|
||||
requestor->onIconsAvailable(this, buildIconMap());
|
||||
@@ -138,19 +140,38 @@ void SpriteAtlas::dumpDebugLogs() const {
|
||||
Log::Info(Event::General, "SpriteAtlas::loaded: %d", loaded);
|
||||
}
|
||||
|
||||
void SpriteAtlas::setSprites(const Sprites& newSprites) {
|
||||
for (const auto& pair : newSprites) {
|
||||
_setSprite(pair.first, pair.second);
|
||||
void SpriteAtlas::addImage(const std::string& id, std::unique_ptr<style::Image> image_) {
|
||||
icons.clear();
|
||||
|
||||
auto it = entries.find(id);
|
||||
if (it == entries.end()) {
|
||||
entries.emplace(id, Entry { std::move(image_), {}, {} });
|
||||
return;
|
||||
}
|
||||
|
||||
Entry& entry = it->second;
|
||||
|
||||
// There is already a sprite with that name in our store.
|
||||
if (entry.image->image.size != image_->image.size) {
|
||||
Log::Warning(Event::Sprite, "Can't change sprite dimensions for '%s'", id.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
entry.image = std::move(image_);
|
||||
|
||||
if (entry.iconRect) {
|
||||
copy(entry, &Entry::iconRect);
|
||||
}
|
||||
|
||||
if (entry.patternRect) {
|
||||
copy(entry, &Entry::patternRect);
|
||||
}
|
||||
}
|
||||
|
||||
void SpriteAtlas::setSprite(const std::string& name, std::shared_ptr<const SpriteImage> sprite) {
|
||||
_setSprite(name, sprite);
|
||||
}
|
||||
|
||||
void SpriteAtlas::removeSprite(const std::string& name) {
|
||||
void SpriteAtlas::removeImage(const std::string& id) {
|
||||
icons.clear();
|
||||
auto it = entries.find(name);
|
||||
|
||||
auto it = entries.find(id);
|
||||
if (it == entries.end()) {
|
||||
return;
|
||||
}
|
||||
@@ -168,49 +189,15 @@ void SpriteAtlas::removeSprite(const std::string& name) {
|
||||
entries.erase(it);
|
||||
}
|
||||
|
||||
void SpriteAtlas::_setSprite(const std::string& name,
|
||||
const std::shared_ptr<const SpriteImage>& sprite) {
|
||||
icons.clear();
|
||||
if (!sprite->image.valid()) {
|
||||
Log::Warning(Event::Sprite, "invalid sprite image '%s'", name.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
auto it = entries.find(name);
|
||||
if (it == entries.end()) {
|
||||
entries.emplace(name, Entry { sprite, {}, {} });
|
||||
return;
|
||||
}
|
||||
|
||||
Entry& entry = it->second;
|
||||
|
||||
// There is already a sprite with that name in our store.
|
||||
if (entry.spriteImage->image.size != sprite->image.size) {
|
||||
Log::Warning(Event::Sprite, "Can't change sprite dimensions for '%s'", name.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
entry.spriteImage = sprite;
|
||||
|
||||
if (entry.iconRect) {
|
||||
copy(entry, &Entry::iconRect);
|
||||
}
|
||||
|
||||
if (entry.patternRect) {
|
||||
copy(entry, &Entry::patternRect);
|
||||
}
|
||||
}
|
||||
|
||||
std::shared_ptr<const SpriteImage> SpriteAtlas::getSprite(const std::string& name) {
|
||||
const auto it = entries.find(name);
|
||||
const style::Image* SpriteAtlas::getImage(const std::string& id) const {
|
||||
const auto it = entries.find(id);
|
||||
if (it != entries.end()) {
|
||||
return it->second.spriteImage;
|
||||
} else {
|
||||
if (!entries.empty()) {
|
||||
Log::Info(Event::Sprite, "Can't find sprite named '%s'", name.c_str());
|
||||
}
|
||||
return nullptr;
|
||||
return it->second.image.get();
|
||||
}
|
||||
if (!entries.empty()) {
|
||||
Log::Info(Event::Sprite, "Can't find sprite named '%s'", id.c_str());
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void SpriteAtlas::getIcons(IconRequestor& requestor) {
|
||||
@@ -225,21 +212,21 @@ void SpriteAtlas::removeRequestor(IconRequestor& requestor) {
|
||||
requestors.erase(&requestor);
|
||||
}
|
||||
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getIcon(const std::string& name) {
|
||||
return getImage(name, &Entry::iconRect);
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getIcon(const std::string& id) {
|
||||
return getImage(id, &Entry::iconRect);
|
||||
}
|
||||
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getPattern(const std::string& name) {
|
||||
return getImage(name, &Entry::patternRect);
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getPattern(const std::string& id) {
|
||||
return getImage(id, &Entry::patternRect);
|
||||
}
|
||||
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getImage(const std::string& name,
|
||||
optional<SpriteAtlasElement> SpriteAtlas::getImage(const std::string& id,
|
||||
optional<Rect<uint16_t>> Entry::*entryRect) {
|
||||
|
||||
auto it = entries.find(name);
|
||||
auto it = entries.find(id);
|
||||
if (it == entries.end()) {
|
||||
if (!entries.empty()) {
|
||||
Log::Info(Event::Sprite, "Can't find sprite named '%s'", name.c_str());
|
||||
Log::Info(Event::Sprite, "Can't find sprite named '%s'", id.c_str());
|
||||
}
|
||||
return {};
|
||||
}
|
||||
@@ -247,17 +234,17 @@ optional<SpriteAtlasElement> SpriteAtlas::getImage(const std::string& name,
|
||||
Entry& entry = it->second;
|
||||
|
||||
if (entry.*entryRect) {
|
||||
assert(entry.spriteImage.get());
|
||||
assert(entry.image.get());
|
||||
return SpriteAtlasElement {
|
||||
*(entry.*entryRect),
|
||||
entry.spriteImage,
|
||||
*entry.image,
|
||||
size,
|
||||
pixelRatio
|
||||
};
|
||||
}
|
||||
|
||||
const uint16_t pixelWidth = std::ceil(entry.spriteImage->image.size.width / pixelRatio);
|
||||
const uint16_t pixelHeight = std::ceil(entry.spriteImage->image.size.height / pixelRatio);
|
||||
const uint16_t pixelWidth = std::ceil(entry.image->image.size.width / pixelRatio);
|
||||
const uint16_t pixelHeight = std::ceil(entry.image->image.size.height / pixelRatio);
|
||||
|
||||
// Increase to next number divisible by 4, but at least 1.
|
||||
// This is so we can scale down the texture coordinates and pack them
|
||||
@@ -279,7 +266,7 @@ optional<SpriteAtlasElement> SpriteAtlas::getImage(const std::string& name,
|
||||
|
||||
return SpriteAtlasElement {
|
||||
rect,
|
||||
entry.spriteImage,
|
||||
*entry.image,
|
||||
size,
|
||||
pixelRatio
|
||||
};
|
||||
@@ -292,7 +279,7 @@ void SpriteAtlas::copy(const Entry& entry, optional<Rect<uint16_t>> Entry::*entr
|
||||
image.fill(0);
|
||||
}
|
||||
|
||||
const PremultipliedImage& src = entry.spriteImage->image;
|
||||
const PremultipliedImage& src = entry.image->image;
|
||||
const Rect<uint16_t>& rect = *(entry.*entryRect);
|
||||
|
||||
const uint32_t padding = 1;
|
||||
@@ -316,7 +303,7 @@ void SpriteAtlas::copy(const Entry& entry, optional<Rect<uint16_t>> Entry::*entr
|
||||
|
||||
IconMap SpriteAtlas::buildIconMap() {
|
||||
if (icons.empty()) {
|
||||
for (auto entry : entries) {
|
||||
for (const auto& entry : entries) {
|
||||
icons.emplace(std::piecewise_construct,
|
||||
std::forward_as_tuple(entry.first),
|
||||
std::forward_as_tuple(*getIcon(entry.first)));
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
#include <mbgl/gl/texture.hpp>
|
||||
#include <mbgl/util/noncopyable.hpp>
|
||||
#include <mbgl/util/optional.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
|
||||
#include <string>
|
||||
#include <map>
|
||||
@@ -25,7 +25,7 @@ class Context;
|
||||
|
||||
class SpriteAtlasElement {
|
||||
public:
|
||||
SpriteAtlasElement(Rect<uint16_t>, std::shared_ptr<const SpriteImage>, Size size, float pixelRatio);
|
||||
SpriteAtlasElement(Rect<uint16_t>, const style::Image&, Size size, float pixelRatio);
|
||||
|
||||
Rect<uint16_t> pos;
|
||||
bool sdf;
|
||||
@@ -52,7 +52,7 @@ public:
|
||||
|
||||
class SpriteAtlas : public util::noncopyable {
|
||||
public:
|
||||
using Sprites = std::map<std::string, std::shared_ptr<const SpriteImage>>;
|
||||
using Images = std::map<std::string, std::unique_ptr<style::Image>>;
|
||||
|
||||
SpriteAtlas(Size, float pixelRatio);
|
||||
~SpriteAtlas();
|
||||
@@ -71,10 +71,9 @@ public:
|
||||
|
||||
void setObserver(SpriteAtlasObserver*);
|
||||
|
||||
void setSprite(const std::string&, std::shared_ptr<const SpriteImage>);
|
||||
void removeSprite(const std::string&);
|
||||
|
||||
std::shared_ptr<const SpriteImage> getSprite(const std::string& name);
|
||||
const style::Image* getImage(const std::string&) const;
|
||||
void addImage(const std::string&, std::unique_ptr<style::Image>);
|
||||
void removeImage(const std::string&);
|
||||
|
||||
void getIcons(IconRequestor& requestor);
|
||||
void removeRequestor(IconRequestor& requestor);
|
||||
@@ -93,18 +92,16 @@ public:
|
||||
float getPixelRatio() const { return pixelRatio; }
|
||||
|
||||
// Only for use in tests.
|
||||
void setSprites(const Sprites& sprites);
|
||||
const PremultipliedImage& getAtlasImage() const {
|
||||
return image;
|
||||
}
|
||||
|
||||
private:
|
||||
void _setSprite(const std::string&, const std::shared_ptr<const SpriteImage>& = nullptr);
|
||||
void emitSpriteLoadedIfComplete();
|
||||
|
||||
// Invoked by SpriteAtlasWorker
|
||||
friend class SpriteAtlasWorker;
|
||||
void onParsed(Sprites&& result);
|
||||
void onParsed(Images&& result);
|
||||
void onError(std::exception_ptr);
|
||||
|
||||
const Size size;
|
||||
@@ -118,7 +115,7 @@ private:
|
||||
SpriteAtlasObserver* observer = nullptr;
|
||||
|
||||
struct Entry {
|
||||
std::shared_ptr<const SpriteImage> spriteImage;
|
||||
std::unique_ptr<style::Image> image;
|
||||
|
||||
// One sprite image might be used as both an icon image and a pattern image. If so,
|
||||
// it must have two distinct entries in the texture. The one for the icon image has
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#include <mbgl/sprite/sprite_parser.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
|
||||
#include <mbgl/util/logging.hpp>
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
|
||||
namespace mbgl {
|
||||
|
||||
SpriteImagePtr createSpriteImage(const PremultipliedImage& image,
|
||||
std::unique_ptr<style::Image> createStyleImage(const PremultipliedImage& image,
|
||||
const uint32_t srcX,
|
||||
const uint32_t srcY,
|
||||
const uint32_t width,
|
||||
@@ -37,7 +37,7 @@ SpriteImagePtr createSpriteImage(const PremultipliedImage& image,
|
||||
// Copy from the source image into our individual sprite image
|
||||
PremultipliedImage::copy(image, dstImage, { srcX, srcY }, { 0, 0 }, { width, height });
|
||||
|
||||
return std::make_unique<const SpriteImage>(std::move(dstImage), ratio, sdf);
|
||||
return std::make_unique<style::Image>(std::move(dstImage), ratio, sdf);
|
||||
}
|
||||
|
||||
namespace {
|
||||
@@ -84,8 +84,8 @@ bool getBoolean(const JSValue& value, const char* name, const bool def = false)
|
||||
|
||||
} // namespace
|
||||
|
||||
Sprites parseSprite(const std::string& image, const std::string& json) {
|
||||
const PremultipliedImage raster = decodeImage(image);
|
||||
Images parseSprite(const std::string& encodedImage, const std::string& json) {
|
||||
const PremultipliedImage raster = decodeImage(encodedImage);
|
||||
|
||||
JSDocument doc;
|
||||
doc.Parse<0>(json.c_str());
|
||||
@@ -96,7 +96,7 @@ Sprites parseSprite(const std::string& image, const std::string& json) {
|
||||
} else if (!doc.IsObject()) {
|
||||
throw std::runtime_error("Sprite JSON root must be an object");
|
||||
} else {
|
||||
Sprites sprites;
|
||||
Images images;
|
||||
for (const auto& property : doc.GetObject()) {
|
||||
const std::string name = { property.name.GetString(), property.name.GetStringLength() };
|
||||
const JSValue& value = property.value;
|
||||
@@ -109,13 +109,13 @@ Sprites parseSprite(const std::string& image, const std::string& json) {
|
||||
const double pixelRatio = getDouble(value, "pixelRatio", 1);
|
||||
const bool sdf = getBoolean(value, "sdf", false);
|
||||
|
||||
auto sprite = createSpriteImage(raster, x, y, width, height, pixelRatio, sdf);
|
||||
if (sprite) {
|
||||
sprites.emplace(name, sprite);
|
||||
auto image = createStyleImage(raster, x, y, width, height, pixelRatio, sdf);
|
||||
if (image) {
|
||||
images.emplace(name, std::move(image));
|
||||
}
|
||||
}
|
||||
}
|
||||
return sprites;
|
||||
return images;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -11,12 +11,12 @@
|
||||
|
||||
namespace mbgl {
|
||||
|
||||
class SpriteImage;
|
||||
|
||||
using SpriteImagePtr = std::shared_ptr<const SpriteImage>;
|
||||
namespace style {
|
||||
class Image;
|
||||
} // namespace style
|
||||
|
||||
// Extracts an individual image from a spritesheet from the given location.
|
||||
SpriteImagePtr createSpriteImage(const PremultipliedImage&,
|
||||
std::unique_ptr<style::Image> createStyleImage(const PremultipliedImage&,
|
||||
uint32_t srcX,
|
||||
uint32_t srcY,
|
||||
uint32_t srcWidth,
|
||||
@@ -24,9 +24,9 @@ SpriteImagePtr createSpriteImage(const PremultipliedImage&,
|
||||
double ratio,
|
||||
bool sdf);
|
||||
|
||||
using Sprites = std::map<std::string, SpriteImagePtr>;
|
||||
using Images = std::map<std::string, std::unique_ptr<style::Image>>;
|
||||
|
||||
// Parses an image and an associated JSON file and returns the sprite objects.
|
||||
Sprites parseSprite(const std::string& image, const std::string& json);
|
||||
Images parseSprite(const std::string& image, const std::string& json);
|
||||
|
||||
} // namespace mbgl
|
||||
|
||||
@@ -1,14 +1,12 @@
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/util/exception.hpp>
|
||||
|
||||
#include <cmath>
|
||||
|
||||
namespace mbgl {
|
||||
namespace style {
|
||||
|
||||
SpriteImage::SpriteImage(PremultipliedImage&& image_,
|
||||
const float pixelRatio_,
|
||||
bool sdf_)
|
||||
Image::Image(PremultipliedImage&& image_,
|
||||
const float pixelRatio_,
|
||||
bool sdf_)
|
||||
: image(std::move(image_)),
|
||||
pixelRatio(pixelRatio_),
|
||||
sdf(sdf_) {
|
||||
@@ -20,4 +18,5 @@ SpriteImage::SpriteImage(PremultipliedImage&& image_,
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace style
|
||||
} // namespace mbgl
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
#include <mbgl/text/glyph.hpp>
|
||||
#include <mbgl/sprite/sprite_atlas.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/util/optional.hpp>
|
||||
|
||||
namespace mbgl {
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
|
||||
#include <mbgl/util/default_thread_pool.hpp>
|
||||
#include <mbgl/annotation/annotation.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/map/map.hpp>
|
||||
#include <mbgl/map/backend_scope.hpp>
|
||||
#include <mbgl/gl/headless_backend.hpp>
|
||||
@@ -16,9 +16,9 @@ using namespace mbgl;
|
||||
|
||||
namespace {
|
||||
|
||||
std::shared_ptr<SpriteImage> namedMarker(const std::string &name) {
|
||||
std::unique_ptr<style::Image> namedMarker(const std::string& name) {
|
||||
PremultipliedImage image = decodeImage(util::read_file("test/fixtures/sprites/" + name));
|
||||
return std::make_shared<SpriteImage>(std::move(image), 1.0);
|
||||
return std::make_unique<style::Image>(std::move(image), 1.0);
|
||||
}
|
||||
|
||||
class AnnotationTest {
|
||||
@@ -43,7 +43,7 @@ TEST(Annotations, SymbolAnnotation) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double>(0, 0), "default_marker" });
|
||||
test.checkRendering("point_annotation");
|
||||
|
||||
@@ -158,7 +158,7 @@ TEST(Annotations, AddMultiple) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double> { -10, 0 }, "default_marker" });
|
||||
|
||||
test::render(test.map, test.view);
|
||||
@@ -185,8 +185,8 @@ TEST(Annotations, UpdateSymbolAnnotationGeometry) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationIcon("flipped_marker", namedMarker("flipped_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("flipped_marker", namedMarker("flipped_marker.png"));
|
||||
AnnotationID point = test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" });
|
||||
|
||||
test::render(test.map, test.view);
|
||||
@@ -199,8 +199,8 @@ TEST(Annotations, UpdateSymbolAnnotationIcon) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationIcon("flipped_marker", namedMarker("flipped_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("flipped_marker", namedMarker("flipped_marker.png"));
|
||||
AnnotationID point = test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" });
|
||||
|
||||
test::render(test.map, test.view);
|
||||
@@ -281,7 +281,7 @@ TEST(Annotations, RemovePoint) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
AnnotationID point = test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" });
|
||||
|
||||
test::render(test.map, test.view);
|
||||
@@ -320,7 +320,7 @@ TEST(Annotations, SwitchStyle) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" });
|
||||
|
||||
test::render(test.map, test.view);
|
||||
@@ -333,7 +333,7 @@ TEST(Annotations, QueryRenderedFeatures) {
|
||||
AnnotationTest test;
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" });
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double> { 0, 50 }, "default_marker" });
|
||||
|
||||
@@ -357,7 +357,7 @@ TEST(Annotations, QueryFractionalZoomLevels) {
|
||||
auto box = ScreenBox { {}, { double(viewSize.width), double(viewSize.height) } };
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
|
||||
std::vector<mbgl::AnnotationID> ids;
|
||||
for (int longitude = 0; longitude < 10; ++longitude) {
|
||||
@@ -389,7 +389,7 @@ TEST(Annotations, VisibleFeatures) {
|
||||
auto box = ScreenBox { {}, { double(viewSize.width), double(viewSize.height) } };
|
||||
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.setLatLngZoom({ 5, 5 }, 3);
|
||||
|
||||
std::vector<mbgl::AnnotationID> ids;
|
||||
@@ -442,7 +442,7 @@ TEST(Annotations, DebugSparse) {
|
||||
test.map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"));
|
||||
test.map.setDebug(MapDebugOptions::TileBorders);
|
||||
test.map.setZoom(1);
|
||||
test.map.addAnnotationIcon("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotationImage("default_marker", namedMarker("default_marker.png"));
|
||||
test.map.addAnnotation(SymbolAnnotation { Point<double>(10, 10), "default_marker" });
|
||||
|
||||
test.checkRendering("debug_sparse");
|
||||
|
||||
@@ -3,12 +3,12 @@
|
||||
#include <mbgl/gl/headless_backend.hpp>
|
||||
#include <mbgl/gl/offscreen_view.hpp>
|
||||
#include <mbgl/util/default_thread_pool.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/test/stub_file_source.hpp>
|
||||
#include <mbgl/test/util.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
#include <mbgl/util/io.hpp>
|
||||
#include <mbgl/util/run_loop.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/source.hpp>
|
||||
|
||||
using namespace mbgl;
|
||||
@@ -19,11 +19,9 @@ namespace {
|
||||
class QueryTest {
|
||||
public:
|
||||
QueryTest() {
|
||||
auto decoded = decodeImage(util::read_file("test/fixtures/sprites/default_marker.png"));
|
||||
auto image = std::make_unique<SpriteImage>(std::move(decoded), 1.0);
|
||||
|
||||
map.setStyleJSON(util::read_file("test/fixtures/api/query_style.json"));
|
||||
map.addImage("test-icon", std::move(image));
|
||||
map.addImage("test-icon", std::make_unique<style::Image>(
|
||||
decodeImage(util::read_file("test/fixtures/sprites/default_marker.png")), 1.0));
|
||||
|
||||
test::render(map, view);
|
||||
}
|
||||
|
||||
@@ -9,7 +9,6 @@
|
||||
#include <mbgl/gl/offscreen_view.hpp>
|
||||
#include <mbgl/gl/context.hpp>
|
||||
#include <mbgl/util/default_thread_pool.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/storage/network_status.hpp>
|
||||
#include <mbgl/storage/default_file_source.hpp>
|
||||
#include <mbgl/storage/online_file_source.hpp>
|
||||
@@ -17,6 +16,7 @@
|
||||
#include <mbgl/util/io.hpp>
|
||||
#include <mbgl/util/run_loop.hpp>
|
||||
#include <mbgl/util/async_task.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/style/layers/background_layer.hpp>
|
||||
#include <mbgl/util/color.hpp>
|
||||
|
||||
@@ -479,8 +479,8 @@ TEST(Map, AddImage) {
|
||||
Map map(test.backend, test.view.getSize(), 1, test.fileSource, test.threadPool, MapMode::Still);
|
||||
auto decoded1 = decodeImage(util::read_file("test/fixtures/sprites/default_marker.png"));
|
||||
auto decoded2 = decodeImage(util::read_file("test/fixtures/sprites/default_marker.png"));
|
||||
auto image1 = std::make_unique<SpriteImage>(std::move(decoded1), 1.0);
|
||||
auto image2 = std::make_unique<SpriteImage>(std::move(decoded2), 1.0);
|
||||
auto image1 = std::make_unique<style::Image>(std::move(decoded1), 1.0);
|
||||
auto image2 = std::make_unique<style::Image>(std::move(decoded2), 1.0);
|
||||
|
||||
// No-op.
|
||||
map.addImage("test-icon", std::move(image1));
|
||||
@@ -495,7 +495,7 @@ TEST(Map, RemoveImage) {
|
||||
|
||||
Map map(test.backend, test.view.getSize(), 1, test.fileSource, test.threadPool, MapMode::Still);
|
||||
auto decoded = decodeImage(util::read_file("test/fixtures/sprites/default_marker.png"));
|
||||
auto image = std::make_unique<SpriteImage>(std::move(decoded), 1.0);
|
||||
auto image = std::make_unique<style::Image>(std::move(decoded), 1.0);
|
||||
|
||||
map.setStyleJSON(util::read_file("test/fixtures/api/icon_style.json"));
|
||||
map.addImage("test-icon", std::move(image));
|
||||
@@ -508,7 +508,7 @@ TEST(Map, GetImage) {
|
||||
|
||||
Map map(test.backend, test.view.getSize(), 1, test.fileSource, test.threadPool, MapMode::Still);
|
||||
auto decoded = decodeImage(util::read_file("test/fixtures/sprites/default_marker.png"));
|
||||
auto image = std::make_unique<SpriteImage>(std::move(decoded), 1.0);
|
||||
auto image = std::make_unique<style::Image>(std::move(decoded), 1.0);
|
||||
|
||||
map.setStyleJSON(util::read_file("test/fixtures/api/icon_style.json"));
|
||||
map.addImage("test-icon", std::move(image));
|
||||
|
||||
@@ -18,12 +18,13 @@ using namespace mbgl;
|
||||
|
||||
TEST(SpriteAtlas, Basic) {
|
||||
FixtureLog log;
|
||||
|
||||
auto spriteParseResult = parseSprite(util::read_file("test/fixtures/annotations/emerald.png"),
|
||||
util::read_file("test/fixtures/annotations/emerald.json"));
|
||||
|
||||
SpriteAtlas atlas({ 63, 112 }, 1);
|
||||
atlas.setSprites(spriteParseResult);
|
||||
|
||||
auto images = parseSprite(util::read_file("test/fixtures/annotations/emerald.png"),
|
||||
util::read_file("test/fixtures/annotations/emerald.json"));
|
||||
for (auto& pair : images) {
|
||||
atlas.addImage(pair.first, std::move(pair.second));
|
||||
}
|
||||
|
||||
EXPECT_EQ(1.0f, atlas.getPixelRatio());
|
||||
EXPECT_EQ(63u, atlas.getSize().width);
|
||||
@@ -74,11 +75,13 @@ TEST(SpriteAtlas, Basic) {
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, Size) {
|
||||
auto spriteParseResult = parseSprite(util::read_file("test/fixtures/annotations/emerald.png"),
|
||||
util::read_file("test/fixtures/annotations/emerald.json"));
|
||||
|
||||
SpriteAtlas atlas({ 63, 112 }, 1.4);
|
||||
atlas.setSprites(spriteParseResult);
|
||||
|
||||
auto images = parseSprite(util::read_file("test/fixtures/annotations/emerald.png"),
|
||||
util::read_file("test/fixtures/annotations/emerald.json"));
|
||||
for (auto& pair : images) {
|
||||
atlas.addImage(pair.first, std::move(pair.second));
|
||||
}
|
||||
|
||||
EXPECT_DOUBLE_EQ(1.4f, atlas.getPixelRatio());
|
||||
EXPECT_EQ(63u, atlas.getSize().width);
|
||||
@@ -110,7 +113,7 @@ TEST(SpriteAtlas, Updates) {
|
||||
EXPECT_EQ(32u, atlas.getSize().width);
|
||||
EXPECT_EQ(32u, atlas.getSize().height);
|
||||
|
||||
atlas.setSprite("one", std::make_shared<SpriteImage>(PremultipliedImage({ 16, 12 }), 1));
|
||||
atlas.addImage("one", std::make_unique<style::Image>(PremultipliedImage({ 16, 12 }), 1));
|
||||
auto one = *atlas.getIcon("one");
|
||||
float imagePixelRatio = one.relativePixelRatio * atlas.getPixelRatio();
|
||||
EXPECT_EQ(0, one.pos.x);
|
||||
@@ -129,45 +132,30 @@ TEST(SpriteAtlas, Updates) {
|
||||
|
||||
test::checkImage("test/fixtures/sprite_atlas/updates_before", atlas.getAtlasImage());
|
||||
|
||||
// Update sprite
|
||||
// Update image
|
||||
PremultipliedImage image2({ 16, 12 });
|
||||
for (size_t i = 0; i < image2.bytes(); i++) {
|
||||
image2.data.get()[i] = 255;
|
||||
}
|
||||
auto newSprite = std::make_shared<SpriteImage>(std::move(image2), 1);
|
||||
atlas.setSprite("one", newSprite);
|
||||
ASSERT_EQ(newSprite, atlas.getSprite("one"));
|
||||
atlas.addImage("one", std::make_unique<style::Image>(std::move(image2), 1));
|
||||
|
||||
test::checkImage("test/fixtures/sprite_atlas/updates_after", atlas.getAtlasImage());
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, AddRemove) {
|
||||
FixtureLog log;
|
||||
|
||||
const auto sprite1 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
const auto sprite2 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
const auto sprite3 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
|
||||
SpriteAtlas atlas({ 32, 32 }, 1);
|
||||
|
||||
// Adding single
|
||||
atlas.setSprite("one", sprite1);
|
||||
atlas.addImage("one", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
atlas.addImage("two", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
atlas.addImage("three", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
|
||||
// Adding multiple
|
||||
atlas.setSprite("two", sprite2);
|
||||
atlas.setSprite("three", sprite3);
|
||||
atlas.removeImage("one");
|
||||
atlas.removeImage("two");
|
||||
|
||||
// Removing
|
||||
atlas.removeSprite("one");
|
||||
atlas.removeSprite("two");
|
||||
|
||||
// Accessing
|
||||
EXPECT_EQ(sprite3, atlas.getSprite("three"));
|
||||
|
||||
EXPECT_TRUE(log.empty());
|
||||
|
||||
EXPECT_EQ(nullptr, atlas.getSprite("two"));
|
||||
EXPECT_EQ(nullptr, atlas.getSprite("four"));
|
||||
EXPECT_NE(nullptr, atlas.getImage("three"));
|
||||
EXPECT_EQ(nullptr, atlas.getImage("two"));
|
||||
EXPECT_EQ(nullptr, atlas.getImage("four"));
|
||||
|
||||
EXPECT_EQ(1u, log.count({
|
||||
EventSeverity::Info,
|
||||
@@ -181,9 +169,6 @@ TEST(SpriteAtlas, AddRemove) {
|
||||
int64_t(-1),
|
||||
"Can't find sprite named 'four'",
|
||||
}));
|
||||
|
||||
// Overwriting
|
||||
atlas.setSprite("three", sprite1);
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, RemoveReleasesBinPackRect) {
|
||||
@@ -191,68 +176,40 @@ TEST(SpriteAtlas, RemoveReleasesBinPackRect) {
|
||||
|
||||
SpriteAtlas atlas({ 36, 36 }, 1);
|
||||
|
||||
const auto big = std::make_shared<SpriteImage>(PremultipliedImage({ 32, 32 }), 1);
|
||||
|
||||
atlas.setSprite("big", big);
|
||||
atlas.addImage("big", std::make_unique<style::Image>(PremultipliedImage({ 32, 32 }), 1));
|
||||
EXPECT_TRUE(atlas.getIcon("big"));
|
||||
|
||||
atlas.removeSprite("big");
|
||||
atlas.removeImage("big");
|
||||
|
||||
atlas.setSprite("big", big);
|
||||
atlas.addImage("big", std::make_unique<style::Image>(PremultipliedImage({ 32, 32 }), 1));
|
||||
EXPECT_TRUE(atlas.getIcon("big"));
|
||||
|
||||
EXPECT_EQ(big, atlas.getSprite("big"));
|
||||
EXPECT_TRUE(log.empty());
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, OtherPixelRatio) {
|
||||
FixtureLog log;
|
||||
|
||||
const auto sprite1 = std::make_shared<SpriteImage>(PremultipliedImage({ 8, 8 }), 1);
|
||||
|
||||
SpriteAtlas atlas({ 32, 32 }, 1);
|
||||
|
||||
// Adding mismatched sprite image
|
||||
atlas.setSprite("one", sprite1);
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, Multiple) {
|
||||
const auto sprite1 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
const auto sprite2 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
|
||||
SpriteAtlas atlas({ 32, 32 }, 1);
|
||||
|
||||
atlas.setSprites({
|
||||
{ "one", sprite1 }, { "two", sprite2 },
|
||||
});
|
||||
atlas.addImage("one", std::make_unique<style::Image>(PremultipliedImage({ 8, 8 }), 2));
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, Replace) {
|
||||
FixtureLog log;
|
||||
|
||||
const auto sprite1 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
const auto sprite2 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
|
||||
SpriteAtlas atlas({ 32, 32 }, 1);
|
||||
|
||||
atlas.setSprite("sprite", sprite1);
|
||||
EXPECT_EQ(sprite1, atlas.getSprite("sprite"));
|
||||
atlas.setSprite("sprite", sprite2);
|
||||
EXPECT_EQ(sprite2, atlas.getSprite("sprite"));
|
||||
atlas.addImage("sprite", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
auto image = atlas.getImage("sprite");
|
||||
atlas.addImage("sprite", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
EXPECT_NE(image, atlas.getImage("sprite"));
|
||||
}
|
||||
|
||||
TEST(SpriteAtlas, ReplaceWithDifferentDimensions) {
|
||||
FixtureLog log;
|
||||
|
||||
PremultipliedImage image({ 16, 16 });
|
||||
PremultipliedImage image2({ 18, 18 });
|
||||
const auto sprite1 = std::make_shared<SpriteImage>(PremultipliedImage({ 16, 16 }), 2);
|
||||
const auto sprite2 = std::make_shared<SpriteImage>(PremultipliedImage({ 18, 18 }), 2);
|
||||
|
||||
SpriteAtlas atlas({ 32, 32 }, 1);
|
||||
|
||||
atlas.setSprite("sprite", sprite1);
|
||||
atlas.setSprite("sprite", sprite2);
|
||||
atlas.addImage("sprite", std::make_unique<style::Image>(PremultipliedImage({ 16, 16 }), 2));
|
||||
atlas.addImage("sprite", std::make_unique<style::Image>(PremultipliedImage({ 18, 18 }), 2));
|
||||
|
||||
EXPECT_EQ(1u, log.count({
|
||||
EventSeverity::Warning,
|
||||
@@ -260,8 +217,6 @@ TEST(SpriteAtlas, ReplaceWithDifferentDimensions) {
|
||||
int64_t(-1),
|
||||
"Can't change sprite dimensions for 'sprite'",
|
||||
}));
|
||||
|
||||
EXPECT_EQ(sprite1, atlas.getSprite("sprite"));
|
||||
}
|
||||
|
||||
class SpriteAtlasTest {
|
||||
@@ -292,14 +247,14 @@ public:
|
||||
Response successfulSpriteImageResponse(const Resource& resource) {
|
||||
EXPECT_EQ("test/fixtures/resources/sprite.png", resource.url);
|
||||
Response response;
|
||||
response.data = std::make_shared<std::string>(util::read_file(resource.url));
|
||||
response.data = std::make_unique<std::string>(util::read_file(resource.url));
|
||||
return response;
|
||||
}
|
||||
|
||||
Response successfulSpriteJSONResponse(const Resource& resource) {
|
||||
EXPECT_EQ("test/fixtures/resources/sprite.json", resource.url);
|
||||
Response response;
|
||||
response.data = std::make_shared<std::string>(util::read_file(resource.url));
|
||||
response.data = std::make_unique<std::string>(util::read_file(resource.url));
|
||||
return response;
|
||||
}
|
||||
|
||||
@@ -313,7 +268,7 @@ Response failedSpriteResponse(const Resource&) {
|
||||
|
||||
Response corruptSpriteResponse(const Resource&) {
|
||||
Response response;
|
||||
response.data = std::make_shared<std::string>("CORRUPT");
|
||||
response.data = std::make_unique<std::string>("CORRUPT");
|
||||
return response;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,57 +0,0 @@
|
||||
#include <mbgl/test/util.hpp>
|
||||
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
#include <mbgl/util/exception.hpp>
|
||||
|
||||
using namespace mbgl;
|
||||
|
||||
TEST(Sprite, SpriteImageZeroWidth) {
|
||||
PremultipliedImage image({ 0, 16 });
|
||||
try {
|
||||
SpriteImage(std::move(image), 2.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite image dimensions may not be zero", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(Sprite, SpriteImageZeroHeight) {
|
||||
PremultipliedImage image({ 16, 0 });
|
||||
try {
|
||||
SpriteImage(std::move(image), 2.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite image dimensions may not be zero", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(Sprite, SpriteImageZeroRatio) {
|
||||
PremultipliedImage image({ 16, 16 });
|
||||
try {
|
||||
SpriteImage(std::move(image), 0.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite pixelRatio may not be <= 0", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(Sprite, SpriteImage) {
|
||||
PremultipliedImage image({ 32, 24 });
|
||||
SpriteImage sprite(std::move(image), 2.0);
|
||||
EXPECT_EQ(16, sprite.getWidth());
|
||||
EXPECT_EQ(32u, sprite.image.size.width);
|
||||
EXPECT_EQ(12, sprite.getHeight());
|
||||
EXPECT_EQ(24u, sprite.image.size.height);
|
||||
EXPECT_EQ(2, sprite.pixelRatio);
|
||||
}
|
||||
|
||||
TEST(Sprite, SpriteImageFractionalRatio) {
|
||||
PremultipliedImage image({ 20, 12 });
|
||||
SpriteImage sprite(std::move(image), 1.5);
|
||||
EXPECT_EQ(float(20.0 / 1.5), sprite.getWidth());
|
||||
EXPECT_EQ(20u, sprite.image.size.width);
|
||||
EXPECT_EQ(float(12.0 / 1.5), sprite.getHeight());
|
||||
EXPECT_EQ(12u, sprite.image.size.height);
|
||||
EXPECT_EQ(1.5, sprite.pixelRatio);
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
#include <mbgl/test/fixture_log_observer.hpp>
|
||||
|
||||
#include <mbgl/sprite/sprite_parser.hpp>
|
||||
#include <mbgl/sprite/sprite_image.hpp>
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
#include <mbgl/util/io.hpp>
|
||||
#include <mbgl/util/string.hpp>
|
||||
@@ -27,19 +27,19 @@ TEST(Sprite, SpriteImageCreationInvalid) {
|
||||
ASSERT_EQ(200u, image_1x.size.width);
|
||||
ASSERT_EQ(299u, image_1x.size.height);
|
||||
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 0, 16, 1, false)); // width == 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 16, 0, 1, false)); // height == 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, -1, 16, 1, false)); // width < 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 16, -1, 1, false)); // height < 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 1, 1, 0, false)); // ratio == 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 1, 1, -1, false)); // ratio < 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 1, 1, 23, false)); // ratio too large
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 2048, 16, 1, false)); // too wide
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 16, 1025, 1, false)); // too tall
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, -1, 0, 16, 16, 1, false)); // srcX < 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, -1, 16, 16, 1, false)); // srcY < 0
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, image_1x.size.width + 1, 16, 1, false)); // right edge out of bounds
|
||||
ASSERT_EQ(nullptr, createSpriteImage(image_1x, 0, 0, 16, image_1x.size.height + 1, 1, false)); // bottom edge out of bounds
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 0, 16, 1, false)); // width == 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 16, 0, 1, false)); // height == 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, -1, 16, 1, false)); // width < 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 16, -1, 1, false)); // height < 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 1, 1, 0, false)); // ratio == 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 1, 1, -1, false)); // ratio < 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 1, 1, 23, false)); // ratio too large
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 2048, 16, 1, false)); // too wide
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 16, 1025, 1, false)); // too tall
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, -1, 0, 16, 16, 1, false)); // srcX < 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, -1, 16, 16, 1, false)); // srcY < 0
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, image_1x.size.width + 1, 16, 1, false)); // right edge out of bounds
|
||||
ASSERT_EQ(nullptr, createStyleImage(image_1x, 0, 0, 16, image_1x.size.height + 1, 1, false)); // bottom edge out of bounds
|
||||
|
||||
EXPECT_EQ(1u, log.count({
|
||||
EventSeverity::Error,
|
||||
@@ -141,7 +141,7 @@ TEST(Sprite, SpriteImageCreation1x) {
|
||||
ASSERT_EQ(299u, image_1x.size.height);
|
||||
|
||||
{ // "museum_icon":{"x":177,"y":187,"width":18,"height":18,"pixelRatio":1,"sdf":false}
|
||||
const auto sprite = createSpriteImage(image_1x, 177, 187, 18, 18, 1, false);
|
||||
const auto sprite = createStyleImage(image_1x, 177, 187, 18, 18, 1, false);
|
||||
ASSERT_TRUE(sprite.get());
|
||||
EXPECT_EQ(18, sprite->getWidth());
|
||||
EXPECT_EQ(18, sprite->getHeight());
|
||||
@@ -157,7 +157,7 @@ TEST(Sprite, SpriteImageCreation2x) {
|
||||
const PremultipliedImage image_2x = decodeImage(util::read_file("test/fixtures/annotations/emerald@2x.png"));
|
||||
|
||||
// "museum_icon":{"x":354,"y":374,"width":36,"height":36,"pixelRatio":2,"sdf":false}
|
||||
const auto sprite = createSpriteImage(image_2x, 354, 374, 36, 36, 2, false);
|
||||
const auto sprite = createStyleImage(image_2x, 354, 374, 36, 36, 2, false);
|
||||
ASSERT_TRUE(sprite.get());
|
||||
EXPECT_EQ(18, sprite->getWidth());
|
||||
EXPECT_EQ(18, sprite->getHeight());
|
||||
@@ -172,7 +172,7 @@ TEST(Sprite, SpriteImageCreation1_5x) {
|
||||
const PremultipliedImage image_2x = decodeImage(util::read_file("test/fixtures/annotations/emerald@2x.png"));
|
||||
|
||||
// "museum_icon":{"x":354,"y":374,"width":36,"height":36,"pixelRatio":2,"sdf":false}
|
||||
const auto sprite = createSpriteImage(image_2x, 354, 374, 36, 36, 1.5, false);
|
||||
const auto sprite = createStyleImage(image_2x, 354, 374, 36, 36, 1.5, false);
|
||||
ASSERT_TRUE(sprite.get());
|
||||
EXPECT_EQ(24, sprite->getWidth());
|
||||
EXPECT_EQ(24, sprite->getHeight());
|
||||
@@ -183,7 +183,7 @@ TEST(Sprite, SpriteImageCreation1_5x) {
|
||||
sprite->image);
|
||||
|
||||
// "hospital_icon":{"x":314,"y":518,"width":36,"height":36,"pixelRatio":2,"sdf":false}
|
||||
const auto sprite2 = createSpriteImage(image_2x, 314, 518, 35, 35, 1.5, false);
|
||||
const auto sprite2 = createStyleImage(image_2x, 314, 518, 35, 35, 1.5, false);
|
||||
ASSERT_TRUE(sprite2.get());
|
||||
EXPECT_EQ(float(35 / 1.5), sprite2->getWidth());
|
||||
EXPECT_EQ(float(35 / 1.5), sprite2->getHeight());
|
||||
@@ -280,7 +280,7 @@ TEST(Sprite, SpriteParsing) {
|
||||
names);
|
||||
|
||||
{
|
||||
auto sprite = images.find("generic-metro")->second;
|
||||
auto& sprite = images.find("generic-metro")->second;
|
||||
EXPECT_EQ(18, sprite->getWidth());
|
||||
EXPECT_EQ(18, sprite->getHeight());
|
||||
EXPECT_EQ(18u, sprite->image.size.width);
|
||||
|
||||
52
test/style/style_image.test.cpp
Normal file
52
test/style/style_image.test.cpp
Normal file
@@ -0,0 +1,52 @@
|
||||
#include <mbgl/test/util.hpp>
|
||||
|
||||
#include <mbgl/style/image.hpp>
|
||||
#include <mbgl/util/image.hpp>
|
||||
#include <mbgl/util/exception.hpp>
|
||||
|
||||
using namespace mbgl;
|
||||
|
||||
TEST(StyleImage, ZeroWidth) {
|
||||
try {
|
||||
style::Image(PremultipliedImage({ 0, 16 }), 2.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite image dimensions may not be zero", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(StyleImage, ZeroHeight) {
|
||||
try {
|
||||
style::Image(PremultipliedImage({ 16, 0 }), 2.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite image dimensions may not be zero", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(StyleImage, ZeroRatio) {
|
||||
try {
|
||||
style::Image(PremultipliedImage({ 16, 16 }), 0.0);
|
||||
FAIL() << "Expected exception";
|
||||
} catch (util::SpriteImageException& ex) {
|
||||
EXPECT_STREQ("Sprite pixelRatio may not be <= 0", ex.what());
|
||||
}
|
||||
}
|
||||
|
||||
TEST(StyleImage, Retina) {
|
||||
style::Image image(PremultipliedImage({ 32, 24 }), 2.0);
|
||||
EXPECT_EQ(16, image.getWidth());
|
||||
EXPECT_EQ(32u, image.image.size.width);
|
||||
EXPECT_EQ(12, image.getHeight());
|
||||
EXPECT_EQ(24u, image.image.size.height);
|
||||
EXPECT_EQ(2, image.pixelRatio);
|
||||
}
|
||||
|
||||
TEST(StyleImage, FractionalRatio) {
|
||||
style::Image image(PremultipliedImage({ 20, 12 }), 1.5);
|
||||
EXPECT_EQ(float(20.0 / 1.5), image.getWidth());
|
||||
EXPECT_EQ(20u, image.image.size.width);
|
||||
EXPECT_EQ(float(12.0 / 1.5), image.getHeight());
|
||||
EXPECT_EQ(12u, image.image.size.height);
|
||||
EXPECT_EQ(1.5, image.pixelRatio);
|
||||
}
|
||||
@@ -14,7 +14,7 @@ TEST(getIconQuads, normal) {
|
||||
Anchor anchor(2.0, 3.0, 0.0, 0.5f, 0);
|
||||
SpriteAtlasElement image = {
|
||||
Rect<uint16_t>( 0, 0, 15, 11 ),
|
||||
std::make_shared<const SpriteImage>(PremultipliedImage({1,1}), 1.0),
|
||||
style::Image(PremultipliedImage({1,1}), 1.0),
|
||||
{ 0, 0 },
|
||||
1.0f
|
||||
};
|
||||
@@ -47,7 +47,7 @@ TEST(getIconQuads, style) {
|
||||
Anchor anchor(0.0, 0.0, 0.0, 0.5f, 0);
|
||||
SpriteAtlasElement image = {
|
||||
Rect<uint16_t>( 0, 0, 20, 20 ),
|
||||
std::make_shared<const SpriteImage>(PremultipliedImage({1,1}), 1.0),
|
||||
style::Image(PremultipliedImage({1,1}), 1.0),
|
||||
{ 0, 0 },
|
||||
1.0f
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user