浏览代码

The first Vulkan commit is now live: Implementing Sampler

Panagiotis Christopoulos Charitos 9 年之前
父节点
当前提交
e089e380b5

+ 17 - 3
CMakeLists.txt

@@ -89,7 +89,15 @@ set(ANKI_EXTRA_LIB_DIRS CACHE STRING "Some extra lib paths (Needed for some weir
 # Valgrind
 option(ANKI_VALGRIND_HAPPY "Make valgrind happy" OFF)
 
-set(ANKI_GR_BACKEND "GL" CACHE STRING "The graphics API (GL or VULKAN)")
+set(ANKI_GR_BACKEND "GL" CACHE STRING "The graphics API (GL or vulkan)")
+
+if(${ANKI_GR_BACKEND} STREQUAL "GL")
+	set(GL TRUE)
+	set(VULKAN FALSE)
+else()
+	set(GL FALSE)
+	set(VULKAN TRUE)
+endif()
 
 ################################################################################
 # Compiler & linker flags                                                      #
@@ -197,7 +205,7 @@ include(ExternalProject)
 
 set(ANKI_EXTERN_SUB_DIRS tinyxml2 lua z newton)
 
-if(LINUX OR MACOS OR WINDOWS)
+if((LINUX OR MACOS OR WINDOWS) AND GL)
 	set(ANKI_EXTERN_SUB_DIRS ${ANKI_EXTERN_SUB_DIRS} GLEW)
 endif()
 
@@ -306,7 +314,13 @@ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -pedantic -Wall -W -Wextra -Wstrict-alia
 
 # Set platform specific
 if(LINUX)
-	set(_SYS GL ankiglew pthread dl)
+	if(GL)
+		set(_SYS ${ANKI_GR_BACKEND} ankiglew)
+	else()
+		set(_SYS vulkan)
+	endif()
+
+	set(_SYS ${_SYS} pthread dl)
 elseif(MACOS)
 	find_package(OpenGL REQUIRED)
 	set(_SYS ${OPENGL_LIBRARIES} ankiglew pthread)

+ 28 - 0
include/anki/gr/vulkan/Common.h

@@ -6,3 +6,31 @@
 #pragma once
 
 #include <anki/gr/Common.h>
+#include <vulkan/vulkan.h>
+
+namespace anki
+{
+
+/// @addtogroup vulkan
+/// @{
+
+/// Check if a vulkan function failed.
+#define ANKI_VK_CHECK(x)                                                       \
+	do                                                                         \
+	{                                                                          \
+		VkResult rez = x;                                                      \
+		if(rez != VK_SUCCESS)                                                  \
+		{                                                                      \
+			ANKI_LOGF("Vulkan function failed: %s at (%s:%d %s)",              \
+				#x,                                                            \
+				ANKI_FILE,                                                     \
+				__LINE__,                                                      \
+				ANKI_FUNC);                                                    \
+		}                                                                      \
+	} while(0)
+
+/// Convert compare op.
+VkCompareOp convertCompareOp(CompareOperation ak);
+/// @}
+
+} // end namespace anki

+ 7 - 0
include/anki/gr/vulkan/GrManagerImpl.h

@@ -17,6 +17,10 @@ namespace anki
 class GrManagerImpl
 {
 public:
+	VkInstance m_instance = VK_NULL_HANDLE;
+	VkDevice m_device = VK_NULL_HANDLE;
+	VkQueue m_queue = VK_NULL_HANDLE;
+
 	GrManagerImpl(GrManager* manager)
 		: m_manager(manager)
 	{
@@ -24,6 +28,9 @@ public:
 	}
 
 	~GrManagerImpl();
+
+private:
+	GrManager* m_manager = nullptr;
 };
 /// @}
 

+ 2 - 0
include/anki/gr/vulkan/SamplerImpl.h

@@ -17,6 +17,8 @@ namespace anki
 class SamplerImpl : public VulkanObject
 {
 public:
+	VkSampler m_sampler = VK_NULL_HANDLE;
+
 	SamplerImpl(GrManager* manager)
 		: VulkanObject(manager)
 	{

+ 3 - 1
include/anki/gr/vulkan/VulkanObject.h

@@ -27,7 +27,9 @@ public:
 	{
 	}
 
-private:
+	VkDevice getDevice() const;
+
+protected:
 	GrManager* m_manager = nullptr;
 };
 /// @}

+ 1 - 1
src/gr/CMakeLists.txt

@@ -1,6 +1,6 @@
 file(GLOB ANKI_GR_SOURCES *.cpp)
 
-if(${ANKI_GR_BACKEND} STREQUAL "GL")
+if(GL)
 	file(GLOB ANKI_GR_BACKEND_SOURCES gl/*.cpp)
 else()
 	file(GLOB ANKI_GR_BACKEND_SOURCES vulkan/*.cpp)

+ 49 - 0
src/gr/vulkan/Common.cpp

@@ -0,0 +1,49 @@
+// Copyright (C) 2009-2016, Panagiotis Christopoulos Charitos.
+// All rights reserved.
+// Code licensed under the BSD License.
+// http://www.anki3d.org/LICENSE
+
+#include <anki/gr/vulkan/Common.h>
+
+namespace anki 
+{
+
+//==============================================================================
+VkCompareOp convertCompareOp(CompareOperation ak)
+{
+	VkCompareOp out = VK_COMPARE_OP_NEVER;
+	switch(ak)
+	{
+	case CompareOperation::ALWAYS:
+		out = VK_COMPARE_OP_ALWAYS;
+		break;
+	case CompareOperation::LESS:
+		out = VK_COMPARE_OP_LESS;
+		break;
+	case CompareOperation::EQUAL:
+		out = VK_COMPARE_OP_EQUAL;
+		break;
+	case CompareOperation::LESS_EQUAL:
+		out = VK_COMPARE_OP_LESS_OR_EQUAL;
+		break;
+	case CompareOperation::GREATER:
+		out = VK_COMPARE_OP_GREATER;
+		break;
+	case CompareOperation::GREATER_EQUAL:
+		out = VK_COMPARE_OP_GREATER_OR_EQUAL;
+		break;
+	case CompareOperation::NOT_EQUAL:
+		out = VK_COMPARE_OP_NOT_EQUAL;
+		break;
+	case CompareOperation::NEVER:
+		out = VK_COMPARE_OP_NEVER;
+		break;
+	default:
+		ANKI_ASSERT(0);
+	}
+
+	return out;
+}
+
+} // end namespace anki
+

+ 61 - 1
src/gr/vulkan/SamplerImpl.cpp

@@ -4,13 +4,73 @@
 // http://www.anki3d.org/LICENSE
 
 #include <anki/gr/vulkan/SamplerImpl.h>
+#include <anki/gr/Texture.h>
+#include <cstring>
 
 namespace anki
 {
 
 //==============================================================================
-void SamplerImpl::init(const SamplerInitInfo& init)
+void SamplerImpl::init(const SamplerInitInfo& ii)
 {
+	// Fill the create cio
+	VkSamplerCreateInfo ci;
+	memset(&ci, 0, sizeof(ci));
+
+	ci.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO;
+
+	if(ii.m_minMagFilter == SamplingFilter::NEAREST)
+	{
+		ci.magFilter = ci.minFilter = VK_FILTER_NEAREST;
+	}
+	else
+	{
+		ANKI_ASSERT(ii.m_minMagFilter == SamplingFilter::LINEAR);
+		ci.magFilter = ci.minFilter = VK_FILTER_LINEAR;
+	}
+
+	if(ii.m_mipmapFilter == SamplingFilter::BASE
+		|| ii.m_mipmapFilter == SamplingFilter::NEAREST)
+	{
+		ci.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST;
+	}
+	else
+	{
+		ci.mipmapMode = VK_SAMPLER_MIPMAP_MODE_LINEAR;
+	}
+
+	if(ii.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(ii.m_anisotropyLevel > 0)
+	{
+		ci.anisotropyEnable = VK_TRUE;
+		ci.maxAnisotropy = ii.m_anisotropyLevel;
+	}
+
+	ci.compareOp = convertCompareOp(ii.m_compareOperation);
+	if(ci.compareOp != VK_COMPARE_OP_ALWAYS)
+	{
+		ci.compareEnable = VK_TRUE;
+	}
+
+	ci.minLod = ii.m_minLod;
+	ci.maxLod = ii.m_maxLod;
+
+	ci.unnormalizedCoordinates = VK_FALSE;
+
+	// Create
+	ANKI_VK_CHECK(vkCreateSampler(getDevice(), &ci, nullptr, &m_sampler));
 }
 
 } // end namespace anki

+ 19 - 0
src/gr/vulkan/VulkanObject.cpp

@@ -0,0 +1,19 @@
+// Copyright (C) 2009-2016, Panagiotis Christopoulos Charitos.
+// All rights reserved.
+// Code licensed under the BSD License.
+// http://www.anki3d.org/LICENSE
+
+#include <anki/gr/vulkan/VulkanObject.h>
+#include <anki/gr/GrManager.h>
+#include <anki/gr/vulkan/GrManagerImpl.h>
+
+namespace anki
+{
+
+//==============================================================================
+VkDevice VulkanObject::getDevice() const
+{
+	return m_manager->getImplementation().m_device;
+}
+
+} // end namespace anki