mirror of https://github.com/bkaradzic/bgfx
SVT example fixes
This commit is contained in:
parent
7732554b02
commit
ec167c1d51
|
@ -6,11 +6,11 @@
|
|||
/*
|
||||
* Reference(s):
|
||||
* - Sparse Virtual Textures by Sean Barrett
|
||||
* http://silverspaceship.com/src/svt/
|
||||
* http://web.archive.org/web/20190103162611/http://silverspaceship.com/src/svt/
|
||||
* - Virtual Texture Demo by Brad Blanchard
|
||||
* http://linedef.com/virtual-texture-demo.html
|
||||
* http://web.archive.org/web/20190103162638/http://linedef.com/virtual-texture-demo.html
|
||||
* - Mars texture
|
||||
* http://www.celestiamotherlode.net/catalog/mars.php
|
||||
* http://web.archive.org/web/20190103162730/http://www.celestiamotherlode.net/catalog/mars.php
|
||||
*/
|
||||
|
||||
#include "common.h"
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
#include "vt.h"
|
||||
/*
|
||||
* Copyright 2018 Aleš Mlakar. All rights reserved.
|
||||
* License: https://github.com/bkaradzic/bgfx#license-bsd-2-clause
|
||||
*/
|
||||
|
||||
#include "vt.h"
|
||||
#include <bx/file.h>
|
||||
#include <algorithm>
|
||||
|
||||
|
@ -88,7 +93,7 @@ StagingPool::StagingPool(int _width, int _height, int _count, bool _readBack)
|
|||
|
||||
StagingPool::~StagingPool()
|
||||
{
|
||||
for (int i = 0; i < m_stagingTextures.size(); ++i)
|
||||
for (int i = 0; i < (int)m_stagingTextures.size(); ++i)
|
||||
{
|
||||
bgfx::destroy(m_stagingTextures[i]);
|
||||
}
|
||||
|
@ -96,7 +101,7 @@ StagingPool::~StagingPool()
|
|||
|
||||
void StagingPool::grow(int count)
|
||||
{
|
||||
while (m_stagingTextures.size() < count)
|
||||
while ((int)m_stagingTextures.size() < count)
|
||||
{
|
||||
auto stagingTexture = bgfx::createTexture2D((uint16_t)m_width, (uint16_t)m_height, false, 1, bgfx::TextureFormat::BGRA8, m_flags);
|
||||
m_stagingTextures.push_back(stagingTexture);
|
||||
|
@ -110,14 +115,14 @@ bgfx::TextureHandle StagingPool::getTexture()
|
|||
|
||||
void StagingPool::next()
|
||||
{
|
||||
m_stagingTextureIndex = (m_stagingTextureIndex + 1) % m_stagingTextures.size();
|
||||
m_stagingTextureIndex = (m_stagingTextureIndex + 1) % (int)m_stagingTextures.size();
|
||||
}
|
||||
|
||||
// PageIndexer
|
||||
PageIndexer::PageIndexer(VirtualTextureInfo* _info)
|
||||
: m_info(_info)
|
||||
{
|
||||
m_mipcount = (int)(log2(m_info->GetPageTableSize()) + 1);
|
||||
m_mipcount = int(bx::log2((float)m_info->GetPageTableSize()) + 1);
|
||||
|
||||
m_sizes.resize(m_mipcount);
|
||||
for (int i = 0; i < m_mipcount; ++i)
|
||||
|
@ -200,6 +205,10 @@ int PageIndexer::getCount() const
|
|||
return m_count;
|
||||
}
|
||||
|
||||
int PageIndexer::getMipCount() const {
|
||||
return m_mipcount;
|
||||
}
|
||||
|
||||
// SimpleImage
|
||||
SimpleImage::SimpleImage(int _width, int _height, int _channelCount, uint8_t _clearValue)
|
||||
: m_width(_width)
|
||||
|
@ -441,14 +450,14 @@ PageTable::PageTable(PageCache* _cache, VirtualTextureInfo* _info, PageIndexer*
|
|||
, m_quadtree(nullptr)
|
||||
, m_quadtreeDirty(true) // Force quadtree dirty on startup
|
||||
{
|
||||
int size = m_info->GetPageTableSize();
|
||||
m_quadtree = new Quadtree({ 0, 0, size, size }, (int)log2(size));
|
||||
auto size = m_info->GetPageTableSize();
|
||||
m_quadtree = new Quadtree({ 0, 0, size, size }, (int)bx::log2((float)size));
|
||||
m_texture = bgfx::createTexture2D((uint16_t)size, (uint16_t)size, true, 1, bgfx::TextureFormat::BGRA8, BGFX_SAMPLER_UVW_CLAMP | BGFX_SAMPLER_POINT);
|
||||
|
||||
_cache->added = [=](Page page, Point pt) { m_quadtreeDirty = true; m_quadtree->add(page, pt); };
|
||||
_cache->removed = [=](Page page, Point pt) { m_quadtreeDirty = true; m_quadtree->remove(page); pt; };
|
||||
_cache->removed = [=](Page page, Point pt) { m_quadtreeDirty = true; m_quadtree->remove(page); BX_UNUSED(pt); };
|
||||
|
||||
int PageTableSizeLog2 = (int)log2(m_info->GetPageTableSize());
|
||||
auto PageTableSizeLog2 = m_indexer->getMipCount();
|
||||
|
||||
for (int i = 0; i < PageTableSizeLog2 + 1; ++i)
|
||||
{
|
||||
|
@ -464,11 +473,11 @@ PageTable::~PageTable()
|
|||
{
|
||||
delete m_quadtree;
|
||||
bgfx::destroy(m_texture);
|
||||
for (int i = 0; i < m_images.size(); ++i)
|
||||
for (int i = 0; i < (int)m_images.size(); ++i)
|
||||
{
|
||||
delete m_images[i];
|
||||
}
|
||||
for (int i = 0; i < m_stagingTextures.size(); ++i)
|
||||
for (int i = 0; i < (int)m_stagingTextures.size(); ++i)
|
||||
{
|
||||
bgfx::destroy(m_stagingTextures[i]);
|
||||
}
|
||||
|
@ -481,7 +490,7 @@ void PageTable::update(bgfx::ViewId blitViewId)
|
|||
return;
|
||||
}
|
||||
m_quadtreeDirty = false;
|
||||
int PageTableSizeLog2 = (int)log2(m_info->GetPageTableSize());
|
||||
auto PageTableSizeLog2 = m_indexer->getMipCount();
|
||||
for (int i = 0; i < PageTableSizeLog2 + 1; ++i)
|
||||
{
|
||||
m_quadtree->write(*m_images[i], i);
|
||||
|
@ -499,11 +508,11 @@ bgfx::TextureHandle PageTable::getTexture()
|
|||
|
||||
// PageLoader
|
||||
PageLoader::PageLoader(TileDataFile* _tileDataFile, PageIndexer* _indexer, VirtualTextureInfo* _info)
|
||||
: m_tileDataFile(_tileDataFile)
|
||||
: m_colorMipLevels(false)
|
||||
, m_showBorders(false)
|
||||
, m_tileDataFile(_tileDataFile)
|
||||
, m_indexer(_indexer)
|
||||
, m_info(_info)
|
||||
, m_colorMipLevels(false)
|
||||
, m_showBorders(false)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -807,8 +816,8 @@ void FeedbackBuffer::download()
|
|||
// We do this so that we can fall back to them if we run out of memory
|
||||
void FeedbackBuffer::addRequestAndParents(Page request)
|
||||
{
|
||||
int PageTableSizeLog2 = (int)log2(m_info->GetPageTableSize());
|
||||
int count = PageTableSizeLog2 - request.m_mip + 1;
|
||||
auto PageTableSizeLog2 = m_indexer->getMipCount();
|
||||
auto count = PageTableSizeLog2 - request.m_mip + 1;
|
||||
|
||||
for (int i = 0; i < count; ++i)
|
||||
{
|
||||
|
@ -817,6 +826,7 @@ void FeedbackBuffer::addRequestAndParents(Page request)
|
|||
|
||||
Page page = { xpos, ypos, request.m_mip + i };
|
||||
|
||||
// If it's not a valid page (position or mip out of range) just skip it
|
||||
if (!m_indexer->isValid(page))
|
||||
{
|
||||
return;
|
||||
|
@ -1001,7 +1011,7 @@ void VirtualTexture::update(const std::vector<int>& requests, bgfx::ViewId blitV
|
|||
// If it is, update it's position in the LRU collection
|
||||
// Otherwise add it to the list of pages to load
|
||||
int touched = 0;
|
||||
for (int i = 0; i < requests.size(); ++i)
|
||||
for (int i = 0; i < (int)requests.size(); ++i)
|
||||
{
|
||||
if (requests[i] > 0)
|
||||
{
|
||||
|
@ -1039,10 +1049,10 @@ void VirtualTexture::update(const std::vector<int>& requests, bgfx::ViewId blitV
|
|||
m_pageTable->update(blitViewId);
|
||||
}
|
||||
|
||||
TileDataFile::TileDataFile(const std::string& filename, VirtualTextureInfo* _info, bool _readWrite) : m_info(_info)
|
||||
TileDataFile::TileDataFile(const bx::FilePath& filename, VirtualTextureInfo* _info, bool _readWrite) : m_info(_info)
|
||||
{
|
||||
const char* access = _readWrite ? "w+b" : "rb";
|
||||
m_file = fopen(filename.c_str(), access);
|
||||
m_file = fopen(filename.get(), access);
|
||||
m_size = m_info->GetPageSize() * m_info->GetPageSize() * ChannelCount;
|
||||
}
|
||||
|
||||
|
@ -1108,28 +1118,32 @@ TileGenerator::~TileGenerator()
|
|||
delete m_tileImage;
|
||||
}
|
||||
|
||||
bool TileGenerator::generate(const std::string& filename)
|
||||
bool TileGenerator::generate(const bx::FilePath& filename)
|
||||
{
|
||||
std::string cacheFilename = filename + ".cache";
|
||||
// Generate cache filename
|
||||
char tempFilename[256];
|
||||
bx::snprintf(tempFilename, sizeof(tempFilename), "temp/%s.vt", filename.getBaseName().getPtr());
|
||||
bx::FilePath cacheFilename = tempFilename;
|
||||
// Check if tile file already exist
|
||||
{
|
||||
bx::Error error;
|
||||
bx::FileReader fileReader;
|
||||
fileReader.open(bx::FilePath(cacheFilename.c_str()), &error);
|
||||
fileReader.open(cacheFilename, &error);
|
||||
if (error.isOk())
|
||||
{
|
||||
bx::debugPrintf("Tile data file '%s' already exists. Skipping generation.\n", cacheFilename.c_str());
|
||||
bx::debugPrintf("Tile data file '%s' already exists. Skipping generation.\n", cacheFilename.get());
|
||||
return true;
|
||||
}
|
||||
}
|
||||
// Read image
|
||||
{
|
||||
bx::debugPrintf("Reading image '%s'.\n", filename.c_str());
|
||||
bx::debugPrintf("Reading image '%s'.\n", filename.get());
|
||||
bx::Error error;
|
||||
bx::FileReader fileReader;
|
||||
fileReader.open(bx::FilePath(filename.c_str()), &error);
|
||||
fileReader.open(bx::FilePath(filename.get()), &error);
|
||||
if (!error.isOk())
|
||||
{
|
||||
bx::debugPrintf("Image open failed'%s'.\n", filename.get());
|
||||
return false;
|
||||
}
|
||||
auto size = fileReader.seek(0, bx::Whence::End);
|
||||
|
@ -1139,12 +1153,14 @@ bool TileGenerator::generate(const std::string& filename)
|
|||
fileReader.close();
|
||||
if (!error.isOk())
|
||||
{
|
||||
bx::debugPrintf("Image read failed'%s'.\n", filename.get());
|
||||
return false;
|
||||
}
|
||||
m_sourceImage = bimg::imageParse(&m_allocator, rawImage, uint32_t(size), bimg::TextureFormat::BGRA8, &error);
|
||||
BX_FREE(&m_allocator, rawImage);
|
||||
if (!error.isOk())
|
||||
{
|
||||
bx::debugPrintf("Image parse failed'%s'.\n", filename.get());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -1164,8 +1180,8 @@ bool TileGenerator::generate(const std::string& filename)
|
|||
|
||||
// Generate tiles
|
||||
bx::debugPrintf("Generating tiles\n");
|
||||
int mipcount = (int)log2(m_info->GetPageTableSize());
|
||||
for (int i = 0; i < mipcount + 1; ++i)
|
||||
auto mipcount = m_indexer->getMipCount();
|
||||
for (int i = 0; i < mipcount; ++i)
|
||||
{
|
||||
int count = (m_info->m_virtualTextureSize / m_tilesize) >> i;
|
||||
bx::debugPrintf("Generating Mip:%d Count:%dx%d\n", i, count, count);
|
||||
|
@ -1228,10 +1244,8 @@ void TileGenerator::CopyTile(SimpleImage& image, Page request)
|
|||
Page page = { xpos + x - 1, ypos + y - 1, mip };
|
||||
|
||||
// Wrap so we get the border sections of other pages
|
||||
#define Modulus(_a_, _b_) (int)(_a_ - _b_ * floorf( (float)_a_ / (float)_b_))
|
||||
page.m_x = Modulus(page.m_x, size);
|
||||
page.m_y = Modulus(page.m_y, size);
|
||||
#undef Modulus
|
||||
page.m_x = (int)bx::mod((float)page.m_x, (float)size);
|
||||
page.m_y = (int)bx::mod((float)page.m_y, (float)size);
|
||||
|
||||
m_tileDataFile->readPage(m_indexer->getIndexFromPage(page), &m_page2Image->m_data[0]);
|
||||
|
||||
|
|
|
@ -1,3 +1,8 @@
|
|||
/*
|
||||
* Copyright 2018 Aleš Mlakar. All rights reserved.
|
||||
* License: https://github.com/bkaradzic/bgfx#license-bsd-2-clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "common.h"
|
||||
#include "bgfx_utils.h"
|
||||
|
@ -126,6 +131,7 @@ public:
|
|||
|
||||
bool isValid(Page page);
|
||||
int getCount() const;
|
||||
int getMipCount() const;
|
||||
|
||||
private:
|
||||
VirtualTextureInfo* m_info;
|
||||
|
@ -168,8 +174,8 @@ struct Quadtree
|
|||
void write(Quadtree* node, SimpleImage& image, int miplevel);
|
||||
static Quadtree* findPage(Quadtree* node, Page request, int* index);
|
||||
|
||||
int m_level;
|
||||
Rect m_rectangle;
|
||||
int m_level;
|
||||
Point m_mapping;
|
||||
Quadtree* m_children[4];
|
||||
};
|
||||
|
@ -374,7 +380,7 @@ private:
|
|||
class TileDataFile
|
||||
{
|
||||
public:
|
||||
TileDataFile(const std::string& filename, VirtualTextureInfo* _info, bool _readWrite = false);
|
||||
TileDataFile(const bx::FilePath& filename, VirtualTextureInfo* _info, bool _readWrite = false);
|
||||
~TileDataFile();
|
||||
|
||||
void readInfo();
|
||||
|
@ -396,7 +402,7 @@ public:
|
|||
TileGenerator(VirtualTextureInfo* _info);
|
||||
~TileGenerator();
|
||||
|
||||
bool generate(const std::string& filename);
|
||||
bool generate(const bx::FilePath& filename);
|
||||
|
||||
private:
|
||||
void CopyTile(SimpleImage& image, Page request);
|
||||
|
|
Loading…
Reference in New Issue