|
|
@@ -11,7 +11,10 @@ namespace anki
|
|
|
|
|
|
MicroSampler::~MicroSampler()
|
|
|
{
|
|
|
- // TODO
|
|
|
+ if(m_handle)
|
|
|
+ {
|
|
|
+ vkDestroySampler(m_factory->m_gr->getDevice(), m_handle, nullptr);
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
GrAllocator<U8> MicroSampler::getAllocator() const
|
|
|
@@ -21,26 +24,110 @@ GrAllocator<U8> MicroSampler::getAllocator() const
|
|
|
|
|
|
Error MicroSampler::init(const SamplerInitInfo& inf)
|
|
|
{
|
|
|
- // TODO
|
|
|
+ // Fill the create cio
|
|
|
+ VkSamplerCreateInfo ci = {};
|
|
|
+ ci.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO;
|
|
|
+
|
|
|
+ if(inf.m_minMagFilter == SamplingFilter::NEAREST)
|
|
|
+ {
|
|
|
+ ci.magFilter = ci.minFilter = VK_FILTER_NEAREST;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ ANKI_ASSERT(inf.m_minMagFilter == SamplingFilter::LINEAR);
|
|
|
+ ci.magFilter = ci.minFilter = VK_FILTER_LINEAR;
|
|
|
+ }
|
|
|
+
|
|
|
+ if(inf.m_mipmapFilter == SamplingFilter::BASE || inf.m_mipmapFilter == SamplingFilter::NEAREST)
|
|
|
+ {
|
|
|
+ ci.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ ci.mipmapMode = VK_SAMPLER_MIPMAP_MODE_LINEAR;
|
|
|
+ }
|
|
|
+
|
|
|
+ if(inf.m_repeat)
|
|
|
+ {
|
|
|
+ ci.addressModeU = ci.addressModeV = ci.addressModeW = VK_SAMPLER_ADDRESS_MODE_REPEAT;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ ci.addressModeU = ci.addressModeV = ci.addressModeW = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE;
|
|
|
+ }
|
|
|
+
|
|
|
+ ci.mipLodBias = 0.0;
|
|
|
+
|
|
|
+ if(inf.m_anisotropyLevel > 0)
|
|
|
+ {
|
|
|
+ ci.anisotropyEnable = VK_TRUE;
|
|
|
+ ci.maxAnisotropy = inf.m_anisotropyLevel;
|
|
|
+ }
|
|
|
+
|
|
|
+ ci.compareOp = convertCompareOp(inf.m_compareOperation);
|
|
|
+ if(ci.compareOp != VK_COMPARE_OP_ALWAYS)
|
|
|
+ {
|
|
|
+ ci.compareEnable = VK_TRUE;
|
|
|
+ }
|
|
|
+
|
|
|
+ ci.minLod = inf.m_minLod;
|
|
|
+ ci.maxLod = inf.m_maxLod;
|
|
|
+
|
|
|
+ ci.unnormalizedCoordinates = VK_FALSE;
|
|
|
+
|
|
|
+ // Create
|
|
|
+ ANKI_VK_CHECK(vkCreateSampler(m_factory->m_gr->getDevice(), &ci, nullptr, &m_handle));
|
|
|
+ m_factory->m_gr->trySetVulkanHandleName(inf.getName(), VK_DEBUG_REPORT_OBJECT_TYPE_SAMPLER_EXT, m_handle);
|
|
|
+
|
|
|
return Error::NONE;
|
|
|
}
|
|
|
|
|
|
Error SamplerFactory::init(GrManagerImpl* gr)
|
|
|
{
|
|
|
ANKI_ASSERT(gr);
|
|
|
- // TODO
|
|
|
+ ANKI_ASSERT(!m_gr);
|
|
|
+ m_gr = gr;
|
|
|
+ m_recycler.init(gr->getAllocator());
|
|
|
+
|
|
|
return Error::NONE;
|
|
|
}
|
|
|
|
|
|
void SamplerFactory::destroy()
|
|
|
{
|
|
|
- // TODO
|
|
|
+ m_recycler.destroy();
|
|
|
+ m_gr = nullptr;
|
|
|
}
|
|
|
|
|
|
Error SamplerFactory::newInstance(const SamplerInitInfo& inf, MicroSamplerPtr& psampler)
|
|
|
{
|
|
|
- // TODO
|
|
|
- return Error::NONE;
|
|
|
+ ANKI_ASSERT(m_gr);
|
|
|
+
|
|
|
+ Error err = Error::NONE;
|
|
|
+ MicroSampler* out = m_recycler.findToReuse();
|
|
|
+
|
|
|
+ if(out == nullptr)
|
|
|
+ {
|
|
|
+ // Create a new one
|
|
|
+
|
|
|
+ GrAllocator<U8> alloc = m_gr->getAllocator();
|
|
|
+
|
|
|
+ out = alloc.newInstance<MicroSampler>(this);
|
|
|
+ err = out->init(inf);
|
|
|
+
|
|
|
+ if(err)
|
|
|
+ {
|
|
|
+ alloc.deleteInstance(out);
|
|
|
+ out = nullptr;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if(!err)
|
|
|
+ {
|
|
|
+ ANKI_ASSERT(out->m_refcount.get() == 0);
|
|
|
+ psampler.reset(out);
|
|
|
+ }
|
|
|
+
|
|
|
+ return err;
|
|
|
}
|
|
|
|
|
|
} // end namespace anki
|