mirror of https://github.com/mosra/magnum.git
Browse Source
Same approach as done e.g. in the Ui library -- taking advantage of the base class already allocating an internal state struct, deriving from it and putting the state there instead of either having it as a class member (at the cost of extra header dependency) or as a separate state struct (at the cost of extra allocation). The only downside is a virtual destructor in the state struct, but compared to the alternatives that's completely fine.pull/674/head
13 changed files with 243 additions and 88 deletions
@ -0,0 +1,91 @@
|
||||
#ifndef Magnum_Text_Implementation_abstractGlyphCacheState_h |
||||
#define Magnum_Text_Implementation_abstractGlyphCacheState_h |
||||
/*
|
||||
This file is part of Magnum. |
||||
|
||||
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||
2020, 2021, 2022, 2023, 2024, 2025 |
||||
Vladimír Vondruš <mosra@centrum.cz> |
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a |
||||
copy of this software and associated documentation files (the "Software"), |
||||
to deal in the Software without restriction, including without limitation |
||||
the rights to use, copy, modify, merge, publish, distribute, sublicense, |
||||
and/or sell copies of the Software, and to permit persons to whom the |
||||
Software is furnished to do so, subject to the following conditions: |
||||
|
||||
The above copyright notice and this permission notice shall be included |
||||
in all copies or substantial portions of the Software. |
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
||||
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING |
||||
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
||||
DEALINGS IN THE SOFTWARE. |
||||
*/ |
||||
|
||||
#include <Corrade/Containers/Array.h> |
||||
|
||||
#include "Magnum/Image.h" |
||||
#include "Magnum/PixelFormat.h" |
||||
#include "Magnum/Math/Vector2.h" |
||||
#include "Magnum/Text/AbstractGlyphCache.h" |
||||
#include "Magnum/TextureTools/Atlas.h" |
||||
|
||||
namespace Magnum { namespace Text { |
||||
|
||||
struct AbstractGlyphCache::State { |
||||
explicit State(PixelFormat format, const Vector3i& size, PixelFormat processedFormat, const Vector2i& processedSize, const Vector2i& padding); |
||||
|
||||
/* GlyphCacheGL, GlyphCacheArrayGL, DistanceFieldGlyphCacheGL derive from
|
||||
this to avoid another state struct allocation or putting the extra state |
||||
as members, inflating header size */ |
||||
virtual ~State(); |
||||
|
||||
Image3D image; |
||||
TextureTools::AtlasLandfill atlas; |
||||
|
||||
PixelFormat processedFormat; |
||||
Vector2i processedSize; |
||||
Vector2i padding; |
||||
|
||||
/* 0/4 bytes free */ |
||||
|
||||
/* First element is glyph position relative to a point on the baseline,
|
||||
second layer in the texture atlas, third a region in the atlas |
||||
slice. Index of the item is ID of the glyph in the cache, refered to |
||||
from the fontGlyphMapping array. Index 0 is reserved for an invalid |
||||
glyph. */ |
||||
Containers::Array<Containers::Triple<Vector2i, Int, Range2Di>> glyphs; |
||||
/* `fontRanges[i]` to `fontRanges[i + 1]` is the range in
|
||||
`fontGlyphMapping` containing a mapping for glyphs from font `i`, |
||||
`fontGlyphMapping[fontRanges[i]] + j` is then mapping from glyph ID `j` |
||||
from font `i` to index in the `glyphs` array, or is 0 if given |
||||
glyph isn't present in the cache (which then maps to the invalid |
||||
glyph). */ |
||||
struct Font { |
||||
UnsignedInt offset; |
||||
/* 4 bytes free on 64b, but not so critical I think */ |
||||
const AbstractFont* pointer; |
||||
}; |
||||
Containers::Array<Font> fonts; |
||||
/* With an assumption that majority of font glyphs get put into a cache,
|
||||
this achieves O(1) mapping from a font ID + font-specific glyph ID pair |
||||
to a cache-global glyph ID with far less overhead than a hashmap would, |
||||
and much less memory used as well compared to storing a key, value and a |
||||
hash for each mapping entry. |
||||
|
||||
Another assumption is that there's no more than 64k glyphs in total, |
||||
which makes the mapping save half memory compared to storing 32-bit |
||||
ints. 64K glyphs is enough to fill a 4K texture with 16x16 glyphs, which |
||||
seems enough for now. It however might get reached at some point in |
||||
practice, in which case the type would simply get changed to a 32-bit |
||||
one (and the assertion in addGlyph() then removed). */ |
||||
Containers::Array<UnsignedShort> fontGlyphMapping; |
||||
}; |
||||
|
||||
}} |
||||
|
||||
#endif |
||||
@ -0,0 +1,53 @@
|
||||
#ifndef Magnum_Text_Implementation_glyphCacheGLState_h |
||||
#define Magnum_Text_Implementation_glyphCacheGLState_h |
||||
/*
|
||||
This file is part of Magnum. |
||||
|
||||
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||
2020, 2021, 2022, 2023, 2024, 2025 |
||||
Vladimír Vondruš <mosra@centrum.cz> |
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a |
||||
copy of this software and associated documentation files (the "Software"), |
||||
to deal in the Software without restriction, including without limitation |
||||
the rights to use, copy, modify, merge, publish, distribute, sublicense, |
||||
and/or sell copies of the Software, and to permit persons to whom the |
||||
Software is furnished to do so, subject to the following conditions: |
||||
|
||||
The above copyright notice and this permission notice shall be included |
||||
in all copies or substantial portions of the Software. |
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
||||
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING |
||||
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
||||
DEALINGS IN THE SOFTWARE. |
||||
*/ |
||||
|
||||
#include "Magnum/GL/Texture.h" |
||||
#ifndef MAGNUM_TARGET_GLES2 |
||||
#include "Magnum/GL/TextureArray.h" |
||||
#endif |
||||
#include "Magnum/Text/Implementation/abstractGlyphCacheState.h" |
||||
|
||||
namespace Magnum { namespace Text { |
||||
|
||||
struct GlyphCacheGL::State: AbstractGlyphCache::State { |
||||
explicit State(PixelFormat format, const Vector2i& size, PixelFormat processedFormat, const Vector2i& processedSize, const Vector2i& padding); |
||||
|
||||
GL::Texture2D texture; |
||||
}; |
||||
|
||||
#ifndef MAGNUM_TARGET_GLES2 |
||||
struct GlyphCacheArrayGL::State: AbstractGlyphCache::State { |
||||
explicit State(PixelFormat format, const Vector3i& size, PixelFormat processedFormat, const Vector2i& processedSize, const Vector2i& padding); |
||||
|
||||
GL::Texture2DArray texture; |
||||
}; |
||||
#endif |
||||
|
||||
}} |
||||
|
||||
#endif |
||||
Loading…
Reference in new issue