#pragma once #include "drape_frontend/gui/shape.hpp" #include "drape_frontend/render_state.hpp" #include "drape/binding_info.hpp" #include "drape/drape_global.hpp" #include "drape/glsl_types.hpp" #include "drape/texture_manager.hpp" #include "std/cstdint.hpp" #include "std/unordered_set.hpp" #include "std/utility.hpp" namespace gui { using TAlphabet = unordered_set; class StaticLabel { public: static char const * DefaultDelim; struct Vertex { Vertex() = default; Vertex(glsl::vec3 const & pos, glsl::vec2 const & normal, glsl::vec2 const & color, glsl::vec2 const & outline, glsl::vec2 const & mask) : m_position(pos) , m_normal(normal) , m_colorTexCoord(color) , m_outlineColorTexCoord(outline) , m_maskTexCoord(mask) { } static dp::BindingInfo const & GetBindingInfo(); glsl::vec3 m_position; glsl::vec2 m_normal; glsl::vec2 m_colorTexCoord; glsl::vec2 m_outlineColorTexCoord; glsl::vec2 m_maskTexCoord; }; struct LabelResult { LabelResult(); dp::GLState m_state; buffer_vector m_buffer; m2::RectF m_boundRect; TAlphabet m_alphabet; }; static void CacheStaticText(string const & text, char const * delim, dp::Anchor anchor, dp::FontDecl const & font, ref_ptr mng, LabelResult & result); }; class MutableLabel { public: struct StaticVertex { StaticVertex() = default; StaticVertex(glsl::vec3 const & position, glsl::vec2 const & color, glsl::vec2 const & outlineColor) : m_position(position) , m_color(color) , m_outline(outlineColor) { } static dp::BindingInfo const & GetBindingInfo(); glsl::vec3 m_position; glsl::vec2 m_color; glsl::vec2 m_outline; }; struct DynamicVertex { DynamicVertex() = default; DynamicVertex(glsl::vec2 const & normal, glsl::vec2 const & mask) : m_normal(normal) , m_maskTexCoord(mask) { } static dp::BindingInfo const & GetBindingInfo(); glsl::vec2 m_normal; glsl::vec2 m_maskTexCoord; }; MutableLabel(dp::Anchor anchor); struct PrecacheParams { string m_alphabet; size_t m_maxLength; dp::FontDecl m_font; }; struct PrecacheResult { PrecacheResult(); dp::GLState m_state; buffer_vector m_buffer; m2::PointF m_maxPixelSize; }; struct LabelResult { buffer_vector m_buffer; m2::RectD m_boundRect; }; void Precache(PrecacheParams const & params, PrecacheResult & result, ref_ptr mng); void SetText(LabelResult & result, string text) const; m2::PointF GetAvarageSize() const; using TAlphabetNode = pair; using TAlphabet = vector; TAlphabet const & GetAlphabet() const { return m_alphabet; } private: void SetMaxLength(uint16_t maxLength); ref_ptr SetAlphabet(string const & alphabet, ref_ptr mng); private: dp::Anchor m_anchor; uint16_t m_maxLength = 0; float m_textRatio = 0.0f; TAlphabet m_alphabet; }; class MutableLabelHandle : public Handle { using TBase = Handle; public: MutableLabelHandle(uint32_t id, dp::Anchor anchor, m2::PointF const & pivot); MutableLabelHandle(uint32_t id, dp::Anchor anchor, m2::PointF const & pivot, ref_ptr textures); void GetAttributeMutation(ref_ptr mutator) const override; bool Update(ScreenBase const & screen) override; ref_ptr GetTextView(); void UpdateSize(m2::PointF const & size); protected: void SetContent(string && content); void SetContent(string const & content); void SetTextureManager(ref_ptr textures); private: drape_ptr m_textView; mutable bool m_isContentDirty; string m_content; ref_ptr m_textureManager; bool m_glyphsReady; }; class MutableLabelDrawer { public: using TCreatoreResult = drape_ptr; using THandleCreator = function; struct Params { dp::Anchor m_anchor; dp::FontDecl m_font; m2::PointF m_pivot; string m_alphabet; uint32_t m_maxLength; THandleCreator m_handleCreator; }; /// return maximum pixel size static m2::PointF Draw(Params const & params, ref_ptr mng, dp::Batcher::TFlushFn const & flushFn); }; class StaticLabelHandle : public Handle { using TBase = Handle; public: StaticLabelHandle(uint32_t id, ref_ptr textureManager, dp::Anchor anchor, m2::PointF const & pivot, m2::PointF const & size, TAlphabet const & alphabet); bool Update(ScreenBase const & screen) override; private: strings::UniString m_alphabet; ref_ptr m_textureManager; bool m_glyphsReady; }; }