Shared attributes (#1898)
This commit is contained in:
@@ -40,6 +40,7 @@ using DrawableTweakerPtr = std::shared_ptr<DrawableTweaker>;
|
||||
using IndexVectorBasePtr = std::shared_ptr<IndexVectorBase>;
|
||||
using ShaderProgramBasePtr = std::shared_ptr<ShaderProgramBase>;
|
||||
using Texture2DPtr = std::shared_ptr<Texture2D>;
|
||||
using VertexAttributeArrayPtr = std::shared_ptr<VertexAttributeArray>;
|
||||
|
||||
class Drawable {
|
||||
public:
|
||||
@@ -188,16 +189,10 @@ public:
|
||||
virtual void setColorMode(const gfx::ColorMode&);
|
||||
|
||||
/// Get the vertex attributes that override default values in the shader program
|
||||
virtual const gfx::VertexAttributeArray& getVertexAttributes() const = 0;
|
||||
|
||||
/// Get the mutable vertex attribute array
|
||||
virtual gfx::VertexAttributeArray& mutableVertexAttributes() = 0;
|
||||
const gfx::VertexAttributeArrayPtr& getVertexAttributes() const noexcept { return vertexAttributes; }
|
||||
|
||||
/// Set vertex attribute array
|
||||
virtual void setVertexAttributes(const gfx::VertexAttributeArray&) = 0;
|
||||
|
||||
/// Set vertex attribute array
|
||||
virtual void setVertexAttributes(gfx::VertexAttributeArray&&) = 0;
|
||||
void setVertexAttributes(gfx::VertexAttributeArrayPtr value) noexcept { vertexAttributes = std::move(value); }
|
||||
|
||||
/// Provide raw data for vertices. Incompatible with adding primitives
|
||||
virtual void setVertices(std::vector<uint8_t>&&, std::size_t, AttributeDataType) = 0;
|
||||
@@ -259,6 +254,7 @@ protected:
|
||||
int32_t subLayerIndex = 0;
|
||||
DepthMaskType depthType; // = DepthMaskType::ReadOnly;
|
||||
UniqueDrawableData drawableData{};
|
||||
gfx::VertexAttributeArrayPtr vertexAttributes;
|
||||
|
||||
struct Impl;
|
||||
std::unique_ptr<Impl> impl;
|
||||
|
||||
@@ -42,7 +42,7 @@ public:
|
||||
UniqueDrawable& getCurrentDrawable(bool createIfNone);
|
||||
|
||||
/// Close the current drawable, using a new one for any further work
|
||||
void flush();
|
||||
void flush(gfx::Context& context);
|
||||
|
||||
/// Get all the completed drawables
|
||||
const std::vector<UniqueDrawable>& getDrawables() const { return drawables; }
|
||||
@@ -134,9 +134,6 @@ public:
|
||||
/// Set the shader to be used
|
||||
void setShader(gfx::ShaderProgramBasePtr value) { shader = std::move(value); }
|
||||
|
||||
/// Get the vertex attributes that override default values in the shader program
|
||||
const gfx::VertexAttributeArray& getVertexAttributes() const;
|
||||
|
||||
/// Set the name given to new drawables
|
||||
void setDrawableName(std::string value) { drawableName = std::move(value); }
|
||||
|
||||
@@ -157,9 +154,12 @@ public:
|
||||
/// Clear the tweaker collection
|
||||
void clearTweakers() { tweakers.clear(); }
|
||||
|
||||
/// Get the vertex attributes that override default values in the shader program
|
||||
VertexAttributeArrayPtr& getVertexAttributes() { return vertexAttrs; }
|
||||
const VertexAttributeArrayPtr& getVertexAttributes() const { return vertexAttrs; }
|
||||
|
||||
/// A set of attribute values to be added for each vertex
|
||||
void setVertexAttributes(const VertexAttributeArray& value);
|
||||
void setVertexAttributes(VertexAttributeArray&&);
|
||||
void setVertexAttributes(VertexAttributeArrayPtr attrs) { vertexAttrs = std::move(attrs); }
|
||||
|
||||
/// Add some vertex elements, returns the index of the first one added
|
||||
std::size_t addVertices(const std::vector<std::array<int16_t, 2>>& vertices,
|
||||
@@ -232,6 +232,7 @@ protected:
|
||||
std::vector<UniqueDrawable> drawables;
|
||||
gfx::Drawable::Textures textures;
|
||||
std::vector<DrawableTweakerPtr> tweakers;
|
||||
gfx::VertexAttributeArrayPtr vertexAttrs;
|
||||
|
||||
class Impl;
|
||||
std::unique_ptr<Impl> impl;
|
||||
|
||||
@@ -366,23 +366,11 @@ public:
|
||||
}
|
||||
|
||||
VertexAttributeArray& operator=(VertexAttributeArray&&);
|
||||
VertexAttributeArray& operator=(const VertexAttributeArray&);
|
||||
VertexAttributeArray& operator=(const VertexAttributeArray&) = delete;
|
||||
|
||||
/// Clone the collection
|
||||
virtual UniqueVertexAttributeArray clone() const {
|
||||
auto newAttrs = std::make_unique<VertexAttributeArray>();
|
||||
newAttrs->copy(*this);
|
||||
return newAttrs;
|
||||
}
|
||||
|
||||
/// Copy another collection into this one
|
||||
virtual void copy(const VertexAttributeArray& other) {
|
||||
for (const auto& kv : other.attrs) {
|
||||
if (kv.second) {
|
||||
attrs.insert(std::make_pair(kv.first, copy(*kv.second)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Specialized DataDrivenPaintProperty reader
|
||||
/// @param binders Property binders for the target shader
|
||||
|
||||
@@ -41,12 +41,6 @@ public:
|
||||
|
||||
void setVertices(std::vector<uint8_t>&&, std::size_t, gfx::AttributeDataType) override;
|
||||
|
||||
const gfx::VertexAttributeArray& getVertexAttributes() const override;
|
||||
void setVertexAttributes(const gfx::VertexAttributeArray& value) override;
|
||||
void setVertexAttributes(gfx::VertexAttributeArray&& value) override;
|
||||
|
||||
gfx::VertexAttributeArray& mutableVertexAttributes() override;
|
||||
|
||||
const gfx::UniformBufferArray& getUniformBuffers() const override;
|
||||
gfx::UniformBufferArray& mutableUniformBuffers() override;
|
||||
|
||||
|
||||
@@ -61,16 +61,7 @@ public:
|
||||
VertexAttributeArray::operator=(std::move(other));
|
||||
return *this;
|
||||
}
|
||||
VertexAttributeArrayGL& operator=(const VertexAttributeArrayGL& other) {
|
||||
VertexAttributeArray::operator=(other);
|
||||
return *this;
|
||||
}
|
||||
|
||||
std::unique_ptr<VertexAttributeArray> clone() const override {
|
||||
auto newAttrs = std::make_unique<VertexAttributeArrayGL>();
|
||||
newAttrs->copy(*this);
|
||||
return newAttrs;
|
||||
}
|
||||
VertexAttributeArrayGL& operator=(const VertexAttributeArrayGL&) = delete;
|
||||
|
||||
/// Indicates whether any values have changed
|
||||
bool isDirty() const override;
|
||||
|
||||
@@ -22,6 +22,11 @@ namespace mbgl {
|
||||
class ProgramParameters;
|
||||
class RenderStaticData;
|
||||
|
||||
namespace gfx {
|
||||
class VertexAttributeArray;
|
||||
using VertexAttributeArrayPtr = std::shared_ptr<VertexAttributeArray>;
|
||||
} // namespace gfx
|
||||
|
||||
namespace shaders {
|
||||
struct ClipUBO;
|
||||
} // namespace shaders
|
||||
@@ -85,8 +90,6 @@ public:
|
||||
|
||||
RenderTargetPtr createRenderTarget(const Size size, const gfx::TextureChannelDataType type) override;
|
||||
|
||||
// UniqueFramebuffer createFramebuffer(const gfx::Texture2D& color);
|
||||
|
||||
void resetState(gfx::DepthMode depthMode, gfx::ColorMode colorMode) override;
|
||||
|
||||
void setDirtyState() override;
|
||||
@@ -104,6 +107,8 @@ public:
|
||||
|
||||
std::unique_ptr<gfx::DrawScopeResource> createDrawScopeResource() override;
|
||||
|
||||
gfx::VertexAttributeArrayPtr createVertexAttributeArray() const override;
|
||||
|
||||
#if !defined(NDEBUG)
|
||||
void visualizeStencilBuffer() override;
|
||||
void visualizeDepthBuffer(float depthRangeSize) override;
|
||||
|
||||
@@ -40,12 +40,6 @@ public:
|
||||
|
||||
void setVertices(std::vector<uint8_t>&&, std::size_t, gfx::AttributeDataType) override;
|
||||
|
||||
const gfx::VertexAttributeArray& getVertexAttributes() const override;
|
||||
void setVertexAttributes(const gfx::VertexAttributeArray& value) override;
|
||||
void setVertexAttributes(gfx::VertexAttributeArray&& value) override;
|
||||
|
||||
gfx::VertexAttributeArray& mutableVertexAttributes() override;
|
||||
|
||||
const gfx::UniformBufferArray& getUniformBuffers() const override;
|
||||
gfx::UniformBufferArray& mutableUniformBuffers() override;
|
||||
|
||||
|
||||
@@ -18,17 +18,13 @@ private:
|
||||
friend VertexAttributeArray;
|
||||
VertexAttribute(int index_, gfx::AttributeDataType dataType_, std::size_t count_)
|
||||
: gfx::VertexAttribute(index_, dataType_, count_) {}
|
||||
VertexAttribute(const VertexAttribute& other)
|
||||
: gfx::VertexAttribute(other) {}
|
||||
VertexAttribute(const VertexAttribute& other) = delete;
|
||||
VertexAttribute(VertexAttribute&& other)
|
||||
: gfx::VertexAttribute(std::move(other)) {}
|
||||
|
||||
public:
|
||||
~VertexAttribute() override = default;
|
||||
|
||||
/// Get the Metal buffer, creating it if necessary
|
||||
// const gfx::UniqueVertexBufferResource& getBuffer(UploadPass&, const gfx::BufferUsageType);
|
||||
|
||||
static const gfx::UniqueVertexBufferResource& getBuffer(gfx::VertexAttribute&,
|
||||
UploadPass&,
|
||||
const gfx::BufferUsageType);
|
||||
@@ -45,16 +41,7 @@ public:
|
||||
gfx::VertexAttributeArray::operator=(std::move(other));
|
||||
return *this;
|
||||
}
|
||||
VertexAttributeArray& operator=(const VertexAttributeArray& other) {
|
||||
gfx::VertexAttributeArray::operator=(other);
|
||||
return *this;
|
||||
}
|
||||
|
||||
gfx::UniqueVertexAttributeArray clone() const override {
|
||||
auto newAttrs = std::make_unique<VertexAttributeArray>();
|
||||
newAttrs->copy(*this);
|
||||
return newAttrs;
|
||||
}
|
||||
VertexAttributeArray& operator=(const VertexAttributeArray& other) = delete;
|
||||
|
||||
/// Indicates whether any values have changed
|
||||
bool isDirty() const override;
|
||||
@@ -63,12 +50,6 @@ private:
|
||||
gfx::UniqueVertexAttribute create(int index, gfx::AttributeDataType dataType, std::size_t count) const override {
|
||||
return gfx::UniqueVertexAttribute(new VertexAttribute(index, dataType, count));
|
||||
}
|
||||
|
||||
using gfx::VertexAttributeArray::copy;
|
||||
|
||||
gfx::UniqueVertexAttribute copy(const gfx::VertexAttribute& attr) const override {
|
||||
return gfx::UniqueVertexAttribute(new VertexAttribute(static_cast<const VertexAttribute&>(attr)));
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace mtl
|
||||
|
||||
@@ -48,8 +48,6 @@ public:
|
||||
protected:
|
||||
gfx::UniformBlockArray& mutableUniformBlocks() override { return uniformBlocks; }
|
||||
|
||||
gfx::VertexAttributeArray& mutableVertexAttributes() override { return vertexAttributes; }
|
||||
|
||||
protected:
|
||||
UniqueProgram glProgram;
|
||||
|
||||
|
||||
@@ -62,7 +62,6 @@ public:
|
||||
std::optional<uint32_t> getSamplerLocation(const StringIdentity id) const override;
|
||||
|
||||
const gfx::VertexAttributeArray& getVertexAttributes() const override { return vertexAttributes; }
|
||||
gfx::VertexAttributeArray& mutableVertexAttributes() override { return vertexAttributes; }
|
||||
|
||||
const gfx::UniformBlockArray& getUniformBlocks() const override { return uniformBlocks; }
|
||||
gfx::UniformBlockArray& mutableUniformBlocks() override { return uniformBlocks; }
|
||||
|
||||
@@ -41,14 +41,8 @@ public:
|
||||
/// Get the available vertex attributes and their default values
|
||||
virtual const gfx::VertexAttributeArray& getVertexAttributes() const = 0;
|
||||
|
||||
template <typename T>
|
||||
bool setAttribute(const std::string& name, std::size_t i, T value) {
|
||||
return set(mutableVertexAttributes(), name, i, value);
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual gfx::UniformBlockArray& mutableUniformBlocks() = 0;
|
||||
virtual gfx::VertexAttributeArray& mutableVertexAttributes() = 0;
|
||||
|
||||
protected:
|
||||
util::SimpleIdentity shaderProgramID;
|
||||
|
||||
@@ -40,12 +40,14 @@ class Drawable;
|
||||
class DrawableBuilder;
|
||||
class ShaderProgramBase;
|
||||
class Texture2D;
|
||||
class VertexAttributeArray;
|
||||
|
||||
using DrawablePtr = std::shared_ptr<Drawable>;
|
||||
using UniqueDrawableBuilder = std::unique_ptr<DrawableBuilder>;
|
||||
using UniformBufferPtr = std::shared_ptr<UniformBuffer>;
|
||||
using ShaderProgramBasePtr = std::shared_ptr<ShaderProgramBase>;
|
||||
using Texture2DPtr = std::shared_ptr<Texture2D>;
|
||||
using UniformBufferPtr = std::shared_ptr<UniformBuffer>;
|
||||
using UniqueDrawableBuilder = std::unique_ptr<DrawableBuilder>;
|
||||
using VertexAttributeArrayPtr = std::shared_ptr<VertexAttributeArray>;
|
||||
#endif
|
||||
|
||||
class Context {
|
||||
@@ -57,24 +59,20 @@ public:
|
||||
static constexpr const uint32_t minimumRequiredVertexBindingCount = 8;
|
||||
const uint32_t maximumVertexBindingCount;
|
||||
|
||||
public:
|
||||
Context(Context&&) = delete;
|
||||
Context(const Context&) = delete;
|
||||
Context& operator=(Context&& other) = delete;
|
||||
Context& operator=(const Context& other) = delete;
|
||||
virtual ~Context() = default;
|
||||
|
||||
public:
|
||||
/// Called at the end of a frame.
|
||||
virtual void performCleanup() = 0;
|
||||
|
||||
/// Called when the app receives a memory warning and before it goes to the background.
|
||||
virtual void reduceMemoryUsage() = 0;
|
||||
|
||||
public:
|
||||
virtual std::unique_ptr<OffscreenTexture> createOffscreenTexture(Size, TextureChannelDataType) = 0;
|
||||
|
||||
public:
|
||||
/// Creates an empty texture with the specified dimensions.
|
||||
Texture createTexture(const Size size,
|
||||
TexturePixelType format = TexturePixelType::RGBA,
|
||||
@@ -82,32 +80,19 @@ public:
|
||||
return {size, createTextureResource(size, format, type)};
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual std::unique_ptr<TextureResource> createTextureResource(Size, TexturePixelType, TextureChannelDataType) = 0;
|
||||
|
||||
public:
|
||||
template <RenderbufferPixelType pixelType>
|
||||
Renderbuffer<pixelType> createRenderbuffer(const Size size) {
|
||||
return {size, createRenderbufferResource(pixelType, size)};
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual std::unique_ptr<RenderbufferResource> createRenderbufferResource(RenderbufferPixelType, Size) = 0;
|
||||
|
||||
public:
|
||||
DrawScope createDrawScope() { return DrawScope{createDrawScopeResource()}; }
|
||||
|
||||
protected:
|
||||
virtual std::unique_ptr<DrawScopeResource> createDrawScopeResource() = 0;
|
||||
|
||||
public:
|
||||
virtual std::unique_ptr<CommandEncoder> createCommandEncoder() = 0;
|
||||
|
||||
gfx::RenderingStats& renderingStats() { return stats; }
|
||||
const gfx::RenderingStats& renderingStats() const { return stats; }
|
||||
|
||||
#if !defined(NDEBUG)
|
||||
public:
|
||||
virtual void visualizeStencilBuffer() = 0;
|
||||
virtual void visualizeDepthBuffer(float depthRangeSize) = 0;
|
||||
#endif
|
||||
@@ -118,7 +103,9 @@ public:
|
||||
virtual void setDirtyState() = 0;
|
||||
|
||||
#if MLN_DRAWABLE_RENDERER
|
||||
public:
|
||||
/// Create a new vertex attribute array
|
||||
virtual gfx::VertexAttributeArrayPtr createVertexAttributeArray() const = 0;
|
||||
|
||||
/// Create a new drawable builder
|
||||
virtual UniqueDrawableBuilder createDrawableBuilder(std::string name) = 0;
|
||||
|
||||
@@ -166,6 +153,10 @@ public:
|
||||
#endif
|
||||
|
||||
protected:
|
||||
virtual std::unique_ptr<TextureResource> createTextureResource(Size, TexturePixelType, TextureChannelDataType) = 0;
|
||||
virtual std::unique_ptr<RenderbufferResource> createRenderbufferResource(RenderbufferPixelType, Size) = 0;
|
||||
virtual std::unique_ptr<DrawScopeResource> createDrawScopeResource() = 0;
|
||||
|
||||
gfx::RenderingStats stats;
|
||||
};
|
||||
|
||||
|
||||
@@ -33,10 +33,6 @@ void DrawableBuilder::setCullFaceMode(const gfx::CullFaceMode& value) {
|
||||
impl->cullFaceMode = value;
|
||||
}
|
||||
|
||||
const gfx::VertexAttributeArray& DrawableBuilder::getVertexAttributes() const {
|
||||
return impl->vertexAttrs;
|
||||
}
|
||||
|
||||
UniqueDrawable& DrawableBuilder::getCurrentDrawable(bool createIfNone) {
|
||||
if (!currentDrawable && createIfNone) {
|
||||
currentDrawable = createDrawable();
|
||||
@@ -44,11 +40,11 @@ UniqueDrawable& DrawableBuilder::getCurrentDrawable(bool createIfNone) {
|
||||
return currentDrawable;
|
||||
}
|
||||
|
||||
void DrawableBuilder::flush() {
|
||||
void DrawableBuilder::flush(gfx::Context& context) {
|
||||
if (curVertexCount()) {
|
||||
if (Impl::Mode::Polylines == impl->getMode()) {
|
||||
// setup for polylines
|
||||
impl->setupForPolylines(*this);
|
||||
impl->setupForPolylines(context, *this);
|
||||
}
|
||||
|
||||
const auto& draw = getCurrentDrawable(/*createIfNone=*/true);
|
||||
@@ -68,9 +64,10 @@ void DrawableBuilder::flush() {
|
||||
draw->setTextures(textures);
|
||||
draw->setTweakers(tweakers);
|
||||
|
||||
const auto& builderAttrs = getVertexAttributes();
|
||||
if (auto drawAttrs = builderAttrs.clone()) {
|
||||
draw->setVertexAttributes(std::move(*drawAttrs));
|
||||
if (vertexAttrs) {
|
||||
draw->setVertexAttributes(vertexAttrs);
|
||||
} else {
|
||||
draw->setVertexAttributes(context.createVertexAttributeArray());
|
||||
}
|
||||
|
||||
init();
|
||||
@@ -151,14 +148,6 @@ void DrawableBuilder::addQuad(int16_t x0, int16_t y0, int16_t x1, int16_t y1) {
|
||||
appendTriangle(x1, y1);
|
||||
}
|
||||
|
||||
void DrawableBuilder::setVertexAttributes(const VertexAttributeArray& attrs) {
|
||||
impl->vertexAttrs = attrs;
|
||||
}
|
||||
|
||||
void DrawableBuilder::setVertexAttributes(VertexAttributeArray&& attrs) {
|
||||
impl->vertexAttrs = std::move(attrs);
|
||||
}
|
||||
|
||||
std::size_t DrawableBuilder::addVertices(const std::vector<std::array<int16_t, 2>>& vertices,
|
||||
std::size_t vertexOffset,
|
||||
std::size_t vertexLength) {
|
||||
|
||||
@@ -59,7 +59,7 @@ void DrawableBuilder::Impl::addPolyline(gfx::DrawableBuilder& builder,
|
||||
generator.generate(coordinates, options);
|
||||
}
|
||||
|
||||
void DrawableBuilder::Impl::setupForPolylines(gfx::DrawableBuilder& builder) {
|
||||
void DrawableBuilder::Impl::setupForPolylines(gfx::Context& context, gfx::DrawableBuilder& builder) {
|
||||
// setup vertex attributes
|
||||
static const StringIdentity idVertexAttribName = stringIndexer().get("a_pos_normal");
|
||||
static const StringIdentity idDataAttribName = stringIndexer().get("a_data");
|
||||
@@ -68,11 +68,11 @@ void DrawableBuilder::Impl::setupForPolylines(gfx::DrawableBuilder& builder) {
|
||||
|
||||
builder.setRawVertices({}, polylineVertices.elements(), gfx::AttributeDataType::Short2);
|
||||
|
||||
gfx::VertexAttributeArray attrs;
|
||||
auto attrs = context.createVertexAttributeArray();
|
||||
using VertexVector = gfx::VertexVector<LineLayoutVertex>;
|
||||
std::shared_ptr<VertexVector> verts = std::make_shared<VertexVector>(std::move(polylineVertices));
|
||||
|
||||
if (const auto& attr = attrs.add(idVertexAttribName)) {
|
||||
if (const auto& attr = attrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(verts,
|
||||
offsetof(LineLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -80,7 +80,7 @@ void DrawableBuilder::Impl::setupForPolylines(gfx::DrawableBuilder& builder) {
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
|
||||
if (const auto& attr = attrs.add(idDataAttribName)) {
|
||||
if (const auto& attr = attrs->add(idDataAttribName)) {
|
||||
attr->setSharedRawData(verts,
|
||||
offsetof(LineLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
|
||||
@@ -47,13 +47,11 @@ public:
|
||||
gfx::ColorMode colorMode = gfx::ColorMode::disabled();
|
||||
gfx::CullFaceMode cullFaceMode = gfx::CullFaceMode::disabled();
|
||||
|
||||
VertexAttributeArray vertexAttrs;
|
||||
|
||||
void addPolyline(gfx::DrawableBuilder& builder,
|
||||
const GeometryCoordinates& coordinates,
|
||||
const gfx::PolylineGeneratorOptions& options);
|
||||
|
||||
void setupForPolylines(gfx::DrawableBuilder& builder);
|
||||
void setupForPolylines(gfx::Context&, gfx::DrawableBuilder&);
|
||||
|
||||
bool checkAndSetMode(Mode);
|
||||
|
||||
|
||||
@@ -71,6 +71,9 @@ public:
|
||||
void clear() {
|
||||
dirty = true;
|
||||
v.clear();
|
||||
#if MLN_DRAWABLE_RENDERER
|
||||
buffer.reset();
|
||||
#endif // MLN_DRAWABLE_RENDERER
|
||||
}
|
||||
|
||||
/// Indicate that this shared index vector will no longer be updated.
|
||||
|
||||
@@ -93,16 +93,6 @@ VertexAttributeArray& VertexAttributeArray::operator=(VertexAttributeArray&& oth
|
||||
return *this;
|
||||
}
|
||||
|
||||
VertexAttributeArray& VertexAttributeArray::operator=(const VertexAttributeArray& other) {
|
||||
attrs.clear();
|
||||
for (const auto& kv : other.attrs) {
|
||||
if (kv.second) {
|
||||
add(kv.first, copy(*kv.second));
|
||||
}
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
const std::unique_ptr<VertexAttribute>& VertexAttributeArray::get(const StringIdentity id) const {
|
||||
const auto result = attrs.find(id);
|
||||
return (result != attrs.end()) ? result->second : nullref;
|
||||
|
||||
@@ -532,6 +532,11 @@ Framebuffer Context::createFramebuffer(const gfx::Texture2D& color) {
|
||||
checkFramebuffer();
|
||||
return {color.getSize(), std::move(fbo)};
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArrayPtr Context::createVertexAttributeArray() const {
|
||||
return std::make_shared<VertexAttributeArrayGL>();
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
void Context::clear(std::optional<mbgl::Color> color, std::optional<float> depth, std::optional<int32_t> stencil) {
|
||||
|
||||
@@ -117,6 +117,8 @@ public:
|
||||
|
||||
Framebuffer createFramebuffer(const gfx::Texture2D& color);
|
||||
|
||||
gfx::VertexAttributeArrayPtr createVertexAttributeArray() const override;
|
||||
|
||||
void resetState(gfx::DepthMode depthMode, gfx::ColorMode colorMode) override;
|
||||
|
||||
bool emplaceOrUpdateUniformBuffer(gfx::UniformBufferPtr&,
|
||||
|
||||
@@ -88,21 +88,6 @@ void DrawableGL::setVertices(std::vector<uint8_t>&& data, std::size_t count, gfx
|
||||
impl->vertexType = type_;
|
||||
}
|
||||
|
||||
const gfx::VertexAttributeArray& DrawableGL::getVertexAttributes() const {
|
||||
return impl->vertexAttributes;
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArray& DrawableGL::mutableVertexAttributes() {
|
||||
return impl->vertexAttributes;
|
||||
}
|
||||
|
||||
void DrawableGL::setVertexAttributes(const gfx::VertexAttributeArray& value) {
|
||||
impl->vertexAttributes = static_cast<const VertexAttributeArrayGL&>(value);
|
||||
}
|
||||
void DrawableGL::setVertexAttributes(gfx::VertexAttributeArray&& value) {
|
||||
impl->vertexAttributes = std::move(static_cast<VertexAttributeArrayGL&&>(value));
|
||||
}
|
||||
|
||||
const gfx::UniformBufferArray& DrawableGL::getUniformBuffers() const {
|
||||
return impl->uniformBuffers;
|
||||
}
|
||||
@@ -157,10 +142,11 @@ void DrawableGL::upload(gfx::UploadPass& uploadPass) {
|
||||
return;
|
||||
}
|
||||
|
||||
const bool build = impl->vertexAttributes.isDirty() ||
|
||||
std::any_of(impl->segments.begin(), impl->segments.end(), [](const auto& seg) {
|
||||
return !static_cast<const DrawSegmentGL&>(*seg).getVertexArray().isValid();
|
||||
});
|
||||
const bool build = vertexAttributes &&
|
||||
(vertexAttributes->isDirty() ||
|
||||
std::any_of(impl->segments.begin(), impl->segments.end(), [](const auto& seg) {
|
||||
return !static_cast<const DrawSegmentGL&>(*seg).getVertexArray().isValid();
|
||||
}));
|
||||
|
||||
if (build) {
|
||||
auto& context = uploadPass.getContext();
|
||||
@@ -169,7 +155,7 @@ void DrawableGL::upload(gfx::UploadPass& uploadPass) {
|
||||
|
||||
// Apply drawable values to shader defaults
|
||||
const auto& defaults = shader->getVertexAttributes();
|
||||
const auto& overrides = impl->vertexAttributes;
|
||||
const auto& overrides = *vertexAttributes;
|
||||
|
||||
const auto& indexAttribute = defaults.get(impl->idVertexAttrName);
|
||||
const auto vertexAttributeIndex = static_cast<std::size_t>(indexAttribute ? indexAttribute->getIndex() : -1);
|
||||
|
||||
@@ -39,8 +39,6 @@ public:
|
||||
std::size_t vertexCount = 0;
|
||||
gfx::AttributeDataType vertexType = static_cast<gfx::AttributeDataType>(-1);
|
||||
|
||||
VertexAttributeArrayGL vertexAttributes;
|
||||
|
||||
gfx::IndexBuffer indexBuffer = {0, nullptr};
|
||||
std::vector<gfx::UniqueVertexBufferResource> attributeBuffers;
|
||||
|
||||
|
||||
@@ -444,6 +444,10 @@ std::unique_ptr<gfx::DrawScopeResource> Context::createDrawScopeResource() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArrayPtr Context::createVertexAttributeArray() const {
|
||||
return std::make_shared<VertexAttributeArray>();
|
||||
}
|
||||
|
||||
#if !defined(NDEBUG)
|
||||
void Context::visualizeStencilBuffer() {}
|
||||
|
||||
|
||||
@@ -306,7 +306,10 @@ void Drawable::setVertices(std::vector<uint8_t>&& data, std::size_t count, gfx::
|
||||
impl->vertexType = type;
|
||||
|
||||
if (count && type != gfx::AttributeDataType::Invalid && !data.empty()) {
|
||||
if (auto& attrib = impl->vertexAttributes.getOrAdd(impl->idVertexAttrName, /*index=*/-1, type)) {
|
||||
if (!vertexAttributes) {
|
||||
vertexAttributes = std::make_shared<VertexAttributeArray>();
|
||||
}
|
||||
if (auto& attrib = vertexAttributes->getOrAdd(impl->idVertexAttrName, /*index=*/-1, type)) {
|
||||
attrib->setRawData(std::move(data));
|
||||
attrib->setStride(VertexAttribute::getStrideOf(type));
|
||||
} else {
|
||||
@@ -319,21 +322,6 @@ void Drawable::setVertices(std::vector<uint8_t>&& data, std::size_t count, gfx::
|
||||
}
|
||||
}
|
||||
|
||||
const gfx::VertexAttributeArray& Drawable::getVertexAttributes() const {
|
||||
return impl->vertexAttributes;
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArray& Drawable::mutableVertexAttributes() {
|
||||
return impl->vertexAttributes;
|
||||
}
|
||||
|
||||
void Drawable::setVertexAttributes(const gfx::VertexAttributeArray& value) {
|
||||
impl->vertexAttributes = static_cast<const VertexAttributeArray&>(value);
|
||||
}
|
||||
void Drawable::setVertexAttributes(gfx::VertexAttributeArray&& value) {
|
||||
impl->vertexAttributes = std::move(static_cast<VertexAttributeArray&&>(value));
|
||||
}
|
||||
|
||||
const gfx::UniformBufferArray& Drawable::getUniformBuffers() const {
|
||||
return impl->uniformBuffers;
|
||||
}
|
||||
@@ -513,13 +501,17 @@ void Drawable::upload(gfx::UploadPass& uploadPass_) {
|
||||
impl->indexes->setDirty(false);
|
||||
}
|
||||
|
||||
const bool buildAttribs = impl->vertexAttributes.isDirty() || !impl->vertexDesc;
|
||||
const bool buildAttribs = !vertexAttributes || vertexAttributes->isDirty() || !impl->vertexDesc;
|
||||
|
||||
if (buildAttribs) {
|
||||
#if !defined(NDEBUG)
|
||||
const auto debugGroup = uploadPass.createDebugGroup(debugLabel(*this));
|
||||
#endif
|
||||
|
||||
if (!vertexAttributes) {
|
||||
vertexAttributes = std::make_shared<VertexAttributeArray>();
|
||||
}
|
||||
|
||||
// Apply drawable values to shader defaults
|
||||
std::vector<std::unique_ptr<gfx::VertexBufferResource>> vertexBuffers;
|
||||
auto attributeBindings_ = uploadPass.buildAttributeBindings(impl->vertexCount,
|
||||
@@ -527,13 +519,12 @@ void Drawable::upload(gfx::UploadPass& uploadPass_) {
|
||||
/*vertexAttributeIndex=*/-1,
|
||||
/*vertexData=*/{},
|
||||
shader->getVertexAttributes(),
|
||||
impl->vertexAttributes,
|
||||
*vertexAttributes,
|
||||
usage,
|
||||
vertexBuffers);
|
||||
impl->attributeBuffers = std::move(vertexBuffers);
|
||||
|
||||
impl->vertexAttributes.visitAttributes(
|
||||
[](const auto&, gfx::VertexAttribute& attrib) { attrib.setDirty(false); });
|
||||
vertexAttributes->visitAttributes([](const auto&, gfx::VertexAttribute& attrib) { attrib.setDirty(false); });
|
||||
|
||||
if (impl->attributeBindings != attributeBindings_) {
|
||||
impl->attributeBindings = std::move(attributeBindings_);
|
||||
|
||||
@@ -44,7 +44,6 @@ public:
|
||||
gfx::IndexVectorBasePtr indexes;
|
||||
std::size_t vertexCount = 0;
|
||||
gfx::AttributeDataType vertexType = gfx::AttributeDataType::Invalid;
|
||||
VertexAttributeArray vertexAttributes;
|
||||
|
||||
std::vector<gfx::UniqueVertexBufferResource> attributeBuffers;
|
||||
|
||||
|
||||
@@ -314,7 +314,7 @@ void RenderBackgroundLayer::update(gfx::ShaderRegistry& shaders,
|
||||
auto verticesCopy = rawVertices;
|
||||
builder->setRawVertices(std::move(verticesCopy), vertexCount, gfx::AttributeDataType::Short2);
|
||||
builder->setSegments(gfx::Triangles(), indexes.vector(), segs.data(), segs.size());
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -380,14 +380,14 @@ void RenderCircleLayer::update(gfx::ShaderRegistry& shaders,
|
||||
const auto interpBuffer = context.createUniformBuffer(&interpolateUBO, sizeof(interpolateUBO));
|
||||
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray circleVertexAttrs;
|
||||
circleVertexAttrs.readDataDrivenPaintProperties<CircleColor,
|
||||
CircleRadius,
|
||||
CircleBlur,
|
||||
CircleOpacity,
|
||||
CircleStrokeColor,
|
||||
CircleStrokeWidth,
|
||||
CircleStrokeOpacity>(
|
||||
auto circleVertexAttrs = context.createVertexAttributeArray();
|
||||
circleVertexAttrs->readDataDrivenPaintProperties<CircleColor,
|
||||
CircleRadius,
|
||||
CircleBlur,
|
||||
CircleOpacity,
|
||||
CircleStrokeColor,
|
||||
CircleStrokeWidth,
|
||||
CircleStrokeOpacity>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
if (!circleShaderGroup) {
|
||||
@@ -402,7 +402,7 @@ void RenderCircleLayer::update(gfx::ShaderRegistry& shaders,
|
||||
layerTweaker->setPropertiesAsUniforms(propertiesAsUniforms);
|
||||
}
|
||||
|
||||
if (const auto& attr = circleVertexAttrs.add(idVertexAttribName)) {
|
||||
if (const auto& attr = circleVertexAttrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(CircleLayoutVertex, a1),
|
||||
0,
|
||||
@@ -423,7 +423,7 @@ void RenderCircleLayer::update(gfx::ShaderRegistry& shaders,
|
||||
circleBuilder->setSegments(
|
||||
gfx::Triangles(), bucket.sharedTriangles, bucket.segments.data(), bucket.segments.size());
|
||||
|
||||
circleBuilder->flush();
|
||||
circleBuilder->flush(context);
|
||||
|
||||
for (auto& drawable : circleBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -419,12 +419,13 @@ void RenderFillExtrusionLayer::update(gfx::ShaderRegistry& shaders,
|
||||
continue;
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
propertiesAsUniforms.clear();
|
||||
vertexAttrs.readDataDrivenPaintProperties<FillExtrusionBase,
|
||||
FillExtrusionColor,
|
||||
FillExtrusionHeight,
|
||||
FillExtrusionPattern>(binders, evaluated, propertiesAsUniforms);
|
||||
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs->readDataDrivenPaintProperties<FillExtrusionBase,
|
||||
FillExtrusionColor,
|
||||
FillExtrusionHeight,
|
||||
FillExtrusionPattern>(binders, evaluated, propertiesAsUniforms);
|
||||
|
||||
const auto shader = std::static_pointer_cast<gfx::ShaderProgramBase>(
|
||||
shaderGroup->getOrCreateShader(context, propertiesAsUniforms));
|
||||
@@ -487,14 +488,14 @@ void RenderFillExtrusionLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
}
|
||||
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idPosAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idPosAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(FillExtrusionLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(FillExtrusionLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idNormAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idNormAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(FillExtrusionLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -502,16 +503,13 @@ void RenderFillExtrusionLayer::update(gfx::ShaderRegistry& shaders,
|
||||
gfx::AttributeDataType::Short4);
|
||||
}
|
||||
|
||||
colorBuilder->setEnableStencil(doDepthPass);
|
||||
if (doDepthPass) {
|
||||
depthBuilder->setRawVertices({}, vertexCount, gfx::AttributeDataType::Short2);
|
||||
depthBuilder->setVertexAttributes(vertexAttrs);
|
||||
}
|
||||
colorBuilder->setRawVertices({}, vertexCount, gfx::AttributeDataType::Short2);
|
||||
|
||||
if (doDepthPass) {
|
||||
auto copy = vertexAttrs.clone();
|
||||
depthBuilder->setVertexAttributes(std::move(*copy));
|
||||
}
|
||||
colorBuilder->setEnableStencil(doDepthPass);
|
||||
colorBuilder->setRawVertices({}, vertexCount, gfx::AttributeDataType::Short2);
|
||||
colorBuilder->setVertexAttributes(std::move(vertexAttrs));
|
||||
|
||||
const auto finish = [&](gfx::DrawableBuilder& builder) {
|
||||
@@ -523,7 +521,7 @@ void RenderFillExtrusionLayer::update(gfx::ShaderRegistry& shaders,
|
||||
bucket.triangleSegments.data(),
|
||||
bucket.triangleSegments.size());
|
||||
|
||||
builder.flush();
|
||||
builder.flush(context);
|
||||
|
||||
for (auto& drawable : builder.clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -620,10 +620,11 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
return atlasTweaker;
|
||||
};
|
||||
|
||||
// `Fill*Program` all use `style::FillPaintProperties`
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
propertiesAsUniforms.clear();
|
||||
vertexAttrs.readDataDrivenPaintProperties<FillColor, FillOpacity, FillOutlineColor, FillPattern>(
|
||||
|
||||
// `Fill*Program` all use `style::FillPaintProperties`
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs->readDataDrivenPaintProperties<FillColor, FillOpacity, FillOutlineColor, FillPattern>(
|
||||
binders, evaluated, propertiesAsUniforms);
|
||||
|
||||
if (layerTweaker) {
|
||||
@@ -631,7 +632,7 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
|
||||
const auto vertexCount = bucket.vertices.elements();
|
||||
if (const auto& attr = vertexAttrs.add(idPosAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idPosAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(FillLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -715,15 +716,16 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
builder->setVertexAttrNameId(idVertexAttribName);
|
||||
builder->setShader(outlineTriangulatedShader);
|
||||
builder->setRawVertices({}, bucket.lineVertices.elements(), gfx::AttributeDataType::Short2);
|
||||
gfx::VertexAttributeArray attrs;
|
||||
if (const auto& attr = attrs.add(idVertexAttribName)) {
|
||||
|
||||
auto attrs = context.createVertexAttributeArray();
|
||||
if (const auto& attr = attrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedLineVertices,
|
||||
offsetof(LineLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(LineLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = attrs.add(idDataAttribName)) {
|
||||
if (const auto& attr = attrs->add(idDataAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedLineVertices,
|
||||
offsetof(LineLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -731,6 +733,7 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
gfx::AttributeDataType::UByte4);
|
||||
}
|
||||
builder->setVertexAttributes(std::move(attrs));
|
||||
|
||||
builder->setSegments(gfx::Triangles(),
|
||||
bucket.sharedLineIndexes,
|
||||
bucket.lineSegments.data(),
|
||||
@@ -739,7 +742,7 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
auto tweaker = std::make_shared<OutlineDrawableTweaker>(color, opacity);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
drawable->addTweaker(tweaker);
|
||||
@@ -785,7 +788,7 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
const auto& interpolateUBO,
|
||||
FillVariant type) {
|
||||
builder.setVertexAttrNameId(idPosAttribName);
|
||||
builder.flush();
|
||||
builder.flush(context);
|
||||
|
||||
for (auto& drawable : builder.clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
@@ -919,7 +922,7 @@ void RenderFillLayer::update(gfx::ShaderRegistry& shaders,
|
||||
const StringIdentity tileUBONameId,
|
||||
const auto& tileUBO,
|
||||
FillVariant type) {
|
||||
builder.flush();
|
||||
builder.flush(context);
|
||||
|
||||
for (auto& drawable : builder.clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -72,7 +72,6 @@ void RenderHeatmapLayer::evaluate(const PropertyEvaluationParameters& parameters
|
||||
if (auto tileLayerGroup = renderTarget->getLayerGroup(0)) {
|
||||
auto newTweaker = std::make_shared<HeatmapLayerTweaker>(getID(), evaluatedProperties);
|
||||
|
||||
// propertiesAsUniforms isn't recalculated every update, so carry it over
|
||||
if (layerTweaker) {
|
||||
newTweaker->setPropertiesAsUniforms(layerTweaker->getPropertiesAsUniforms());
|
||||
}
|
||||
@@ -352,7 +351,12 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
[&](gfx::Drawable& drawable) { return drawable.getTileID() && !hasRenderTile(*drawable.getTileID()); });
|
||||
|
||||
const auto& evaluated = static_cast<const HeatmapLayerProperties&>(*evaluatedProperties).evaluated;
|
||||
mbgl::unordered_set<StringIdentity> propertiesAsUniforms;
|
||||
std::optional<mbgl::unordered_set<StringIdentity>> propertiesAsUniforms;
|
||||
#if !defined(NDEBUG)
|
||||
std::optional<mbgl::unordered_set<StringIdentity>> previousPropertiesAsUniforms;
|
||||
#endif
|
||||
|
||||
gfx::ShaderPtr heatmapShader;
|
||||
|
||||
for (const RenderTile& tile : *renderTiles) {
|
||||
const auto& tileID = tile.getOverscaledTileID();
|
||||
@@ -388,15 +392,6 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
return interpolateBuffer;
|
||||
};
|
||||
|
||||
gfx::VertexAttributeArray heatmapVertexAttrs;
|
||||
propertiesAsUniforms.clear();
|
||||
heatmapVertexAttrs.readDataDrivenPaintProperties<HeatmapWeight, HeatmapRadius>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
if (layerTweaker) {
|
||||
layerTweaker->setPropertiesAsUniforms(propertiesAsUniforms);
|
||||
}
|
||||
|
||||
const auto updatedCount = tileLayerGroup->visitDrawables(renderPass, tileID, [&](gfx::Drawable& drawable) {
|
||||
if (drawable.getLayerTweaker() != layerTweaker) {
|
||||
// This drawable was produced on a previous style/bucket, and should not be updated.
|
||||
@@ -417,12 +412,36 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
continue;
|
||||
}
|
||||
|
||||
const auto heatmapShader = heatmapShaderGroup->getOrCreateShader(context, propertiesAsUniforms);
|
||||
if (!propertiesAsUniforms) {
|
||||
propertiesAsUniforms.emplace();
|
||||
}
|
||||
#if !defined(NDEBUG)
|
||||
else {
|
||||
propertiesAsUniforms->clear();
|
||||
}
|
||||
#endif
|
||||
|
||||
auto heatmapVertexAttrs = context.createVertexAttributeArray();
|
||||
heatmapVertexAttrs->readDataDrivenPaintProperties<HeatmapWeight, HeatmapRadius>(
|
||||
paintPropertyBinders, evaluated, *propertiesAsUniforms);
|
||||
|
||||
#if !defined(NDEBUG)
|
||||
// We assume the properties are the same across tiles.
|
||||
if (previousPropertiesAsUniforms) {
|
||||
assert(*propertiesAsUniforms == previousPropertiesAsUniforms);
|
||||
} else {
|
||||
previousPropertiesAsUniforms = propertiesAsUniforms;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!heatmapShader) {
|
||||
continue;
|
||||
heatmapShader = heatmapShaderGroup->getOrCreateShader(context, *propertiesAsUniforms);
|
||||
if (!heatmapShader) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (const auto& attr = heatmapVertexAttrs.add(idVertexAttribName)) {
|
||||
if (const auto& attr = heatmapVertexAttrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(HeatmapLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -441,7 +460,7 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
heatmapBuilder->setSegments(
|
||||
gfx::Triangles(), bucket.sharedTriangles, bucket.segments.data(), bucket.segments.size());
|
||||
|
||||
heatmapBuilder->flush();
|
||||
heatmapBuilder->flush(context);
|
||||
|
||||
for (auto& drawable : heatmapBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
@@ -458,6 +477,10 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
}
|
||||
|
||||
if (layerTweaker && propertiesAsUniforms) {
|
||||
layerTweaker->setPropertiesAsUniforms(*propertiesAsUniforms);
|
||||
}
|
||||
|
||||
// Set up texture layer group
|
||||
if (!layerGroup) {
|
||||
if (auto layerGroup_ = context.createLayerGroup(layerIndex, /*initialCapacity=*/1, getID())) {
|
||||
@@ -494,8 +517,8 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
const auto textureVertexCount = sharedTextureVertices->elements();
|
||||
|
||||
gfx::VertexAttributeArray textureVertexAttrs;
|
||||
if (const auto& attr = textureVertexAttrs.add(idVertexAttribName)) {
|
||||
auto textureVertexAttrs = context.createVertexAttributeArray();
|
||||
if (const auto& attr = textureVertexAttrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(sharedTextureVertices,
|
||||
offsetof(HeatmapLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -530,7 +553,7 @@ void RenderHeatmapLayer::update(gfx::ShaderRegistry& shaders,
|
||||
heatmapTextureBuilder->setTexture(std::move(texture), colorRampLocation.value());
|
||||
}
|
||||
|
||||
heatmapTextureBuilder->flush();
|
||||
heatmapTextureBuilder->flush(context);
|
||||
|
||||
for (auto& drawable : heatmapTextureBuilder->clearDrawables()) {
|
||||
drawable->setLayerTweaker(textureTweaker);
|
||||
|
||||
@@ -365,6 +365,29 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
std::unique_ptr<gfx::DrawableBuilder> hillshadeBuilder;
|
||||
std::unique_ptr<gfx::DrawableBuilder> hillshadePrepareBuilder;
|
||||
|
||||
gfx::VertexAttributeArrayPtr hillshadePrepareVertexAttrs;
|
||||
const auto getPrepareVertexAttributes = [&] {
|
||||
if (!hillshadePrepareVertexAttrs) {
|
||||
hillshadePrepareVertexAttrs = context.createVertexAttributeArray();
|
||||
|
||||
if (const auto& attr = hillshadePrepareVertexAttrs->add(idPosAttribName)) {
|
||||
attr->setSharedRawData(staticDataSharedVertices,
|
||||
offsetof(HillshadeLayoutVertex, a1),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = hillshadePrepareVertexAttrs->add(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(staticDataSharedVertices,
|
||||
offsetof(HillshadeLayoutVertex, a2),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
}
|
||||
return hillshadePrepareVertexAttrs;
|
||||
};
|
||||
|
||||
for (const RenderTile& tile : *renderTiles) {
|
||||
const auto& tileID = tile.getOverscaledTileID();
|
||||
|
||||
@@ -406,31 +429,13 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
singleTileLayerGroup->addLayerTweaker(prepareLayerTweaker);
|
||||
|
||||
gfx::VertexAttributeArray hillshadePrepareVertexAttrs;
|
||||
|
||||
if (const auto& attr = hillshadePrepareVertexAttrs.add(idPosAttribName)) {
|
||||
attr->setSharedRawData(staticDataSharedVertices,
|
||||
offsetof(HillshadeLayoutVertex, a1),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = hillshadePrepareVertexAttrs.getOrAdd(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(staticDataSharedVertices,
|
||||
offsetof(HillshadeLayoutVertex, a2),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
|
||||
hillshadePrepareBuilder = context.createDrawableBuilder("hillshadePrepare");
|
||||
hillshadePrepareBuilder->setShader(hillshadePrepareShader);
|
||||
hillshadePrepareBuilder->setDepthType(gfx::DepthMaskType::ReadOnly);
|
||||
hillshadePrepareBuilder->setColorMode(gfx::ColorMode::unblended());
|
||||
hillshadePrepareBuilder->setCullFaceMode(gfx::CullFaceMode::disabled());
|
||||
|
||||
hillshadePrepareBuilder->setRenderPass(renderPass);
|
||||
hillshadePrepareBuilder->setVertexAttributes(std::move(hillshadePrepareVertexAttrs));
|
||||
hillshadePrepareBuilder->setVertexAttributes(getPrepareVertexAttributes());
|
||||
hillshadePrepareBuilder->setRawVertices(
|
||||
{}, staticDataSharedVertices->elements(), gfx::AttributeDataType::Short2);
|
||||
hillshadePrepareBuilder->setSegments(
|
||||
@@ -445,7 +450,7 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
hillshadePrepareBuilder->setTexture(texture, imageLocation.value());
|
||||
}
|
||||
|
||||
hillshadePrepareBuilder->flush();
|
||||
hillshadePrepareBuilder->flush(context);
|
||||
|
||||
for (auto& drawable : hillshadePrepareBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
@@ -468,33 +473,39 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
segments = &bucket.segments;
|
||||
}
|
||||
|
||||
gfx::VertexAttributeArray hillshadeVertexAttrs;
|
||||
|
||||
if (const auto& attr = hillshadeVertexAttrs.add(idPosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(HillshadeLayoutVertex, a1),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = hillshadeVertexAttrs.getOrAdd(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(HillshadeLayoutVertex, a2),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
|
||||
hillshadeBuilder = context.createDrawableBuilder("hillshade");
|
||||
|
||||
auto updateExisting = [&](gfx::Drawable& drawable) {
|
||||
gfx::VertexAttributeArrayPtr hillshadeVertexAttrs;
|
||||
auto buildVertexAttributes = [&] {
|
||||
if (!hillshadeVertexAttrs) {
|
||||
hillshadeVertexAttrs = context.createVertexAttributeArray();
|
||||
|
||||
if (const auto& attr = hillshadeVertexAttrs->add(idPosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(HillshadeLayoutVertex, a1),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = hillshadeVertexAttrs->getOrAdd(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(HillshadeLayoutVertex, a2),
|
||||
0,
|
||||
sizeof(HillshadeLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
}
|
||||
return hillshadeVertexAttrs;
|
||||
};
|
||||
|
||||
const auto updateExisting = [&](gfx::Drawable& drawable) {
|
||||
// Only current drawables are updated, ones produced for
|
||||
// a previous style retain the attribute values for that style.
|
||||
if (drawable.getLayerTweaker() != layerTweaker) {
|
||||
return false;
|
||||
}
|
||||
|
||||
drawable.setVertexAttributes(std::move(hillshadeVertexAttrs));
|
||||
drawable.setVertexAttributes(buildVertexAttributes());
|
||||
drawable.setVertices({}, vertices->elements(), gfx::AttributeDataType::Short2);
|
||||
|
||||
// Rebuild segments, since they're not shared.
|
||||
@@ -526,9 +537,8 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
hillshadeBuilder->setDepthType(gfx::DepthMaskType::ReadOnly);
|
||||
hillshadeBuilder->setColorMode(gfx::ColorMode::alphaBlended());
|
||||
hillshadeBuilder->setCullFaceMode(gfx::CullFaceMode::disabled());
|
||||
|
||||
hillshadeBuilder->setRenderPass(renderPass);
|
||||
hillshadeBuilder->setVertexAttributes(std::move(hillshadeVertexAttrs));
|
||||
hillshadeBuilder->setVertexAttributes(buildVertexAttributes());
|
||||
hillshadeBuilder->setRawVertices({}, vertices->elements(), gfx::AttributeDataType::Short2);
|
||||
hillshadeBuilder->setSegments(gfx::Triangles(), indices->vector(), segments->data(), segments->size());
|
||||
|
||||
@@ -536,7 +546,7 @@ void RenderHillshadeLayer::update(gfx::ShaderRegistry& shaders,
|
||||
hillshadeBuilder->setTexture(bucket.renderTarget->getTexture(), *hillshadeImageLocation);
|
||||
}
|
||||
|
||||
hillshadeBuilder->flush();
|
||||
hillshadeBuilder->flush(context);
|
||||
|
||||
for (auto& drawable : hillshadeBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -434,11 +434,11 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
};
|
||||
|
||||
auto addAttributes =
|
||||
[&](gfx::DrawableBuilder& builder, const LineBucket& bucket, gfx::VertexAttributeArray&& vertexAttrs) {
|
||||
[&](gfx::DrawableBuilder& builder, const LineBucket& bucket, gfx::VertexAttributeArrayPtr&& vertexAttrs) {
|
||||
const auto vertexCount = bucket.vertices.elements();
|
||||
builder.setRawVertices({}, vertexCount, gfx::AttributeDataType::Short4);
|
||||
|
||||
if (const auto& attr = vertexAttrs.add(idVertexAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(LineLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -446,7 +446,7 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
|
||||
if (const auto& attr = vertexAttrs.add(idDataAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idDataAttribName)) {
|
||||
attr->setSharedRawData(bucket.sharedVertices,
|
||||
offsetof(LineLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -584,14 +584,14 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
|
||||
// dash array line (SDF)
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
vertexAttrs.readDataDrivenPaintProperties<LineColor,
|
||||
LineBlur,
|
||||
LineOpacity,
|
||||
LineGapWidth,
|
||||
LineOffset,
|
||||
LineWidth,
|
||||
LineFloorWidth>(
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs->readDataDrivenPaintProperties<LineColor,
|
||||
LineBlur,
|
||||
LineOpacity,
|
||||
LineGapWidth,
|
||||
LineOffset,
|
||||
LineWidth,
|
||||
LineFloorWidth>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
auto shader = lineSDFShaderGroup->getOrCreateShader(context, propertiesAsUniforms);
|
||||
@@ -610,7 +610,7 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
setSegments(builder, bucket);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
const LinePatternCap cap = bucket.layout.get<LineCap>() == LineCapType::Round ? LinePatternCap::Round
|
||||
: LinePatternCap::Square;
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
@@ -633,10 +633,14 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
paintPropertyBinders.setPatternParameters(patternPosA, patternPosB, crossfade);
|
||||
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
vertexAttrs
|
||||
.readDataDrivenPaintProperties<LineBlur, LineOpacity, LineOffset, LineGapWidth, LineWidth, LinePattern>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs->readDataDrivenPaintProperties<LineBlur,
|
||||
LineOpacity,
|
||||
LineOffset,
|
||||
LineGapWidth,
|
||||
LineWidth,
|
||||
LinePattern>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
auto shader = linePatternShaderGroup->getOrCreateShader(context, propertiesAsUniforms);
|
||||
if (!shader) {
|
||||
@@ -670,7 +674,7 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
|
||||
setSegments(builder, bucket);
|
||||
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setType(mbgl::underlying_type(LineLayerTweaker::LineType::Pattern));
|
||||
drawable->setTileID(tileID);
|
||||
@@ -691,8 +695,8 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
|
||||
// gradient line
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
vertexAttrs.readDataDrivenPaintProperties<LineBlur, LineOpacity, LineGapWidth, LineOffset, LineWidth>(
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs->readDataDrivenPaintProperties<LineBlur, LineOpacity, LineGapWidth, LineOffset, LineWidth>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
auto shader = lineGradientShaderGroup->getOrCreateShader(context, propertiesAsUniforms);
|
||||
@@ -726,7 +730,7 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
setSegments(builder, bucket);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setType(mbgl::underlying_type(LineLayerTweaker::LineType::Gradient));
|
||||
drawable->setTileID(tileID);
|
||||
@@ -746,9 +750,9 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
|
||||
// simple line
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
vertexAttrs
|
||||
.readDataDrivenPaintProperties<LineColor, LineBlur, LineOpacity, LineGapWidth, LineOffset, LineWidth>(
|
||||
->readDataDrivenPaintProperties<LineColor, LineBlur, LineOpacity, LineGapWidth, LineOffset, LineWidth>(
|
||||
paintPropertyBinders, evaluated, propertiesAsUniforms);
|
||||
|
||||
auto shader = lineShaderGroup->getOrCreateShader(context, propertiesAsUniforms);
|
||||
@@ -767,7 +771,7 @@ void RenderLineLayer::update(gfx::ShaderRegistry& shaders,
|
||||
setSegments(builder, bucket);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setType(mbgl::underlying_type(LineLayerTweaker::LineType::Simple));
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -341,11 +341,19 @@ void RenderRasterLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
};
|
||||
|
||||
gfx::VertexAttributeArrayPtr staticAttrs;
|
||||
|
||||
// Build vertex attributes and apply them to a drawable or a builder.
|
||||
// Populates a drawable xor a drawable builder for creates and updates, respectively.
|
||||
// Returns false if the drawable must be re-created.
|
||||
const auto buildVertexData =
|
||||
[this](const gfx::UniqueDrawableBuilder& builder, gfx::Drawable* drawable, const RasterBucket& bucket) {
|
||||
[&](const gfx::UniqueDrawableBuilder& builder, gfx::Drawable* drawable, const RasterBucket& bucket) {
|
||||
// The bucket may later add, remove, or change masking. In that case, the tile's
|
||||
// shared data and segments are not updated, and it needs to be re-created.
|
||||
if (drawable && (bucket.sharedVertices->getDirty() || bucket.sharedTriangles->getDirty())) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// The bucket only fills in geometry for masked tiles,
|
||||
// otherwise the standard tile extent geometry should be used.
|
||||
const bool shared = (!bucket.sharedVertices->empty() && !bucket.sharedTriangles->empty() &&
|
||||
@@ -354,34 +362,33 @@ void RenderRasterLayer::update(gfx::ShaderRegistry& shaders,
|
||||
const auto& indices = shared ? bucket.sharedTriangles : staticDataIndices;
|
||||
const auto* segments = shared ? &bucket.segments : staticDataSegments.get();
|
||||
|
||||
// The bucket may later add, remove, or change masking. In that case, the tile's
|
||||
// shared data and segments are not updated, and it needs to be re-created.
|
||||
if (drawable && (bucket.sharedVertices->getDirty() || bucket.sharedTriangles->getDirty())) {
|
||||
return false;
|
||||
}
|
||||
gfx::VertexAttributeArrayPtr bucketAttrs;
|
||||
auto& vertexAttrs = shared ? bucketAttrs : staticAttrs;
|
||||
if (!vertexAttrs) {
|
||||
vertexAttrs = context.createVertexAttributeArray();
|
||||
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
if (auto& attr = vertexAttrs.add(idPosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(RasterLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(RasterLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (auto& attr = vertexAttrs->add(idPosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(RasterLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(RasterLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
|
||||
if (auto& attr = vertexAttrs.add(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(RasterLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(RasterLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
if (auto& attr = vertexAttrs->add(idTexturePosAttribName)) {
|
||||
attr->setSharedRawData(vertices,
|
||||
offsetof(RasterLayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(RasterLayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
}
|
||||
|
||||
assert(!!drawable ^ !!builder);
|
||||
if (drawable) {
|
||||
drawable->setVertexAttributes(std::move(vertexAttrs));
|
||||
drawable->setVertexAttributes(vertexAttrs);
|
||||
} else if (builder) {
|
||||
builder->setVertexAttributes(std::move(vertexAttrs));
|
||||
builder->setVertexAttributes(vertexAttrs);
|
||||
builder->setRawVertices({}, vertices->elements(), gfx::AttributeDataType::Short2);
|
||||
builder->setSegments(gfx::Triangles(), indices, segments->data(), segments->size());
|
||||
}
|
||||
@@ -412,7 +419,7 @@ void RenderRasterLayer::update(gfx::ShaderRegistry& shaders,
|
||||
setTextures(builder, bucket);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setData(std::make_unique<gfx::ImageDrawableData>(matrix_));
|
||||
@@ -481,11 +488,11 @@ void RenderRasterLayer::update(gfx::ShaderRegistry& shaders,
|
||||
}
|
||||
return true;
|
||||
};
|
||||
if (updateTile(renderPass, tileID, std::move(updateExisting))) {
|
||||
// If we modified drawables without removing them, we're done with this tile.
|
||||
// If we update existing drawables, don't build new ones.
|
||||
// But if the geometry has changed, we need to drop and re-build them anyway.
|
||||
if (updateTile(renderPass, tileID, std::move(updateExisting)) && !geometryChanged) {
|
||||
continue;
|
||||
} else if (geometryChanged) {
|
||||
// If the geometry has changed, the drawable needs to be re-built
|
||||
removeTile(renderPass, tileID);
|
||||
}
|
||||
}
|
||||
@@ -502,7 +509,7 @@ void RenderRasterLayer::update(gfx::ShaderRegistry& shaders,
|
||||
buildVertexData(builder, /*drawable=*/nullptr, bucket);
|
||||
|
||||
// finish
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
drawable->setLayerTweaker(layerTweaker);
|
||||
|
||||
@@ -867,9 +867,9 @@ void updateTileDrawable(gfx::Drawable& drawable,
|
||||
// TODO: detect whether anything has actually changed
|
||||
// See `Placement::updateBucketDynamicVertices`
|
||||
|
||||
gfx::VertexAttributeArray attribs;
|
||||
updateTileAttributes(buffer, isText, paintProps, evaluated, attribs, propertiesAsUniforms);
|
||||
drawable.setVertexAttributes(std::move(attribs));
|
||||
if (auto& attribs = drawable.getVertexAttributes()) {
|
||||
updateTileAttributes(buffer, isText, paintProps, evaluated, *attribs, propertiesAsUniforms);
|
||||
}
|
||||
}
|
||||
|
||||
const StringIdentity idCollisionPosAttribName = stringIndexer().get("a_pos");
|
||||
@@ -878,25 +878,26 @@ const StringIdentity idCollisionExtrudeAttribName = stringIndexer().get("a_extru
|
||||
const StringIdentity idCollisionPlacedAttribName = stringIndexer().get("a_placed");
|
||||
const StringIdentity idCollisionShiftAttribName = stringIndexer().get("a_shift");
|
||||
|
||||
gfx::VertexAttributeArray getCollisionVertexAttributes(const SymbolBucket::CollisionBuffer& buffer) {
|
||||
gfx::VertexAttributeArray vertexAttrs;
|
||||
gfx::VertexAttributeArrayPtr getCollisionVertexAttributes(gfx::Context& context,
|
||||
const SymbolBucket::CollisionBuffer& buffer) {
|
||||
auto vertexAttrs = context.createVertexAttributeArray();
|
||||
using LayoutVertex = gfx::Vertex<CollisionBoxLayoutAttributes>;
|
||||
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idCollisionPosAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idCollisionPosAttribName)) {
|
||||
attr->setSharedRawData(buffer.sharedVertices,
|
||||
offsetof(LayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(LayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idCollisionAnchorPosAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idCollisionAnchorPosAttribName)) {
|
||||
attr->setSharedRawData(buffer.sharedVertices,
|
||||
offsetof(LayoutVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(LayoutVertex),
|
||||
gfx::AttributeDataType::Short2);
|
||||
}
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idCollisionExtrudeAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idCollisionExtrudeAttribName)) {
|
||||
attr->setSharedRawData(buffer.sharedVertices,
|
||||
offsetof(LayoutVertex, a3),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -906,14 +907,14 @@ gfx::VertexAttributeArray getCollisionVertexAttributes(const SymbolBucket::Colli
|
||||
|
||||
using DynamicVertex = gfx::Vertex<CollisionBoxDynamicAttributes>;
|
||||
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idCollisionPlacedAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idCollisionPlacedAttribName)) {
|
||||
attr->setSharedRawData(buffer.sharedDynamicVertices,
|
||||
offsetof(DynamicVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
sizeof(DynamicVertex),
|
||||
gfx::AttributeDataType::UShort2);
|
||||
}
|
||||
if (const auto& attr = vertexAttrs.getOrAdd(idCollisionShiftAttribName)) {
|
||||
if (const auto& attr = vertexAttrs->add(idCollisionShiftAttribName)) {
|
||||
attr->setSharedRawData(buffer.sharedDynamicVertices,
|
||||
offsetof(DynamicVertex, a2),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -1109,12 +1110,12 @@ void RenderSymbolLayer::update(gfx::ShaderRegistry& shaders,
|
||||
collisionBuilder->setDrawableName(layerCollisionPrefix + suffix + "box");
|
||||
collisionBuilder->setShader(shader);
|
||||
addVertices(collisionBox->vertices().vector());
|
||||
collisionBuilder->setVertexAttributes(getCollisionVertexAttributes(*collisionBox));
|
||||
collisionBuilder->setVertexAttributes(getCollisionVertexAttributes(context, *collisionBox));
|
||||
collisionBuilder->setSegments(gfx::Lines(1.0f),
|
||||
collisionBox->sharedLines,
|
||||
collisionBox->segments.data(),
|
||||
collisionBox->segments.size());
|
||||
collisionBuilder->flush();
|
||||
collisionBuilder->flush(context);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1126,12 +1127,12 @@ void RenderSymbolLayer::update(gfx::ShaderRegistry& shaders,
|
||||
collisionBuilder->setDrawableName(layerCollisionPrefix + suffix + "circle");
|
||||
collisionBuilder->setShader(shader);
|
||||
addVertices(collisionCircle->vertices().vector());
|
||||
collisionBuilder->setVertexAttributes(getCollisionVertexAttributes(*collisionCircle));
|
||||
collisionBuilder->setVertexAttributes(getCollisionVertexAttributes(context, *collisionCircle));
|
||||
collisionBuilder->setSegments(gfx::Triangles(),
|
||||
collisionCircle->sharedTriangles,
|
||||
collisionCircle->segments.data(),
|
||||
collisionCircle->segments.size());
|
||||
collisionBuilder->flush();
|
||||
collisionBuilder->flush(context);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1258,8 +1259,8 @@ void RenderSymbolLayer::update(gfx::ShaderRegistry& shaders,
|
||||
const auto vertexCount = buffer.vertices().elements();
|
||||
|
||||
propertiesAsUniforms.clear();
|
||||
gfx::VertexAttributeArray attribs;
|
||||
updateTileAttributes(buffer, isText, bucketPaintProperties, evaluated, attribs, propertiesAsUniforms);
|
||||
auto attribs = context.createVertexAttributeArray();
|
||||
updateTileAttributes(buffer, isText, bucketPaintProperties, evaluated, *attribs, propertiesAsUniforms);
|
||||
|
||||
const auto textHalo = evaluated.get<style::TextHaloColor>().constantOr(Color::black()).a > 0.0f &&
|
||||
evaluated.get<style::TextHaloWidth>().constantOr(1);
|
||||
@@ -1342,7 +1343,7 @@ void RenderSymbolLayer::update(gfx::ShaderRegistry& shaders,
|
||||
|
||||
builder->setSegments(gfx::Triangles(), buffer.sharedTriangles, &renderable.segment.get(), 1);
|
||||
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
|
||||
@@ -175,7 +175,7 @@ void TileSourceRenderItem::updateDebugDrawables(DebugLayerGroupMap& debugLayerGr
|
||||
debugBuilder->setTexture(texture, samplerLocation.value());
|
||||
|
||||
// finish
|
||||
debugBuilder->flush();
|
||||
debugBuilder->flush(context);
|
||||
for (auto& drawable : debugBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tileID);
|
||||
auto& uniforms = drawable->mutableUniformBuffers();
|
||||
@@ -282,7 +282,7 @@ void TileSourceRenderItem::updateDebugDrawables(DebugLayerGroupMap& debugLayerGr
|
||||
auto tweaker = std::make_shared<PolylineDrawableTweaker>(linePropertiesUBO);
|
||||
|
||||
// finish
|
||||
polylineBuilder->flush();
|
||||
polylineBuilder->flush(context);
|
||||
for (auto& drawable : polylineBuilder->clearDrawables()) {
|
||||
drawable->setTileID(tile.getOverscaledTileID());
|
||||
drawable->addTweaker(tweaker);
|
||||
|
||||
@@ -302,8 +302,9 @@ void CustomDrawableLayerHost::Interface::addFill(const GeometryCollection& geome
|
||||
// add to builder
|
||||
static const StringIdentity idVertexAttribName = stringIndexer().get("a_pos");
|
||||
builder->setVertexAttrNameId(idVertexAttribName);
|
||||
gfx::VertexAttributeArray attrs;
|
||||
if (const auto& attr = attrs.add(idVertexAttribName)) {
|
||||
|
||||
auto attrs = context.createVertexAttributeArray();
|
||||
if (const auto& attr = attrs->add(idVertexAttribName)) {
|
||||
attr->setSharedRawData(sharedVertices,
|
||||
offsetof(FillLayoutVertex, a1),
|
||||
/*vertexOffset=*/0,
|
||||
@@ -315,14 +316,14 @@ void CustomDrawableLayerHost::Interface::addFill(const GeometryCollection& geome
|
||||
builder->setSegments(gfx::Triangles(), sharedTriangles, triangleSegments.data(), triangleSegments.size());
|
||||
|
||||
// flush current builder drawable
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
}
|
||||
|
||||
void CustomDrawableLayerHost::Interface::finish() {
|
||||
if (builder && !builder->empty()) {
|
||||
// finish
|
||||
const auto finish_ = [this](auto& tweaker) {
|
||||
builder->flush();
|
||||
builder->flush(context);
|
||||
for (auto& drawable : builder->clearDrawables()) {
|
||||
assert(tileID.has_value());
|
||||
drawable->setTileID(tileID.value());
|
||||
|
||||
Reference in New Issue
Block a user