Version 5.2.0.0.beta1, tag libreoffice-5.2.0.0.beta1
[LibreOffice.git] / vcl / opengl / FixedTextureAtlas.cxx
blob87c5bb1ff2ac8f85e926b753ec88234f57c2c5e3
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 */
11 #include <sal/config.h>
12 #include <vcl/opengl/OpenGLContext.hxx>
13 #include <vcl/opengl/OpenGLHelper.hxx>
15 #include "opengl/framebuffer.hxx"
16 #include "opengl/texture.hxx"
18 #include "opengl/FixedTextureAtlas.hxx"
20 struct FixedTexture
22 ImplOpenGLTexture* mpTexture;
23 int mnFreeSlots;
24 std::vector<bool> maAllocatedSlots;
26 FixedTexture(ImplOpenGLTexture* pTexture, int nNumberOfSlots)
27 : mpTexture(pTexture)
28 , mnFreeSlots(nNumberOfSlots)
29 , maAllocatedSlots(nNumberOfSlots, false)
31 auto aDeallocateFunction = [this] (int nSlotNumber)
33 deallocateSlot(nSlotNumber);
36 mpTexture->SetSlotDeallocateCallback(aDeallocateFunction);
37 mpTexture->InitializeSlotMechanism(nNumberOfSlots);
40 void allocateSlot(int nSlot)
42 maAllocatedSlots[nSlot] = true;
43 mnFreeSlots--;
46 void deallocateSlot(int nSlot)
48 maAllocatedSlots[nSlot] = false;
49 mnFreeSlots++;
52 int findAndAllocateFreeSlot()
54 for (size_t i = 0; i < maAllocatedSlots.size(); ++i)
56 if (!maAllocatedSlots[i])
58 allocateSlot(i);
59 return i;
62 return -1;
66 FixedTextureAtlasManager::FixedTextureAtlasManager(int nWidthFactor, int nHeightFactor, int nSubTextureSize)
67 : mWidthFactor(nWidthFactor)
68 , mHeightFactor(nHeightFactor)
69 , mSubTextureSize(nSubTextureSize)
73 FixedTextureAtlasManager::~FixedTextureAtlasManager()
75 for (std::unique_ptr<FixedTexture>& pFixedTexture : maFixedTextures)
77 // Free texture early in VCL shutdown while we have a context.
78 delete pFixedTexture->mpTexture;
82 void FixedTextureAtlasManager::CreateNewTexture()
84 int nTextureWidth = mWidthFactor * mSubTextureSize;
85 int nTextureHeight = mHeightFactor * mSubTextureSize;
86 std::unique_ptr<FixedTexture> pFixedTexture(
87 new FixedTexture(new ImplOpenGLTexture(nTextureWidth, nTextureHeight, true),
88 mWidthFactor * mHeightFactor));
90 maFixedTextures.push_back(std::move(pFixedTexture));
93 OpenGLTexture FixedTextureAtlasManager::Reserve(int nWidth, int nHeight)
95 FixedTexture* pFixedTexture = nullptr;
97 auto funFreeSlot = [] (std::unique_ptr<FixedTexture>& inFixedTexture)
99 return inFixedTexture->mnFreeSlots > 0;
102 auto it = std::find_if(maFixedTextures.begin(), maFixedTextures.end(), funFreeSlot);
104 if (it != maFixedTextures.end())
106 pFixedTexture = (*it).get();
108 else
110 CreateNewTexture();
111 pFixedTexture = maFixedTextures.back().get();
114 int nSlot = pFixedTexture->findAndAllocateFreeSlot();
116 // Calculate coordinates in texture
117 int nX = (nSlot % mWidthFactor) * mSubTextureSize;
118 int nY = (nSlot / mWidthFactor) * mSubTextureSize;
120 Rectangle aRectangle(Point(nX, nY), Size(nWidth, nHeight));
122 return OpenGLTexture(pFixedTexture->mpTexture, aRectangle, nSlot);
125 OpenGLTexture FixedTextureAtlasManager::InsertBuffer(int nWidth, int nHeight, int nFormat, int nType, sal_uInt8* pData)
127 OpenGLTexture aTexture = Reserve(nWidth, nHeight);
128 if (pData == nullptr)
129 return aTexture;
131 aTexture.CopyData(nWidth, nHeight, nFormat, nType, pData);
133 return aTexture;
136 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */