This commit is contained in:
Dmitry 2021-08-04 00:11:49 +03:00
parent 3a8e683f01
commit 19e3df1de9
48 changed files with 286 additions and 303 deletions

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -120,7 +120,7 @@ void CommandBufferD3D12::EndRenderPass()
{
auto pCmdList = GetD3DGraphicsCommandList();
CD3DX12_RESOURCE_BARRIER barriers[VERUS_MAX_RT];
CD3DX12_RESOURCE_BARRIER barriers[VERUS_MAX_CA];
int barrierCount = 0;
int index = 0;
for (const auto& attachment : _pRenderPass->_vAttachments)
@ -138,7 +138,7 @@ void CommandBufferD3D12::EndRenderPass()
barriers[barrierCount++] = CD3DX12_RESOURCE_BARRIER::Transition(resources, _vAttachmentStates[index], attachment._finalState, subresource);
}
index++;
if (VERUS_MAX_RT == barrierCount)
if (VERUS_MAX_CA == barrierCount)
{
pCmdList->ResourceBarrier(barrierCount, barriers);
barrierCount = 0;
@ -157,16 +157,17 @@ void CommandBufferD3D12::BindVertexBuffers(GeometryPtr geo, UINT32 bindingsFilte
auto& geoD3D12 = static_cast<RGeometryD3D12>(*geo);
D3D12_VERTEX_BUFFER_VIEW views[VERUS_MAX_VB];
const int count = geoD3D12.GetVertexBufferCount();
int at = 0;
int filteredCount = 0;
VERUS_FOR(i, count)
{
if ((bindingsFilter >> i) & 0x1)
{
views[at] = *geoD3D12.GetD3DVertexBufferView(i);
at++;
VERUS_RT_ASSERT(filteredCount < VERUS_MAX_VB);
views[filteredCount] = *geoD3D12.GetD3DVertexBufferView(i);
filteredCount++;
}
}
GetD3DGraphicsCommandList()->IASetVertexBuffers(0, at, views);
GetD3DGraphicsCommandList()->IASetVertexBuffers(0, filteredCount, views);
}
void CommandBufferD3D12::BindIndexBuffer(GeometryPtr geo)
@ -200,7 +201,8 @@ void CommandBufferD3D12::SetViewport(std::initializer_list<Vector4> il, float mi
_viewportSize = Vector4(w, h, 1 / w, 1 / h);
}
CD3DX12_VIEWPORT vpD3D12[VERUS_MAX_RT];
VERUS_RT_ASSERT(il.size() <= VERUS_MAX_CA);
CD3DX12_VIEWPORT vpD3D12[VERUS_MAX_CA];
int count = 0;
for (const auto& rc : il)
vpD3D12[count++] = CD3DX12_VIEWPORT(rc.getX(), rc.getY(), rc.Width(), rc.Height(), minDepth, maxDepth);
@ -209,7 +211,8 @@ void CommandBufferD3D12::SetViewport(std::initializer_list<Vector4> il, float mi
void CommandBufferD3D12::SetScissor(std::initializer_list<Vector4> il)
{
CD3DX12_RECT rcD3D12[VERUS_MAX_RT];
VERUS_RT_ASSERT(il.size() <= VERUS_MAX_CA);
CD3DX12_RECT rcD3D12[VERUS_MAX_CA];
int count = 0;
for (const auto& rc : il)
rcD3D12[count++] = CD3DX12_RECT(
@ -346,6 +349,7 @@ void CommandBufferD3D12::PrepareSubpass()
const auto& ref = subpass._vInput[i];
if (_vAttachmentStates[ref._index] != ref._state)
{
VERUS_RT_ASSERT(barrierCount < VERUS_MAX_FB_ATTACH);
const auto& resources = fs._vResources[resIndex];
barriers[barrierCount++] = CD3DX12_RESOURCE_BARRIER::Transition(resources, _vAttachmentStates[ref._index], ref._state, subresource);
_vAttachmentStates[ref._index] = ref._state;
@ -357,6 +361,7 @@ void CommandBufferD3D12::PrepareSubpass()
const auto& ref = subpass._vColor[i];
if (_vAttachmentStates[ref._index] != ref._state)
{
VERUS_RT_ASSERT(barrierCount < VERUS_MAX_FB_ATTACH);
const auto& resources = fs._vResources[resIndex];
barriers[barrierCount++] = CD3DX12_RESOURCE_BARRIER::Transition(resources, _vAttachmentStates[ref._index], ref._state, subresource);
_vAttachmentStates[ref._index] = ref._state;
@ -368,6 +373,7 @@ void CommandBufferD3D12::PrepareSubpass()
const auto& ref = subpass._depthStencil;
if (_vAttachmentStates[ref._index] != ref._state)
{
VERUS_RT_ASSERT(barrierCount < VERUS_MAX_FB_ATTACH);
barriers[barrierCount++] = CD3DX12_RESOURCE_BARRIER::Transition(fs._vResources.back(), _vAttachmentStates[ref._index], ref._state, subresource);
_vAttachmentStates[ref._index] = ref._state;
}

View File

@ -84,15 +84,16 @@ void CommandBufferVulkan::BeginRenderPass(RPHandle renderPassHandle, FBHandle fr
vkrpbi.framebuffer = framebuffer._framebuffer;
vkrpbi.renderArea.extent.width = framebuffer._width;
vkrpbi.renderArea.extent.height = framebuffer._height;
VkClearValue clearValue[VERUS_MAX_FB_ATTACH] = {};
VkClearValue clearValues[VERUS_MAX_FB_ATTACH] = {};
VERUS_RT_ASSERT(ilClearValues.size() <= VERUS_MAX_FB_ATTACH);
int count = 0;
for (const auto& x : ilClearValues)
{
memcpy(clearValue[count].color.float32, x.ToPointer(), sizeof(clearValue[count].color.float32));
memcpy(clearValues[count].color.float32, x.ToPointer(), sizeof(clearValues[count].color.float32));
count++;
}
vkrpbi.clearValueCount = count;
vkrpbi.pClearValues = clearValue;
vkrpbi.pClearValues = clearValues;
vkCmdBeginRenderPass(GetVkCommandBuffer(), &vkrpbi, VK_SUBPASS_CONTENTS_INLINE);
if (setViewportAndScissor)
{
@ -118,17 +119,18 @@ void CommandBufferVulkan::BindVertexBuffers(GeometryPtr geo, UINT32 bindingsFilt
VkBuffer buffers[VERUS_MAX_VB];
VkDeviceSize offsets[VERUS_MAX_VB];
const int count = geoVulkan.GetVertexBufferCount();
int at = 0;
int filteredCount = 0;
VERUS_FOR(i, count)
{
if ((bindingsFilter >> i) & 0x1)
{
buffers[at] = geoVulkan.GetVkVertexBuffer(i);
offsets[at] = geoVulkan.GetVkVertexBufferOffset(i);
at++;
VERUS_RT_ASSERT(filteredCount < VERUS_MAX_VB);
buffers[filteredCount] = geoVulkan.GetVkVertexBuffer(i);
offsets[filteredCount] = geoVulkan.GetVkVertexBufferOffset(i);
filteredCount++;
}
}
vkCmdBindVertexBuffers(GetVkCommandBuffer(), 0, at, buffers, offsets);
vkCmdBindVertexBuffers(GetVkCommandBuffer(), 0, filteredCount, buffers, offsets);
}
void CommandBufferVulkan::BindIndexBuffer(GeometryPtr geo)
@ -156,7 +158,8 @@ void CommandBufferVulkan::SetViewport(std::initializer_list<Vector4> il, float m
_viewportSize = Vector4(w, h, 1 / w, 1 / h);
}
VkViewport vpVulkan[VERUS_MAX_RT];
VERUS_RT_ASSERT(il.size() <= VERUS_MAX_CA);
VkViewport vpVulkan[VERUS_MAX_CA];
int count = 0;
for (const auto& rc : il)
{
@ -173,7 +176,8 @@ void CommandBufferVulkan::SetViewport(std::initializer_list<Vector4> il, float m
void CommandBufferVulkan::SetScissor(std::initializer_list<Vector4> il)
{
VkRect2D rcVulkan[VERUS_MAX_RT];
VERUS_RT_ASSERT(il.size() <= VERUS_MAX_CA);
VkRect2D rcVulkan[VERUS_MAX_CA];
int count = 0;
for (const auto& rc : il)
{

View File

@ -117,7 +117,7 @@ void PipelineVulkan::Init(RcPipelineDesc desc)
depthStencilState.depthCompareOp = ToNativeCompareOp(desc._depthCompareOp);
depthStencilState.stencilTestEnable = desc._stencilTestEnable;
VkPipelineColorBlendAttachmentState vkpcbas[VERUS_MAX_RT] = {};
VkPipelineColorBlendAttachmentState vkpcbas[VERUS_MAX_CA] = {};
FillColorBlendAttachmentStates(desc, attachmentCount, vkpcbas);
VkPipelineColorBlendStateCreateInfo colorBlendState = {};
colorBlendState.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;

View File

@ -1175,7 +1175,7 @@ FBHandle RendererVulkan::CreateFramebuffer(RPHandle renderPassHandle, std::initi
{
VkResult res = VK_SUCCESS;
VkImageView imageViews[VERUS_MAX_RT] = {};
VkImageView imageViews[VERUS_MAX_FB_ATTACH] = {};
VkFramebuffer framebuffer = VK_NULL_HANDLE;
VkFramebufferCreateInfo vkfci = {};
vkfci.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO;
@ -1188,6 +1188,7 @@ FBHandle RendererVulkan::CreateFramebuffer(RPHandle renderPassHandle, std::initi
}
for (const auto& x : il)
{
VERUS_RT_ASSERT(count < VERUS_MAX_FB_ATTACH);
auto& texVulkan = static_cast<RTextureVulkan>(*x);
switch (cubeMapFace)
{

View File

@ -18,7 +18,7 @@ void Run()
LPWSTR* argArray = CommandLineToArgvW(GetCommandLine(), &argCount);
WideString pathnameW;
std::wcout << _T("TextureTool") << std::endl;
std::wcout << _T("Copyright (c) 2016-2020 Dmitry Maluev") << std::endl;
std::wcout << _T("Copyright (c) 2016-2021 Dmitry Maluev") << std::endl;
if (argCount < 2)
{
std::wcout << _T("Enter file name: ");
@ -87,7 +87,8 @@ void Run()
if (srcMipSet.m_nMipLevels <= 1)
CMP_GenerateMIPLevels(&srcMipSet, 0);
CMP_MipLevel* pMipLevel = srcMipSet.m_pMipLevelTable[0];
CMP_MipLevel* pMipLevel = nullptr;
CMP_GetMipLevel(&pMipLevel, &srcMipSet, 0, 0);
const BYTE* pData = pMipLevel->m_pbData;
const int pixelCount = srcMipSet.m_nWidth * srcMipSet.m_nHeight;
@ -273,12 +274,14 @@ void Run()
}
// Save shuffled mip level, read from inIndex:
CMP_MipLevel* pDstMipLevel = srcMipSet.m_pMipLevelTable[mip];
CMP_MipLevel* pDstMipLevel = nullptr;
CMP_GetMipLevel(&pDstMipLevel, &srcMipSet, mip, 0);
memcpy(pDstMipLevel->m_pbData, vMip[inIndex].data(), mipW * mipH * sizeof(UINT32));
}
else
{
CMP_MipLevel* pDstMipLevel = srcMipSet.m_pMipLevelTable[mip];
CMP_MipLevel* pDstMipLevel = nullptr;
CMP_GetMipLevel(&pDstMipLevel, &srcMipSet, mip, 0);
memcpy(pDstMipLevel->m_pbData, vMip[outIndex].data(), mipW * mipH * sizeof(UINT32));
}

View File

@ -3,8 +3,8 @@
<ImportGroup Label="PropertySheets" />
<PropertyGroup Label="UserMacros" />
<PropertyGroup>
<IncludePath>C:\Compressonator_3.2.4691\include;C:\Home\Projects\Verus\verus\Verus\src;C:\Home\Middleware\AMD Tootle 2.3\include;C:\Home\Middleware\bullet3-2.89\src;C:\Home\Middleware\bullet3-2.89\Extras;C:\Home\Middleware\libogg-1.3.4\include;C:\Home\Middleware\libvorbis-1.3.7\include;C:\Home\Middleware\openal-soft-1.20.1-bin\include;C:\Home\Middleware\SDL2-2.0.14\include;C:\VulkanSDK\1.2.182.0\Include;$(IncludePath)</IncludePath>
<LibraryPath>C:\Compressonator_3.2.4691\lib\VS2017\x64;C:\Home\Middleware\bullet3-2.89\bin;C:\Home\Middleware\AMD Tootle 2.3\lib;C:\Home\Middleware\libogg-1.3.4\lib;C:\Home\Middleware\libvorbis-1.3.7\lib2;C:\Home\Middleware\openal-soft-1.20.1-bin\libs\Win64;C:\Home\Middleware\SDL2-2.0.14\lib\x64;C:\VulkanSDK\1.2.182.0\Lib;$(LibraryPath)</LibraryPath>
<IncludePath>C:\Compressonator_4.2.5185\include;C:\Home\Projects\Verus\verus\Verus\src;C:\Home\Middleware\AMD Tootle 2.3\include;C:\Home\Middleware\bullet3-2.89\src;C:\Home\Middleware\bullet3-2.89\Extras;C:\Home\Middleware\libogg-1.3.4\include;C:\Home\Middleware\libvorbis-1.3.7\include;C:\Home\Middleware\openal-soft-1.20.1-bin\include;C:\Home\Middleware\SDL2-2.0.14\include;C:\VulkanSDK\1.2.182.0\Include;$(IncludePath)</IncludePath>
<LibraryPath>C:\Compressonator_4.2.5185\lib\VS2017\x64;C:\Home\Middleware\bullet3-2.89\bin;C:\Home\Middleware\AMD Tootle 2.3\lib;C:\Home\Middleware\libogg-1.3.4\lib;C:\Home\Middleware\libvorbis-1.3.7\lib2;C:\Home\Middleware\openal-soft-1.20.1-bin\libs\Win64;C:\Home\Middleware\SDL2-2.0.14\lib\x64;C:\VulkanSDK\1.2.182.0\Lib;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<ItemDefinitionGroup />
<ItemGroup />

View File

@ -66,7 +66,7 @@ Animation::~Animation()
{
}
void Animation::Update(int alphaTrackCount, PAlphaTrack pAlphaTracks)
void Animation::Update(int layerCount, PLayer pLayers)
{
VERUS_QREF_TIMER;
@ -75,22 +75,22 @@ void Animation::Update(int alphaTrackCount, PAlphaTrack pAlphaTracks)
_vTriggerStates.resize(_pCollection->GetMaxBones());
// Async BindSkeleton():
if (!_blendMotion.GetBoneCount() && _pSkeleton->GetBoneCount())
_pSkeleton->InsertBonesIntoMotion(_blendMotion);
if (!_transitionMotion.GetBoneCount() && _pSkeleton->GetBoneCount())
_pSkeleton->InsertBonesIntoMotion(_transitionMotion);
if (_playing)
{
float dt2 = dt;
if (_blending) // Still blending?
if (_transition) // Still in transition?
{
_blendTime += dt2;
if (_blendTime >= _blendDuration)
_transitionTime += dt2;
if (_transitionTime >= _transitionDuration)
{
_blending = false;
dt2 -= _blendTime - _blendDuration;
_transition = false;
dt2 -= _transitionTime - _transitionDuration;
}
}
if (!_blending && !_currentMotion.empty()) // Done blending?
if (!_transition && !_currentMotion.empty()) // Done transitioning?
{
RMotionData md = *_pCollection->Find(_C(_currentMotion));
const float duration = md._motion.GetDuration();
@ -102,44 +102,41 @@ void Animation::Update(int alphaTrackCount, PAlphaTrack pAlphaTracks)
_time = md._loop ? fmod(_time, duration) : duration;
md._motion.ResetTriggers(GetTriggerStatesArray()); // New loop, reset triggers.
if (_pDelegate)
_pDelegate->Animation_OnEnd(_C(_currentMotion)); // This can call BlendTo and change everything.
_pDelegate->Animation_OnEnd(_C(_currentMotion)); // This can call TransitionTo and change everything.
}
}
}
UpdateSkeleton(alphaTrackCount, pAlphaTracks);
UpdateSkeleton(layerCount, pLayers);
}
void Animation::UpdateSkeleton(int alphaTrackCount, PAlphaTrack pAlphaTracks)
void Animation::UpdateSkeleton(int layerCount, PLayer pLayers)
{
if (!_currentMotion.empty() && alphaTrackCount >= 0) // Alpha track (-1) should not modify the skeleton.
if (!_currentMotion.empty() && layerCount >= 0) // Special layer -1 should not modify the skeleton.
{
RMotionData md = *_pCollection->Find(_C(_currentMotion));
int alphaMotionCount = 0;
Skeleton::AlphaMotion alphaMotions[s_maxAlphaTracks];
int layeredMotionCount = 0;
Skeleton::LayeredMotion layeredMotions[s_maxLayers];
for (int i = 0; i < alphaTrackCount && i < s_maxAlphaTracks; ++i)
for (int i = 0; i < layerCount && i < s_maxLayers; ++i)
{
alphaMotions[i]._pMotion = pAlphaTracks[i]._pAnimation->GetMotion(); // Can be in blend state.
alphaMotions[i]._rootBone = pAlphaTracks[i]._rootBone;
alphaMotions[i]._alpha = pAlphaTracks[i]._pAnimation->GetAlpha();
alphaMotions[i]._time = pAlphaTracks[i]._pAnimation->GetTime();
alphaMotionCount++;
layeredMotions[i]._pMotion = pLayers[i]._pAnimation->GetMotion(); // Can be in blend state.
layeredMotions[i]._rootBone = pLayers[i]._rootBone;
layeredMotions[i]._alpha = pLayers[i]._pAnimation->GetAlpha();
layeredMotions[i]._time = pLayers[i]._pAnimation->GetTime();
layeredMotionCount++;
}
if (_blending)
if (_transition)
{
md._motion.BindBlendMotion(&_blendMotion, Math::ApplyEasing(_easing, _blendTime / _blendDuration));
_pSkeleton->ApplyMotion(md._motion, _time, alphaMotionCount, alphaMotions);
md._motion.BindBlendMotion(&_transitionMotion, Math::ApplyEasing(_easing, _transitionTime / _transitionDuration));
_pSkeleton->ApplyMotion(md._motion, _time, layeredMotionCount, layeredMotions);
}
else
{
#ifdef VERUS_COMPARE_MODE
_pSkeleton->ApplyMotion(md._motion, 0, alphaMotionCount, alphaMotions);
#else
_pSkeleton->ApplyMotion(md._motion, _time, alphaMotionCount, alphaMotions);
#endif
md._motion.BindBlendMotion(nullptr, 0);
_pSkeleton->ApplyMotion(md._motion, _time, layeredMotionCount, layeredMotions);
}
}
}
@ -170,36 +167,35 @@ void Animation::Pause()
_playing = false;
}
void Animation::BlendTo(CSZ name, Range<float> duration, int randTime, PMotion pFromMotion)
void Animation::TransitionTo(CSZ name, Range<float> duration, int randTime, PMotion pFromMotion)
{
VERUS_QREF_UTILS;
PMotion pMotion = pFromMotion;
if (!_currentMotion.empty() || pFromMotion)
if (!_currentMotion.empty() || pFromMotion) // Deal with previous motion?
{
if (!pFromMotion)
pMotion = &_pCollection->Find(_C(_currentMotion))->_motion;
if (_blending) // Already blending?
pMotion->BindBlendMotion(&_blendMotion, Math::ApplyEasing(_easing, _blendTime / _blendDuration));
pMotion->BakeMotionAt(_time, _blendMotion); // Capture current pose.
if (_transition) // Already in transition?
pMotion->BindBlendMotion(&_transitionMotion, Math::ApplyEasing(_easing, _transitionTime / _transitionDuration));
pMotion->BakeMotionAt(_time, _transitionMotion); // Capture current pose.
pMotion->BindBlendMotion(nullptr, 0);
}
if ((0 == duration._max) || (_currentMotion.empty() && name && _prevMotion == name && _blendTime / _blendDuration < 0.5f))
if ((0 == duration._max) || (_currentMotion.empty() && name && _prevMotion == name && _transitionTime / _transitionDuration < 0.5f))
{
_blending = false; // Special case for alpha tracks.
_transition = false; // Special case for layers.
}
else
{
_blending = true;
_blendDuration = (_currentMotion == (name ? name : "")) ? duration._min : duration._max;
_blendTime = 0;
_transition = true;
// Transition to same motion should be faster.
_transitionDuration = (_currentMotion == (name ? name : "")) ? duration._min : duration._max;
_transitionTime = 0;
}
_prevMotion = _currentMotion;
_currentMotion = name ? name : "";
// Reset triggers:
// Reset triggers, change motion:
if (pMotion)
pMotion->ResetTriggers(GetTriggerStatesArray());
if (name)
@ -216,14 +212,14 @@ void Animation::BlendTo(CSZ name, Range<float> duration, int randTime, PMotion p
_playing = true;
}
bool Animation::BlendToNew(std::initializer_list<CSZ> names, Range<float> duration, int randTime, PMotion pFromMotion)
bool Animation::TransitionToNew(std::initializer_list<CSZ> names, Range<float> duration, int randTime, PMotion pFromMotion)
{
for (auto name : names)
{
if (_currentMotion == name)
return false;
}
BlendTo(*names.begin(), duration, randTime, pFromMotion);
TransitionTo(*names.begin(), duration, randTime, pFromMotion);
return true;
}
@ -245,8 +241,8 @@ PMotion Animation::GetMotion()
{
p = &_pCollection->Find(_C(_currentMotion))->_motion;
}
if (p && _blending)
p->BindBlendMotion(&_blendMotion, Math::ApplyEasing(_easing, _blendTime / _blendDuration));
if (p && _transition)
p->BindBlendMotion(&_transitionMotion, Math::ApplyEasing(_easing, _transitionTime / _transitionDuration));
return p;
}
@ -259,8 +255,8 @@ float Animation::GetAlpha(CSZ name) const
matchCurrentMotion = Str::StartsWith(_C(_currentMotion), name);
matchPrevMotion = Str::StartsWith(_C(_prevMotion), name);
}
const bool doBlend = name ? (matchCurrentMotion || matchPrevMotion) : true;
if (_blending && doBlend)
const bool doTransition = name ? (matchCurrentMotion || matchPrevMotion) : true;
if (_transition && doTransition)
{
bool fadeIn = _prevMotion.empty() && !_currentMotion.empty();
bool fadeOut = !_prevMotion.empty() && _currentMotion.empty();
@ -270,9 +266,9 @@ float Animation::GetAlpha(CSZ name) const
fadeOut = matchPrevMotion && !matchCurrentMotion;
}
if (fadeIn)
return Math::ApplyEasing(_easing, _blendTime / _blendDuration);
return Math::ApplyEasing(_easing, _transitionTime / _transitionDuration);
if (fadeOut)
return Math::ApplyEasing(_easing, 1 - _blendTime / _blendDuration);
return Math::ApplyEasing(_easing, 1 - _transitionTime / _transitionDuration);
}
if (name)
return matchCurrentMotion ? 1.f : 0.f;

View File

@ -12,7 +12,7 @@ namespace verus
};
VERUS_TYPEDEFS(AnimationDelegate);
//! Objects of this type are stored in Collection.
// Objects of this type are stored in Collection.
struct MotionData
{
Motion _motion;
@ -22,7 +22,7 @@ namespace verus
VERUS_TYPEDEFS(MotionData);
typedef StoreUniqueWithNoRefCount<String, MotionData> TStoreMotions;
//! The collection of motion objects (Motion) that can be reused by multiple animation objects (Animation).
// The collection of motion objects that can be reused by multiple animation objects.
class Collection : private TStoreMotions, public IO::AsyncCallback
{
public:
@ -38,15 +38,12 @@ namespace verus
};
VERUS_TYPEDEFS(Collection);
//! Holds the collection (Collection) of motion objects (Motion) and provides the ability to interpolate between them.
//! Note: triggers will work properly with 'multiple animations' + 'single
//! collection' only if you add motions before binding collection.
//!
// Holds the collection of motion objects and provides the ability to interpolate between them.
// Note: triggers will work properly with 'multiple animations' + 'single collection' only if you add motions before binding collection.
class Animation : public MotionDelegate
{
public:
static const int s_maxAlphaTracks = 4;
static const int s_maxLayers = 8;
enum class Edge : int
{
@ -54,34 +51,34 @@ namespace verus
end = (1 << 1)
};
struct AlphaTrack
struct Layer
{
Animation* _pAnimation = nullptr;
CSZ _rootBone = nullptr;
};
VERUS_TYPEDEFS(AlphaTrack);
VERUS_TYPEDEFS(Layer);
private:
PCollection _pCollection = nullptr;
PAnimationDelegate _pDelegate = nullptr;
PSkeleton _pSkeleton = nullptr;
Motion _blendMotion;
Motion _transitionMotion;
String _currentMotion;
String _prevMotion;
Vector<int> _vTriggerStates;
Easing _easing = Easing::quadInOut;
float _time = 0;
float _blendDuration = 0;
float _blendTime = 0;
bool _blending = false;
float _transitionDuration = 0;
float _transitionTime = 0;
bool _transition = false;
bool _playing = false;
public:
Animation();
~Animation();
void Update(int alphaTrackCount = 0, PAlphaTrack pAlphaTracks = nullptr);
void UpdateSkeleton(int alphaTrackCount = 0, PAlphaTrack pAlphaTracks = nullptr);
void Update(int layerCount = 0, PLayer pLayers = nullptr);
void UpdateSkeleton(int layerCount = 0, PLayer pLayers = nullptr);
void BindCollection(PCollection p);
void BindSkeleton(PSkeleton p);
@ -94,11 +91,11 @@ namespace verus
Str GetCurrentMotionName() const { return _C(_currentMotion); }
void BlendTo(CSZ name,
void TransitionTo(CSZ name,
Range<float> duration = 0.5f, int randTime = -1, PMotion pFromMotion = nullptr);
bool BlendToNew(std::initializer_list<CSZ> names,
bool TransitionToNew(std::initializer_list<CSZ> names,
Range<float> duration = 0.5f, int randTime = -1, PMotion pFromMotion = nullptr);
bool IsBlending() const { return _blending; }
bool IsInTransition() const { return _transition; }
void SetEasing(Easing easing) { _easing = easing; }

View File

@ -1268,3 +1268,17 @@ int Motion::GetLastKeyframe() const
frame = Math::Max(frame, it->second.GetLastKeyframe());
return frame;
}
bool Motion::ExtractNestBone(CSZ name, SZ nestBone)
{
CSZ pBegin = strstr(name, "[");
CSZ pEnd = strstr(name, "]:");
if (pBegin && pEnd && pBegin < pEnd)
{
const size_t count = pEnd - pBegin - 1;
strncpy(nestBone, pBegin + 1, count);
nestBone[count] = 0;
return true;
}
return false;
}

View File

@ -11,12 +11,10 @@ namespace verus
};
VERUS_TYPEDEFS(MotionDelegate);
//! Motion holds a series of keyframes and provides the ability to interpolate between them.
//! Motion can be stored in XAN format. Motion's rate can be
//! scaled and even reversed. Animation object (Animation) can be used to
//! handle multiple motion objects.
//!
// Motion holds a series of keyframes and provides the ability to interpolate between them.
// Motion can be stored in XAN format.
// Motion's rate can be scaled and even reversed.
// Animation object can be used to handle multiple motion objects.
class Motion : public Object
{
public:
@ -62,10 +60,10 @@ namespace verus
String _name;
Motion* _pMotion = nullptr;
TMapRot _mapRot; //!< Rotation keyframes.
TMapPos _mapPos; //!< Position keyframes.
TMapScale _mapScale; //!< Scaling keyframes.
TMapTrigger _mapTrigger; //!< Trigger keyframes.
TMapRot _mapRot; // Rotation keyframes.
TMapPos _mapPos; // Position keyframes.
TMapScale _mapScale; // Scaling keyframes.
TMapTrigger _mapTrigger; // Trigger keyframes.
int _lastTriggerState = 0;
Flags _flags = Flags::none;
@ -336,6 +334,8 @@ namespace verus
void Exec(CSZ code, PBone pBone = nullptr, Bone::Channel channel = Bone::Channel::rotation);
int GetLastKeyframe() const;
static bool ExtractNestBone(CSZ name, SZ nestBone);
};
VERUS_TYPEDEFS(Motion);
}

View File

@ -5,10 +5,8 @@ namespace verus
{
namespace Anim
{
//! Shaker can load standard wav file, 8-bit mono, and use it as a function of time.
//! Works well for camera's shaking effects.
//!
// Shaker can load standard wav file, 8-bit mono, and use it as a function of time.
// Works well for camera's shaking effects.
class Shaker
{
Vector<float> _vData;
@ -26,7 +24,7 @@ namespace verus
void Update();
void Reset() { _offset = 0; }
void Randomize();
//! Returns the current value in the range [-1 to 1].
// Returns the current value in the range [-1 to 1].
float Get();
void SetScaleBias(float s, float b);
};

View File

@ -130,7 +130,7 @@ Skeleton::PBone Skeleton::FindBoneByIndex(int index)
return nullptr;
}
void Skeleton::ApplyMotion(RMotion motion, float time, int alphaMotionCount, PAlphaMotion pAlphaMotions)
void Skeleton::ApplyMotion(RMotion motion, float time, int layeredMotionCount, PLayeredMotion pLayeredMotions)
{
if (_ragdollMode)
{
@ -168,8 +168,8 @@ void Skeleton::ApplyMotion(RMotion motion, float time, int alphaMotionCount, PAl
if (_pCurrentMotion->IsReversed())
_currentTime = _pCurrentMotion->GetNativeDuration() - _currentTime;
_alphaMotionCount = alphaMotionCount;
_pAlphaMotions = pAlphaMotions;
_layeredMotionCount = layeredMotionCount;
_pLayeredMotions = pLayeredMotions;
ResetBones();
for (auto& kv : _mapBones)
@ -185,10 +185,10 @@ void Skeleton::ApplyMotion(RMotion motion, float time, int alphaMotionCount, PAl
// Reset blend motion!
motion.BindBlendMotion(nullptr, 0);
VERUS_FOR(i, _alphaMotionCount)
VERUS_FOR(i, _layeredMotionCount)
{
if (_pAlphaMotions[i]._pMotion)
_pAlphaMotions[i]._pMotion->BindBlendMotion(nullptr, 0);
if (_pLayeredMotions[i]._pMotion)
_pLayeredMotions[i]._pMotion->BindBlendMotion(nullptr, 0);
}
}
@ -233,32 +233,32 @@ void Skeleton::RecursiveBoneUpdate()
pMotionBone->ComputeScaleAt(_currentTime, scale);
// Blend with other motions:
VERUS_FOR(i, _alphaMotionCount)
VERUS_FOR(i, _layeredMotionCount)
{
if (!_pAlphaMotions[i]._pMotion)
if (!_pLayeredMotions[i]._pMotion)
continue;
PMotion pAlphaMotion = _pAlphaMotions[i]._pMotion;
Motion::PBone pAlphaBone = pAlphaMotion->FindBone(_C(pCurrentBone->_name));
const float alpha = _pAlphaMotions[i]._alpha;
float time = _pAlphaMotions[i]._time * pAlphaMotion->GetPlaybackSpeed(); // To native time.
if (pAlphaMotion->IsReversed())
time = pAlphaMotion->GetNativeDuration() - time;
if (pAlphaBone && alpha > 0 &&
(pCurrentBone->_name == _pAlphaMotions[i]._rootBone ||
IsParentOf(_C(pCurrentBone->_name), _pAlphaMotions[i]._rootBone)))
PMotion pLayeredMotion = _pLayeredMotions[i]._pMotion;
Motion::PBone pLayeredBone = pLayeredMotion->FindBone(_C(pCurrentBone->_name));
const float alpha = _pLayeredMotions[i]._alpha;
float time = _pLayeredMotions[i]._time * pLayeredMotion->GetPlaybackSpeed(); // To native time.
if (pLayeredMotion->IsReversed())
time = pLayeredMotion->GetNativeDuration() - time;
if (pLayeredBone && alpha > 0 &&
(pCurrentBone->_name == _pLayeredMotions[i]._rootBone ||
IsParentOf(_C(pCurrentBone->_name), _pLayeredMotions[i]._rootBone)))
{
// Alpha motion can also be in blend state.
Quat qA;
Vector3 scaleA, eulerA, posA;
pAlphaBone->ComputeRotationAt(time, eulerA, qA);
pAlphaBone->ComputePositionAt(time, posA);
pAlphaBone->ComputeScaleAt(time, scaleA);
// Layered motion can also be in blend state.
Quat qL;
Vector3 scaleL, eulerL, posL;
pLayeredBone->ComputeRotationAt(time, eulerL, qL);
pLayeredBone->ComputePositionAt(time, posL);
pLayeredBone->ComputeScaleAt(time, scaleL);
// Mix with alpha motion:
q = VMath::slerp(alpha, q, qA);
pos = VMath::lerp(alpha, pos, posA);
scale = VMath::lerp(alpha, scale, scaleA);
// Mix with layered motion:
q = VMath::slerp(alpha, q, qL);
pos = VMath::lerp(alpha, pos, posL);
scale = VMath::lerp(alpha, scale, scaleL);
}
}

View File

@ -5,32 +5,26 @@ namespace verus
{
namespace Anim
{
//! Standard skeleton, which can be animated using motion object (Motion).
//! X3D format can support up to 256 bones, but the hardware has certain
//! limitations. With Shader Model 2.0 the shader can hold about 32 bone
//! matrices. Other bones must be remapped using Primary Bones concept.
//!
//! Alpha Motions (AlphaMotion) add the ability to mix multiple motions,
//! just like images are mixed with alpha channel. Alpha Motion affects
//! it's root bone and all descendants of that bone.
//!
//! A ragdoll can be created automatically or configured using XML .rig file.
//! Ragdoll's simulation can start from any motion frame and any simulated pose
//! can be baked back into motion object, allowing smooth transition to ragdoll
//! simulation and back to motion.
//!
// Standard skeleton, which can be animated using motion object.
// X3D format can support up to 256 bones, but the hardware has certain limitations.
// With Shader Model 2.0 the shader can hold about 32 bone matrices.
// Other bones must be remapped using Primary Bones concept.
// Layered motions add the ability to mix multiple motions, just like images are mixed with alpha channel.
// Layered motion affects it's root bone and all descendants of that bone.
// A ragdoll can be created automatically or configured using XML .rig file.
// Ragdoll's simulation can start from any motion frame and any simulated pose can be baked back into motion object,
// allowing smooth transition to ragdoll simulation and back to motion.
class Skeleton : public Object
{
public:
struct AlphaMotion
struct LayeredMotion
{
PMotion _pMotion = nullptr;
CSZ _rootBone = nullptr;
float _alpha = 0;
float _time = 0;
};
VERUS_TYPEDEFS(AlphaMotion);
VERUS_TYPEDEFS(LayeredMotion);
struct Bone : AllocatorAware
{
@ -41,10 +35,10 @@ namespace verus
Transform3 _matExternal = Transform3::identity();
Transform3 _matAdapt = Transform3::identity();
Transform3 _matToActorSpace = Transform3::identity();
Vector3 _rigRot = Vector3(0); //!< Rotation angles of ragdoll's rigid component.
Vector3 _cRot = Vector3(0); //!< Constraint's rotation angles.
Vector3 _cLimits = Vector3(0); //!< Constraint's limits.
Vector3 _boxSize = Vector3(0); //!< For a box shape.
Vector3 _rigRot = Vector3(0); // Rotation angles of ragdoll's rigid component.
Vector3 _cRot = Vector3(0); // Constraint's rotation angles.
Vector3 _cLimits = Vector3(0); // Constraint's limits.
Vector3 _boxSize = Vector3(0); // For a box shape.
String _name;
String _parentName;
btCollisionShape* _pShape = nullptr;
@ -54,10 +48,10 @@ namespace verus
float _length = 0;
float _mass = 0;
float _friction = 0;
int _shaderIndex = 0; //!< Index of a matrix in the vertex shader.
int _shaderIndex = 0; // Index of a matrix in the vertex shader.
bool _ready = false;
bool _rigBone = true;
bool _hinge = false; //!< btHingeConstraint vs btConeTwistConstraint.
bool _hinge = false; // btHingeConstraint vs btConeTwistConstraint.
bool _noCollision = false;
};
VERUS_TYPEDEFS(Bone);
@ -73,11 +67,11 @@ namespace verus
TMapPrimary _mapPrimary;
PBone _pCurrentBone = nullptr;
PMotion _pCurrentMotion = nullptr;
PAlphaMotion _pAlphaMotions = nullptr;
PLayeredMotion _pLayeredMotions = nullptr;
float _currentTime = 0;
float _mass = 0;
int _primaryBoneCount = 0;
int _alphaMotionCount = 0;
int _layeredMotionCount = 0;
bool _ragdollMode = false;
public:
@ -96,14 +90,14 @@ namespace verus
PBone InsertBone(RBone bone);
PBone FindBone(CSZ name);
PcBone FindBone(CSZ name) const;
//! Uses shader's array index to find a bone.
// Uses shader's array index to find a bone.
PBone FindBoneByIndex(int index);
//! Sets the current pose using motion object (Motion).
// Sets the current pose using motion object (Motion).
void ApplyMotion(RMotion motion, float time,
int alphaMotionCount = 0, PAlphaMotion pAlphaMotions = nullptr);
int layeredMotionCount = 0, PLayeredMotion pLayeredMotions = nullptr);
//! Fills the array of matrices that will be used by a shader.
// Fills the array of matrices that will be used by a shader.
void UpdateUniformBufferArray(mataff* p) const;
void ResetFinalPose();
@ -128,9 +122,9 @@ namespace verus
return;
}
//! Adds skeleton's bones to motion object (Motion).
// Adds skeleton's bones to motion object (Motion).
void InsertBonesIntoMotion(RMotion motion) const;
//! Removes motion's bones, which are not skeleton's bones.
// Removes motion's bones, which are not skeleton's bones.
void DeleteOutsiders(RMotion motion) const;
void AdjustPrimaryBones(const Vector<String>& vPrimaryBones);
@ -145,7 +139,7 @@ namespace verus
bool IsRagdollMode() const { return _ragdollMode; }
RcTransform3 GetRagdollToWorldMatrix() { return _matRagdollToWorld; }
//! Saves the current pose into motion object (Motion) at some frame.
// Saves the current pose into motion object (Motion) at some frame.
void BakeMotion(RMotion motion, int frame = 0, bool kinect = false);
void AdaptBindPoseOf(const Skeleton& that);
void SimpleIK(CSZ boneDriven, CSZ boneDriver, RcVector3 dirDriverSpace, RcVector3 dirDesiredMeshSpace, float limitDot, float alpha);
@ -158,8 +152,8 @@ namespace verus
void FixateFeet(RMotion motion);
//! Tries to compute the highest speed at which a bone would move with this motion applied.
//! Can be used to sync animation and movement to fix the sliding feet problem.
// Tries to compute the highest speed at which a bone would move with this motion applied.
// Can be used to sync animation and movement to fix the sliding feet problem.
Vector3 GetHighestSpeed(RMotion motion, CSZ name, RcVector3 scale = Vector3(1, 0, 1), bool positive = false);
void ComputeBoneLengths(Map<String, float>& m, bool accumulated = false);

View File

@ -5,24 +5,17 @@ namespace verus
{
namespace Anim
{
//! Warp manages sphere-based deformations to create such effects like dangling and speech.
//! Any other part of the mesh can also be deformed.
//! Warp's zone objects (Zone) can use motion object or can simulate spring physics,
//! for example to simulate female's breast. Warp class includes a function to
//! convert special audio files to motion (ConvertAudioToMotion()).
//!
//! If there is a filename.wav, containing character's speech, some additional
//! files must be created:
//! 1. filename_Jaw.wav; effects: Stretch 400, Dynamic 10 Gate, 8000 8-bit.
//! 2. filename_O.wav; effects: Low pass 5000Hz, Keep O noise, Dynamic 10 Gate,
//! 8000 8-bit.
//! 3. filename_S.wav; effects: Keep S noise, Dynamic 10 Gate, Stretch 400,
//! 8000 8-bit.
//!
//! Motion should be applied to the skeleton before it will be used in Update()
//! method. Then _skeletonReady can be set to true for the mesh.
//!
// Warp manages sphere-based deformations to create such effects like dangling and speech.
// Any other part of the mesh can also be deformed.
// Warp's zone objects can use motion object or can simulate spring physics,
// for example to simulate female's breast.
// Warp class includes a function to convert special audio files to motion.
// If there is a filename.wav, containing character's speech, some additional files must be created:
// 1. filename_Jaw.wav; effects: Stretch 400, Dynamic 10 Gate, 8000 8-bit.
// 2. filename_O.wav; effects: Low pass 5000Hz, Keep O noise, Dynamic 10 Gate, 8000 8-bit.
// 3. filename_S.wav; effects: Keep S noise, Dynamic 10 Gate, Stretch 400, 8000 8-bit.
// Motion should be applied to the skeleton before it will be used in Update() method.
// Then _skeletonReady can be set to true for the mesh.
class Warp : public Object
{
public:

View File

@ -244,7 +244,7 @@ void StreamPlayer::ThreadProc()
int processed;
alGetSourcei(_source, AL_BUFFERS_PROCESSED, &processed);
#ifdef VERUS_RELEASE_DEBUG
#ifdef _DEBUG
char debug[80];
sprintf_s(debug, "ThreadProc() processed=%d", processed);
VERUS_LOG_DEBUG(debug);

View File

@ -10,8 +10,8 @@ namespace verus
GeometryPtr _geometry;
ShaderPtr _shader;
CSZ _shaderBranch = nullptr;
String _colorAttachBlendEqs[VERUS_MAX_RT];
String _colorAttachWriteMasks[VERUS_MAX_RT];
String _colorAttachBlendEqs[VERUS_MAX_CA];
String _colorAttachWriteMasks[VERUS_MAX_CA];
PipelineRasterizationState _rasterizationState;
PrimitiveTopology _topology = PrimitiveTopology::triangleList;
int _sampleCount = 1;

View File

@ -5,7 +5,7 @@ namespace verus
{
namespace D
{
//! See: https://marknelson.us/posts/2007/11/13/no-exceptions.html
// See: https://marknelson.us/posts/2007/11/13/no-exceptions.html
class RuntimeError : public std::exception
{
mutable StringStream _ss;

View File

@ -5,10 +5,9 @@ namespace verus
{
namespace GUI
{
//! Module for drawing texture-based fonts.
//! Use AngelCode Bitmap Font Generator to create required files.
//! Geometry uses -32767 to 32767 short texture coordinates.
// Module for drawing texture-based fonts.
// Use AngelCode Bitmap Font Generator to create required files.
// Geometry uses -32767 to 32767 short texture coordinates.
class Font : public Object
{
public:

View File

@ -27,10 +27,9 @@ namespace verus
};
VERUS_TYPEDEFS(ViewDelegate);
//! Views contain other controls.
//! By default they have "done" state.
//! You should call ViewManager::FadeTo() after loading.
// Views contain other controls.
// By default they have "done" state.
// You should call ViewManager::FadeTo() after loading.
class View : public Widget, public Container
{
friend class ViewManager;

View File

@ -5,10 +5,9 @@ namespace verus
{
namespace GUI
{
//! Ultimate GUI manager.
//! Contains views ordered by z-depth.
//! Contains fonts, cursor and GUI utility functions.
// Ultimate GUI manager.
// Contains views ordered by z-depth.
// Contains fonts, cursor and GUI utility functions.
typedef StoreUniqueWithNoRefCount<String, Font> TStoreFonts;
class ViewManager : public Singleton<ViewManager>, public Object, private TStoreFonts
{

View File

@ -26,12 +26,10 @@ namespace verus
typedef std::function<void(RcEventArgs)> TFnEvent;
//! Base class for all controls and even frames.
//! Control has position, size, id text, value text (for buttons, labels, etc.).
//! It can be enabled/disabled, visible/hidden.
//! Control belongs to certain view and it's position is relative to sizer or
//! owner view if no sizer is specified.
// Base class for all controls and even frames.
// Control has position, size, id text, value text (for buttons, labels, etc.).
// It can be enabled/disabled, visible/hidden.
// Control belongs to certain view and it's position is relative to sizer or owner view if no sizer is specified.
class Widget : public AllocatorAware
{
Animator _animator;

View File

@ -32,8 +32,8 @@ namespace verus
virtual void HandleInput() override;
virtual void Update() override;
//! Creates the underlying controller (Physics::CharacterController).
//! EndRagdoll() calls this method automatically.
// Creates the underlying controller.
// EndRagdoll() calls this method automatically.
void InitController();
void DoneController();
Physics::RCharacterController GetController() { return _cc; }
@ -62,9 +62,9 @@ namespace verus
void AddExtraForce(RcVector3 v) { _extraForce += v; }
// For AI:
//! Check if the speed is less than expected.
// Check if the speed is less than expected.
bool IsStuck();
//! Is typically called when AI gets a new task.
// Is typically called when AI gets a new task.
void StartUnstuckCooldown() { _unstuckCooldown.Start(); }
// Ragdoll:

View File

@ -85,7 +85,7 @@ namespace verus
RcVector3 GetSideDirection() const { return _dv._sideDir; }
RcVector3 GetSideDirection2D() const { return _dv._sideDir2D; }
//! Rotates smoothly across multiple frames.
// Rotates smoothly across multiple frames.
void Rotate(RcVector3 front, float speed);
void LookAt(RcPoint3 point, bool forceTarget = false);

View File

@ -3,7 +3,7 @@
namespace verus
{
//! This allocator will reserve aligned memory blocks.
// This allocator will reserve aligned memory blocks.
class AlignedAllocator : public BaseAllocator
{
INT64 _memUsedTotal = 0;

View File

@ -3,7 +3,7 @@
namespace verus
{
//! Objects of this class will use the allocator provided by Utils.
// Objects of this class will use the allocator provided by Utils.
class AllocatorAware
{
public:

View File

@ -3,7 +3,7 @@
namespace verus
{
//! Uses a single, fixed-size buffer as if it was connected end-to-end.
// Uses a single, fixed-size buffer as if it was connected end-to-end.
class BaseCircularBuffer
{
BYTE* _pBase = nullptr;

View File

@ -3,7 +3,7 @@
namespace verus
{
//! This class converts different data types.
// This class converts different data types.
class Convert
{
public:

View File

@ -3,7 +3,7 @@
namespace verus
{
//! This class can transfer singleton pointers to another library.
// This class can transfer singleton pointers to another library.
class GlobalVarsClipboard
{
struct Pair

View File

@ -80,10 +80,10 @@
#define VERUS_UBUFFER struct alignas(VERUS_MEMORY_ALIGNMENT)
#define VERUS_MAX_BONES 128
#define VERUS_MAX_RT 8
#define VERUS_MAX_FB_ATTACH (VERUS_MAX_RT * 4)
#define VERUS_MAX_VB 8
#define VERUS_MAX_BONES 128
#define VERUS_MAX_CA 8 // Maximum number of color attachments per subpass, similar to D3D12_SIMULTANEOUS_RENDER_TARGET_COUNT.
#define VERUS_MAX_FB_ATTACH 32 // Maximum number of attachments per framebuffer. Includes color and other attachments for all subpasses.
#define VERUS_MAX_VB 8 // Maximum number of vertex buffer bindings per draw call.
#define VERUS_COLOR_BLEND_OFF "off"
#define VERUS_COLOR_BLEND_ALPHA "s*(sa)+d*(1-sa)"

View File

@ -3,7 +3,7 @@
namespace verus
{
//! Custom allocator for the Standard Template Library. Will try to use the allocator provided by Utils.
// Custom allocator for the Standard Template Library. Will try to use the allocator provided by Utils.
template<typename T>
class AllocatorAwareSTL
{
@ -72,14 +72,14 @@ namespace verus
}
};
//! This function will compare two allocators.
// This function will compare two allocators.
template<typename T>
bool operator==(const AllocatorAwareSTL<T>& l, const AllocatorAwareSTL<T>& r)
{
return true;
}
//! This function will compare two allocators.
// This function will compare two allocators.
template<typename T>
bool operator!=(const AllocatorAwareSTL<T>& l, const AllocatorAwareSTL<T>& r)
{

View File

@ -5,7 +5,7 @@ extern int g_singletonAllocCount;
namespace verus
{
//! Restricts the instantiation of a class to one object.
// Restricts the instantiation of a class to one object.
template<typename T>
class Singleton : public AllocatorAware
{

View File

@ -3,18 +3,15 @@
namespace verus
{
//! A convenient way to store a collection of objects.
//! It's a good idea not to use new/delete explicitly. Use STL allocator.
//! 'Unique' class uses map and supports reference counting.
//! The Insert method returns a raw pointer which should be wrapped inside a Ptr.
//!
//! Types of pointers:
//! - raw pointer - very dumb, no automatic initialization.
//! - Ptr wrapper - like a smart pointer, but even smarter.
//! - Pwn wrapper - owning Ptr, basically calls Done in destructor.
//! Use Ptr for function parameters. Use Pwn for class members.
//!
// A convenient way to store a collection of objects.
// It's a good idea not to use new/delete explicitly. Use STL allocator.
// 'Unique' class uses map and supports reference counting.
// The Insert method returns a raw pointer which should be wrapped inside a Ptr.
// Types of pointers:
// - raw pointer - very dumb, no automatic initialization.
// - Ptr wrapper - like a smart pointer, but even smarter.
// - Pwn wrapper - owning Ptr, basically calls Done in destructor.
// Use Ptr for function parameters. Use Pwn for class members.
template<typename TValue>
class Store
{

View File

@ -18,9 +18,9 @@ namespace verus
Utils(PBaseAllocator pAlloc);
~Utils();
//! Construct Utils using the provided allocator:
// Construct Utils using the provided allocator:
static void MakeEx(PBaseAllocator pAlloc);
//! Destruct Utils using the provided allocator:
// Destruct Utils using the provided allocator:
static void FreeEx(PBaseAllocator pAlloc);
// Called from BaseGame::Initialize():

View File

@ -11,10 +11,10 @@ namespace verus
};
VERUS_TYPEDEFS(AsyncCallback);
//! Load resources asynchronously.
//! Load method just adds the url to a queue.
//! Load and Cancel are virtual so that they can be safely called from another
//! DLL. Internally they can allocate and free memory.
// Load resources asynchronously.
// Load method just adds the url to a queue.
// Load and Cancel are virtual so that they can be safely called from another DLL.
// Internally they can allocate and free memory.
class Async : public Singleton<Async>, public Object, public Lockable
{
public:

View File

@ -5,8 +5,7 @@ namespace verus
{
namespace IO
{
//! Treat a file as a stream.
//!
// Treat a file as a stream.
class File : public SeekableStream
{
FILE* _pFile = nullptr;

View File

@ -5,7 +5,7 @@ namespace verus
{
namespace Net
{
//! Holds IP address and port.
// Holds IP address and port.
class Addr
{
public:
@ -22,13 +22,13 @@ namespace verus
bool operator==(const Addr& that) const;
//! Returns localhost address 127.0.0.1.
// Returns localhost address 127.0.0.1.
static Addr Localhost(int port = 0);
bool IsNull() const { return !_addr || !_port; }
bool IsLocalhost() const;
//! Accepts IP:Port or URL, which is resolved using getaddrinfo().
// Accepts IP:Port or URL, which is resolved using getaddrinfo().
void FromString(CSZ addr);
String ToString(bool addPort = false) const;

View File

@ -5,7 +5,7 @@ namespace verus
{
namespace Net
{
//! Provides ability to read files from the internet using HTTP.
// Provides ability to read files from the internet using HTTP.
class HttpFile : public IO::Stream
{
static const int s_httpPort = 80;

View File

@ -128,14 +128,14 @@ namespace verus
int ReservePlayer();
void CancelReservation(int id);
//! Writes the report into the send buffer for some or all players. This will eventually send this report.
//! \param id Player's ID. Use -1 to send the report to all players. Server cannot send the report to itself.
//! \param p Pointer to report's data. Must not be less than the size of the report.
//! \param deferred Will send it as soon as possible if false.
// Writes the report into the send buffer for some or all players. This will eventually send this report.
// id = Player's ID. Use -1 to send the report to all players. Server cannot send the report to itself.
// p = Pointer to report's data. Must not be less than the size of the report.
// deferred = Will send it as soon as possible if false.
void SendReportAsync(int id, BYTE* p, bool deferred = false);
//! Reads reports from recv buffers, cleans them, calls MultiplayerDelegate's callbacks.
// Reads reports from recv buffers, cleans them, calls MultiplayerDelegate's callbacks.
void ProcessRecvBuffers();
//! Writes the KICK report to the player's send buffer. This will eventually kick the specified player.
// Writes the KICK report to the player's send buffer. This will eventually kick the specified player.
void Kick(int id);
VERUS_P(int GetIdByAddr(RcAddr addr) const);

View File

@ -47,13 +47,7 @@ void Camera::Update()
void Camera::UpdateView()
{
_frontDir = VMath::normalizeApprox(_atPos - _eyePos);
#ifdef VERUS_COMPARE_MODE
_frontDir = VMath::normalizeApprox(Vector3(glm::round(m_dirFront.GLM() * glm::vec3(4, 4, 4))));
_eyePos = Point3(int(_eyePos.getX()), int(_eyePos.getY()), int(_eyePos.getZ()));
_matV = Matrix4::lookAt(_eyePos, _eyePos + _frontDir, _upDir);
#else
_matV = Matrix4::lookAt(_eyePos, _atPos, _upDir);
#endif
_matVi = VMath::orthoInverse(_matV);
}

View File

@ -5,7 +5,7 @@ namespace verus
{
namespace Scene
{
//! Basic camera without extra features. For shadow map computations, etc.
// Basic camera without extra features. For shadow map computations, etc.
class Camera
{
protected:
@ -100,14 +100,14 @@ namespace verus
};
VERUS_TYPEDEFS(Camera);
//! The interface for getting the cursor's position.
// The interface for getting the cursor's position.
struct CursorPosProvider
{
virtual void GetPos(int& x, int& y) = 0;
};
VERUS_TYPEDEFS(CursorPosProvider);
//! More advanced camera, used to show the world to the user. With motion blur.
// More advanced camera, used to show the world to the user. With motion blur.
class MainCamera : public Camera
{
Matrix4 _matPrevVP = Matrix4::identity(); // For motion blur.

View File

@ -21,8 +21,8 @@ namespace verus
};
VERUS_TYPEDEFS(BlockEmitter);
//! Block is a scene node which has a model and material info.
//! Most blocks form the scene's so called static or immovable geometry.
// Block is a scene node which has a model and material info.
// Most blocks form the scene's so called static or immovable geometry.
class Block : public SceneNode
{
Vector4 _userColor = Vector4(0);

View File

@ -17,7 +17,7 @@ namespace verus
};
VERUS_TYPEDEFS(LightData);
//! Light is a scene node with light's info.
// Light is a scene node with light's info.
class Light : public SceneNode
{
LightData _data;

View File

@ -5,10 +5,10 @@ namespace verus
{
namespace Scene
{
//! Model is an element of the scene manager container
//! * has a mesh
//! * has a material
//! * has generic parameters
// Model is an element of the scene manager container
// * has a mesh
// * has a material
// * has generic parameters
class Model : public Object
{
Mesh _mesh;

View File

@ -5,17 +5,17 @@ namespace verus
{
namespace Scene
{
//! SceneNode is an element of the scene manager container.
//! * has a name
//! * can be parent or child
//! * has generic parameters
//! * has bounds
// SceneNode is an element of the scene manager container.
// * has a name
// * can be parent or child
// * has generic parameters
// * has bounds
class SceneNode : public AllocatorAware, public Physics::UserPtr
{
protected:
Transform3 _tr = Transform3::identity(); //!< Main transformation matrix.
Vector3 _uiRotation = Vector3(0); //!< User-friendly rotation used in editor's UI.
Vector3 _uiScale = Vector3(1, 1, 1); //!< User-friendly scale used in editor's UI.
Transform3 _tr = Transform3::identity(); // Main transformation matrix.
Vector3 _uiRotation = Vector3(0); // User-friendly rotation used in editor's UI.
Vector3 _uiScale = Vector3(1, 1, 1); // User-friendly scale used in editor's UI.
Math::Bounds _bounds;
IO::Dictionary _dict;
String _name;
@ -24,7 +24,7 @@ namespace verus
NodeType _type = NodeType::unknown;
bool _dynamic = false;
bool _hidden = false;
bool _octreeBindOnce = false; //!< Don't rebind this node after every bounds change.
bool _octreeBindOnce = false; // Don't rebind this node after every bounds change.
bool _selected = false;
bool _transient = false;
@ -71,9 +71,9 @@ namespace verus
virtual void RestoreTransform(RcTransform3 tr, RcVector3 rot, RcVector3 scale);
VERUS_P(void ComputeTransform());
Point3 GetPosition() const; //!< Gets the position from the main transformation matrix.
Vector3 GetRotation() const; //!< Gets the user-friendly rotation.
Vector3 GetScale() const; //!< Gets the user-friendly scale.
Point3 GetPosition() const; // Gets the position from the main transformation matrix.
Vector3 GetRotation() const; // Gets the user-friendly rotation.
Vector3 GetScale() const; // Gets the user-friendly scale.
virtual void MoveTo(RcPoint3 pos);
virtual void RotateTo(RcVector3 v);
virtual void ScaleTo(RcVector3 v);

View File

@ -10,21 +10,13 @@
// System:
#ifdef _WIN32
# pragma comment(lib, "ws2_32.lib")
# include <WS2tcpip.h>
# include <Shlwapi.h>
# pragma comment(lib, "Shlwapi.lib")
# include <shellapi.h>
# include <ShlObj.h>
# include <ShellScalingAPI.h>
# pragma comment(lib, "Shcore.lib")
//# pragma comment(lib, "shell32.lib")
//# define _WIN32_DCOM
//# include <comdef.h>
//# include <wbemidl.h>
//# pragma comment(lib, "wbemuuid.lib")
# include <tchar.h>
# include <mmsystem.h>
# include <ShellScalingApi.h>
# include <Shlwapi.h>
# pragma comment(lib, "WS2_32.lib")
# pragma comment(lib, "ShLwApi.lib")
# pragma comment(lib, "shcore.lib")
#else
# include <dlfcn.h>
#endif
@ -59,7 +51,7 @@ using namespace Microsoft::WRL;
# pragma comment(lib, "d3dcompiler.lib")
# pragma comment(lib, "dxgi.lib")
# pragma comment(lib, "dxguid.lib")
# include "ThirdParty/d3dx12.h" // See: https://github.com/microsoft/DirectX-Graphics-Samples/tree/master/Libraries/D3DX12
# include "ThirdParty/d3dx12.h" // See: https://github.com/microsoft/DirectX-Headers/tree/main/include/directx
# include "ThirdParty/D3D12MemAlloc.h" // See: https://github.com/GPUOpen-LibrariesAndSDKs/D3D12MemoryAllocator
#endif
@ -100,9 +92,9 @@ using namespace Microsoft::WRL;
# pragma comment(lib, "libvorbisfile.lib")
#endif
// AMD Compressonator:
// AMD Compressonator (use CompressonatorFrameWork_x64):
#ifdef VERUS_INCLUDE_COMPRESSONATOR
# include <CMP_Framework.h>
# include <compressonator.h>
# pragma comment(lib, "CMP_Framework_MD_DLL.lib")
#endif