diff --git a/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.h b/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.h index 9a08749f4..05c305d64 100644 --- a/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.h +++ b/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.h @@ -1,6 +1,7 @@ #pragma once +#include "YAxisOrientation.h" #include "BitmapRef.hpp" namespace msdfgen { @@ -11,14 +12,16 @@ class Bitmap { public: Bitmap(); - Bitmap(int width, int height); - Bitmap(const BitmapConstRef &orig); + Bitmap(int width, int height, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION); + explicit Bitmap(const BitmapConstRef &orig); + explicit Bitmap(const BitmapConstSection &orig); Bitmap(const Bitmap &orig); #ifdef MSDFGEN_USE_CPP11 Bitmap(Bitmap &&orig); #endif ~Bitmap(); Bitmap &operator=(const BitmapConstRef &orig); + Bitmap &operator=(const BitmapConstSection &orig); Bitmap &operator=(const Bitmap &orig); #ifdef MSDFGEN_USE_CPP11 Bitmap &operator=(Bitmap &&orig); @@ -38,10 +41,17 @@ public: #endif operator BitmapRef(); operator BitmapConstRef() const; + operator BitmapSection(); + operator BitmapConstSection() const; + /// Returns a reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + BitmapSection getSection(int xMin, int yMin, int xMax, int yMax); + /// Returns a constant reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + BitmapConstSection getConstSection(int xMin, int yMin, int xMax, int yMax) const; private: T *pixels; int w, h; + YAxisOrientation yOrientation; }; diff --git a/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.hpp b/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.hpp index 940435778..afb53942f 100644 --- a/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.hpp +++ b/Source/ThirdParty/msdfgen/msdfgen/core/Bitmap.hpp @@ -7,28 +7,41 @@ namespace msdfgen { template -Bitmap::Bitmap() : pixels(NULL), w(0), h(0) { } +Bitmap::Bitmap() : pixels(NULL), w(0), h(0), yOrientation(MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) { } template -Bitmap::Bitmap(int width, int height) : w(width), h(height) { +Bitmap::Bitmap(int width, int height, YAxisOrientation yOrientation) : w(width), h(height), yOrientation(yOrientation) { pixels = new T[N*w*h]; } template -Bitmap::Bitmap(const BitmapConstRef &orig) : w(orig.width), h(orig.height) { +Bitmap::Bitmap(const BitmapConstRef &orig) : w(orig.width), h(orig.height), yOrientation(orig.yOrientation) { pixels = new T[N*w*h]; memcpy(pixels, orig.pixels, sizeof(T)*N*w*h); } template -Bitmap::Bitmap(const Bitmap &orig) : w(orig.w), h(orig.h) { +Bitmap::Bitmap(const BitmapConstSection &orig) : w(orig.width), h(orig.height), yOrientation(orig.yOrientation) { + pixels = new T[N*w*h]; + T *dst = pixels; + const T *src = orig.pixels; + int rowLength = N*w; + for (int y = 0; y < h; ++y) { + memcpy(dst, src, sizeof(T)*rowLength); + dst += rowLength; + src += orig.rowStride; + } +} + +template +Bitmap::Bitmap(const Bitmap &orig) : w(orig.w), h(orig.h), yOrientation(orig.yOrientation) { pixels = new T[N*w*h]; memcpy(pixels, orig.pixels, sizeof(T)*N*w*h); } #ifdef MSDFGEN_USE_CPP11 template -Bitmap::Bitmap(Bitmap &&orig) : pixels(orig.pixels), w(orig.w), h(orig.h) { +Bitmap::Bitmap(Bitmap &&orig) : pixels(orig.pixels), w(orig.w), h(orig.h), yOrientation(orig.yOrientation) { orig.pixels = NULL; orig.w = 0, orig.h = 0; } @@ -36,25 +49,46 @@ Bitmap::Bitmap(Bitmap &&orig) : pixels(orig.pixels), w(orig.w), h(or template Bitmap::~Bitmap() { - delete [] pixels; + delete[] pixels; } template Bitmap &Bitmap::operator=(const BitmapConstRef &orig) { if (pixels != orig.pixels) { - delete [] pixels; + delete[] pixels; w = orig.width, h = orig.height; + yOrientation = orig.yOrientation; pixels = new T[N*w*h]; memcpy(pixels, orig.pixels, sizeof(T)*N*w*h); } return *this; } +template +Bitmap &Bitmap::operator=(const BitmapConstSection &orig) { + if (orig.pixels && orig.pixels >= pixels && orig.pixels < pixels+N*w*h) + return *this = Bitmap(orig); + delete[] pixels; + w = orig.width, h = orig.height; + yOrientation = orig.yOrientation; + pixels = new T[N*w*h]; + T *dst = pixels; + const T *src = orig.pixels; + int rowLength = N*w; + for (int y = 0; y < h; ++y) { + memcpy(dst, src, sizeof(T)*rowLength); + dst += rowLength; + src += orig.rowStride; + } + return *this; +} + template Bitmap &Bitmap::operator=(const Bitmap &orig) { if (this != &orig) { - delete [] pixels; + delete[] pixels; w = orig.w, h = orig.h; + yOrientation = orig.yOrientation; pixels = new T[N*w*h]; memcpy(pixels, orig.pixels, sizeof(T)*N*w*h); } @@ -65,9 +99,10 @@ Bitmap &Bitmap::operator=(const Bitmap &orig) { template Bitmap &Bitmap::operator=(Bitmap &&orig) { if (this != &orig) { - delete [] pixels; + delete[] pixels; pixels = orig.pixels; w = orig.w, h = orig.h; + yOrientation = orig.yOrientation; orig.pixels = NULL; } return *this; @@ -106,12 +141,32 @@ Bitmap::operator const T *() const { template Bitmap::operator BitmapRef() { - return BitmapRef(pixels, w, h); + return BitmapRef(pixels, w, h, yOrientation); } template Bitmap::operator BitmapConstRef() const { - return BitmapConstRef(pixels, w, h); + return BitmapConstRef(pixels, w, h, yOrientation); +} + +template +Bitmap::operator BitmapSection() { + return BitmapSection(pixels, w, h, yOrientation); +} + +template +Bitmap::operator BitmapConstSection() const { + return BitmapConstSection(pixels, w, h, yOrientation); +} + +template +BitmapSection Bitmap::getSection(int xMin, int yMin, int xMax, int yMax) { + return BitmapSection(pixels+N*(w*yMin+xMin), xMax-xMin, yMax-yMin, N*w, yOrientation); +} + +template +BitmapConstSection Bitmap::getConstSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapConstSection(pixels+N*(w*yMin+xMin), xMax-xMin, yMax-yMin, N*w, yOrientation); } } diff --git a/Source/ThirdParty/msdfgen/msdfgen/core/BitmapRef.hpp b/Source/ThirdParty/msdfgen/msdfgen/core/BitmapRef.hpp index cb17f95dc..6e93fe983 100644 --- a/Source/ThirdParty/msdfgen/msdfgen/core/BitmapRef.hpp +++ b/Source/ThirdParty/msdfgen/msdfgen/core/BitmapRef.hpp @@ -1,41 +1,154 @@ #pragma once -#include "base.h" +#include "YAxisOrientation.h" namespace msdfgen { /// Reference to a 2D image bitmap or a buffer acting as one. Pixel storage not owned or managed by the object. template +struct BitmapRef; +/// Constant reference to a 2D image bitmap or a buffer acting as one. Pixel storage not owned or managed by the object. +template +struct BitmapConstRef; +/// Reference to a 2D image bitmap with non-contiguous rows of pixels. Pixel storage not owned or managed by the object. Can represent e.g. a section of a larger bitmap, bitmap with padded rows, or vertically flipped bitmap (rowStride can be negative). +template +struct BitmapSection; +/// Constant reference to a 2D image bitmap with non-contiguous rows of pixels. Pixel storage not owned or managed by the object. Can represent e.g. a section of a larger bitmap, bitmap with padded rows, or vertically flipped bitmap (rowStride can be negative). +template +struct BitmapConstSection; + +template struct BitmapRef { T *pixels; int width, height; + YAxisOrientation yOrientation; - inline BitmapRef() : pixels(NULL), width(0), height(0) { } - inline BitmapRef(T *pixels, int width, int height) : pixels(pixels), width(width), height(height) { } + inline BitmapRef() : pixels(NULL), width(0), height(0), yOrientation(MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) { } + inline BitmapRef(T *pixels, int width, int height, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), yOrientation(yOrientation) { } inline T *operator()(int x, int y) const { return pixels+N*(width*y+x); } + /// Returns a reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapSection getSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapSection(pixels+N*(width*yMin+xMin), xMax-xMin, yMax-yMin, N*width, yOrientation); + } + + /// Returns a constant reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getConstSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapConstSection(pixels+N*(width*yMin+xMin), xMax-xMin, yMax-yMin, N*width, yOrientation); + } + }; -/// Constant reference to a 2D image bitmap or a buffer acting as one. Pixel storage not owned or managed by the object. -template +template struct BitmapConstRef { const T *pixels; int width, height; + YAxisOrientation yOrientation; - inline BitmapConstRef() : pixels(NULL), width(0), height(0) { } - inline BitmapConstRef(const T *pixels, int width, int height) : pixels(pixels), width(width), height(height) { } - inline BitmapConstRef(const BitmapRef &orig) : pixels(orig.pixels), width(orig.width), height(orig.height) { } + inline BitmapConstRef() : pixels(NULL), width(0), height(0), yOrientation(MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) { } + inline BitmapConstRef(const T *pixels, int width, int height, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), yOrientation(yOrientation) { } + inline BitmapConstRef(const BitmapRef &orig) : pixels(orig.pixels), width(orig.width), height(orig.height), yOrientation(orig.yOrientation) { } inline const T *operator()(int x, int y) const { return pixels+N*(width*y+x); } + /// Returns a constant reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapConstSection(pixels+N*(width*yMin+xMin), xMax-xMin, yMax-yMin, N*width, yOrientation); + } + + /// Returns a constant reference to a rectangular section of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getConstSection(int xMin, int yMin, int xMax, int yMax) const { + return getSection(xMin, yMin, xMax, yMax); + } + +}; + +template +struct BitmapSection { + + T *pixels; + int width, height; + /// Specifies the difference between the beginnings of adjacent pixel rows as the number of T elements, can be negative. + int rowStride; + YAxisOrientation yOrientation; + + inline BitmapSection() : pixels(NULL), width(0), height(0), rowStride(0), yOrientation(MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) { } + inline BitmapSection(T *pixels, int width, int height, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), rowStride(N*width), yOrientation(yOrientation) { } + inline BitmapSection(T *pixels, int width, int height, int rowStride, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), rowStride(rowStride), yOrientation(yOrientation) { } + inline BitmapSection(const BitmapRef &orig) : pixels(orig.pixels), width(orig.width), height(orig.height), rowStride(N*orig.width), yOrientation(orig.yOrientation) { } + + inline T *operator()(int x, int y) const { + return pixels+rowStride*y+N*x; + } + + /// Returns a reference to a rectangular subsection of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapSection getSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapSection(pixels+rowStride*yMin+N*xMin, xMax-xMin, yMax-yMin, rowStride, yOrientation); + } + + /// Returns a constant reference to a rectangular subsection of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getConstSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapConstSection(pixels+rowStride*yMin+N*xMin, xMax-xMin, yMax-yMin, rowStride, yOrientation); + } + + /// Makes sure that the section's Y-axis orientation matches the argument by potentially reordering its rows. + inline void reorient(YAxisOrientation newYAxisOrientation) { + if (yOrientation != newYAxisOrientation) { + pixels += rowStride*(height-1); + rowStride = -rowStride; + yOrientation = newYAxisOrientation; + } + } + +}; + +template +struct BitmapConstSection { + + const T *pixels; + int width, height; + /// Specifies the difference between the beginnings of adjacent pixel rows as the number of T elements, can be negative. + int rowStride; + YAxisOrientation yOrientation; + + inline BitmapConstSection() : pixels(NULL), width(0), height(0), rowStride(0), yOrientation(MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) { } + inline BitmapConstSection(const T *pixels, int width, int height, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), rowStride(N*width), yOrientation(yOrientation) { } + inline BitmapConstSection(const T *pixels, int width, int height, int rowStride, YAxisOrientation yOrientation = MSDFGEN_Y_AXIS_DEFAULT_ORIENTATION) : pixels(pixels), width(width), height(height), rowStride(rowStride), yOrientation(yOrientation) { } + inline BitmapConstSection(const BitmapRef &orig) : pixels(orig.pixels), width(orig.width), height(orig.height), rowStride(N*orig.width), yOrientation(orig.yOrientation) { } + inline BitmapConstSection(const BitmapConstRef &orig) : pixels(orig.pixels), width(orig.width), height(orig.height), rowStride(N*orig.width), yOrientation(orig.yOrientation) { } + inline BitmapConstSection(const BitmapSection &orig) : pixels(orig.pixels), width(orig.width), height(orig.height), rowStride(orig.rowStride), yOrientation(orig.yOrientation) { } + + inline const T *operator()(int x, int y) const { + return pixels+rowStride*y+N*x; + } + + /// Returns a constant reference to a rectangular subsection of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getSection(int xMin, int yMin, int xMax, int yMax) const { + return BitmapConstSection(pixels+rowStride*yMin+N*xMin, xMax-xMin, yMax-yMin, rowStride, yOrientation); + } + + /// Returns a constant reference to a rectangular subsection of the bitmap specified by bounds (excluding xMax, yMax). + inline BitmapConstSection getConstSection(int xMin, int yMin, int xMax, int yMax) const { + return getSection(xMin, yMin, xMax, yMax); + } + + /// Makes sure that the section's Y-axis orientation matches the argument by potentially reordering its rows. + inline void reorient(YAxisOrientation newYAxisOrientation) { + if (yOrientation != newYAxisOrientation) { + pixels += rowStride*(height-1); + rowStride = -rowStride; + yOrientation = newYAxisOrientation; + } + } + }; } diff --git a/Source/ThirdParty/msdfgen/msdfgen/core/Contour.h b/Source/ThirdParty/msdfgen/msdfgen/core/Contour.h index 4cae48fad..53ceb8eda 100644 --- a/Source/ThirdParty/msdfgen/msdfgen/core/Contour.h +++ b/Source/ThirdParty/msdfgen/msdfgen/core/Contour.h @@ -21,9 +21,9 @@ public: /// Creates a new edge in the contour and returns its reference. EdgeHolder &addEdge(); /// Adjusts the bounding box to fit the contour. - void bound(double &l, double &b, double &r, double &t) const; + void bound(double &xMin, double &yMin, double &xMax, double &yMax) const; /// Adjusts the bounding box to fit the contour border's mitered corners. - void boundMiters(double &l, double &b, double &r, double &t, double border, double miterLimit, int polarity) const; + void boundMiters(double &xMin, double &yMin, double &xMax, double &yMax, double border, double miterLimit, int polarity) const; /// Computes the winding of the contour. Returns 1 if positive, -1 if negative. int winding() const; /// Reverses the sequence of edges on the contour. diff --git a/Source/ThirdParty/msdfgen/msdfgen/core/MSDFErrorCorrection.h b/Source/ThirdParty/msdfgen/msdfgen/core/MSDFErrorCorrection.h index 9cd14eccf..995b1d614 100644 --- a/Source/ThirdParty/msdfgen/msdfgen/core/MSDFErrorCorrection.h +++ b/Source/ThirdParty/msdfgen/msdfgen/core/MSDFErrorCorrection.h @@ -20,7 +20,7 @@ public: }; MSDFErrorCorrection(); - explicit MSDFErrorCorrection(const BitmapRef &stencil, const SDFTransformation &transformation); + explicit MSDFErrorCorrection(const BitmapSection &stencil, const SDFTransformation &transformation); /// Sets the minimum ratio between the actual and maximum expected distance delta to be considered an error. void setMinDeviationRatio(double minDeviationRatio); /// Sets the minimum ratio between the pre-correction distance error and the post-correction distance error. @@ -29,23 +29,23 @@ public: void protectCorners(const Shape &shape); /// Flags all texels that contribute to edges as protected. template - void protectEdges(const BitmapConstRef &sdf); + void protectEdges(const BitmapConstSection &sdf); /// Flags all texels as protected. void protectAll(); /// Flags texels that are expected to cause interpolation artifacts based on analysis of the SDF only. template - void findErrors(const BitmapConstRef &sdf); + void findErrors(const BitmapConstSection &sdf); /// Flags texels that are expected to cause interpolation artifacts based on analysis of the SDF and comparison with the exact shape distance. template