This commit is contained in:
Nanako 2024-10-15 10:11:53 +08:00
commit 3a0593c3ff
14 changed files with 327 additions and 0 deletions

15
CMakeLists.txt Normal file
View File

@ -0,0 +1,15 @@
cmake_minimum_required(VERSION 3.10)
project(aorii)
include(cmake/retrieve_files.cmake)
find_package(Eigen3 REQUIRED)
find_package(spdlog REQUIRED)
# Debug,
if (CMAKE_BUILD_TYPE STREQUAL "Debug")
add_definitions(-DDEBUG=1)
endif()
add_subdirectory(src/renderer)
add_subdirectory(src/widget)

View File

@ -0,0 +1,61 @@
function(retrieve_files_custom path extension out_files)
message(STATUS "Retrieving files in ${path}")
set(EXTENSIONS "")
foreach(ext ${extension})
list(APPEND EXTENSIONS "${path}/*.${ext}")
endforeach ()
# .h .hpp. ini HEAD_FILES
file(GLOB_RECURSE FIND_FILES RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} CONFIGURE_DEPENDS ${EXTENSIONS})
# HEDADER_FILES SRC_FILES ALL_FILES
set(ALL_FILES ${FIND_FILES})
set(RESULT "")
# ALL_FILES 变量里面的所有文件分类(保留资源管理器的目录结构)
foreach(fileItem ${ALL_FILES})
# Get the directory of the source file
get_filename_component(PARENT_DIR "${fileItem}" DIRECTORY)
#
if(PARENT_DIR STREQUAL "windows")
if(WIN32)
set(RESULT "${RESULT};${fileItem}")
else()
continue()
endif()
elseif(PARENT_DIR STREQUAL "linux")
if(UNIX AND NOT APPLE)
set(RESULT "${RESULT};${fileItem}")
else()
continue()
endif()
elseif(PARENT_DIR STREQUAL "mac")
if(APPLE)
set(RESULT "${RESULT};${fileItem}")
else()
continue()
endif()
else()
#
set(RESULT "${RESULT};${fileItem}")
endif()
# Remove common directory prefix to make the group
string(REPLACE "${path}" "" GROUP "${PARENT_DIR}")
# Make sure we are using windows slashes
string(REPLACE "/" "\\" GROUP "${GROUP}")
# Group into "Source Files" and "Header Files"
set(GROUP "${GROUP}")
source_group("${GROUP}" FILES "${fileItem}")
endforeach()
set(${out_files} ${RESULT} PARENT_SCOPE)
endfunction()
function(retrieve_files path out_files)
set(temp_files "")
retrieve_files_custom(${path} "h;hpp;ini;cpp;c;ixx" temp_files)
set(${out_files} ${${out_files}} ${temp_files} PARENT_SCOPE)
endfunction()

View File

@ -0,0 +1,39 @@
project(renderer)
set(GL_BACKEND FALSE CACHE BOOL "OpenGL backend to use")
set(DX_BACKEND FALSE CACHE BOOL "DirectX backend to use")
set(VK_BACKEND FALSE CACHE BOOL "Vulkan backend to use")
if (NOT GL_BACKEND AND NOT DX_BACKEND AND NOT VK_BACKEND)
message(FATAL_ERROR "No backend selected")
endif()
set(RENDERER_SOURCES
renderer.cpp
renderer.h
renderer_buffer.cpp
renderer_buffer.h
renderer_texture.cpp
renderer_texture.h
)
if (GL_BACKEND)
retrieve_files(backend/gl RENDERER_SOURCES)
add_definitions(-DGL_BACKEND=1)
endif()
if (DX_BACKEND)
retrieve_files(backend/dx RENDERER_SOURCES)
add_definitions(-DDX_BACKEND=1)
endif ()
if (VK_BACKEND)
retrieve_files(backend/vk RENDERER_SOURCES)
add_definitions(-DVK_BACKEND=1)
endif ()
add_library(${PROJECT_NAME} STATIC ${RENDERER_SOURCES})
target_link_libraries(${PROJECT_NAME} Eigen3::Eigen spdlog::spdlog)
target_include_directories(${PROJECT_NAME} PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
if (DX_BACKEND)
target_link_libraries(${PROJECT_NAME} d3d11 d3dcompiler dxgi)
endif ()

View File

@ -0,0 +1,51 @@
#include "dx_backend.h"
#include "dx_texture.h"
#include "spdlog/spdlog.h"
std::shared_ptr<renderer_texture> dx_backend::create_texture(const Eigen::Vector2i& size) {
D3D11_TEXTURE2D_DESC desc = {};
desc.Width = size.x();
desc.Height = size.y();
desc.MipLevels = 1;
desc.ArraySize = 1;
desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
desc.Usage = D3D11_USAGE_DYNAMIC;
desc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
desc.MiscFlags = 0;
ID3D11Texture2D* texture = nullptr;
if (FAILED(device->CreateTexture2D(&desc, nullptr, &texture))) {
return nullptr;
}
return std::make_shared<dx_texture>(texture);
}
void dx_backend::destroy_texture(renderer_texture* texture) {
#ifdef DEBUG
spdlog::info("Destroying texture");
#endif
}
bool dx_backend::init() {
if (!create_device())
return false;
if (!create_context())
return false;
return true;
}
bool dx_backend::create_device() {
D3D_FEATURE_LEVEL featureLevels[] = { D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_11_1 };
const auto result = D3D11CreateDevice(nullptr, D3D_DRIVER_TYPE_HARDWARE, nullptr, 0, featureLevels, 2, D3D11_SDK_VERSION, &device, nullptr, nullptr);
return SUCCEEDED(result);
}
bool dx_backend::create_context() {
device->GetImmediateContext(&context);
return true;
}

View File

@ -0,0 +1,22 @@
#pragma once
#include "renderer.h"
#include <d3d11.h>
class dx_backend : public renderer {
inline static dx_backend* instance = nullptr;
public:
static dx_backend* get_instance() {
return static_cast<dx_backend*>(aorii::s_renderer);
}
bool init() override;
std::shared_ptr<renderer_texture> create_texture(const Eigen::Vector2i& size) override;
void destroy_texture(renderer_texture* texture) override;
private:
bool create_device();
bool create_context();
ID3D11Device* device = nullptr;
ID3D11DeviceContext* context = nullptr;
};

View File

@ -0,0 +1,44 @@
#include "dx_texture.h"
#include "dx_backend.h"
dx_texture::dx_texture(ID3D11Texture2D* texture) {
m_texture = texture;
}
dx_texture::~dx_texture() {
// 如果是Debug模式, 检查m_data是否被释放
#if defined(DEBUG)
assert(!m_data);
#endif
free(m_data);
}
void* dx_texture::lock() {
D3D11_TEXTURE2D_DESC desc;
m_texture->GetDesc(&desc);
m_data = new char[desc.Width * desc.Height * 4];
return m_data;
}
void dx_texture::unlock() {
D3D11_TEXTURE2D_DESC desc;
m_texture->GetDesc(&desc);
D3D11_MAPPED_SUBRESOURCE mappedResource;
auto context = dx_backend::get_instance();
context->Map(m_texture.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
memcpy(mappedResource.pData, m_data, desc.Width * desc.Height * 4);
context->Unmap(m_texture.get(), 0);
delete[] m_data;
m_data = nullptr;
}
bool dx_texture::resize(const Eigen::Vector2i& size) {
return true;
}
Eigen::Vector2i dx_texture::size() {
D3D11_TEXTURE2D_DESC desc;
m_texture->GetDesc(&desc);
return { desc.Width, desc.Height };
}

View File

@ -0,0 +1,19 @@
#pragma once
#include "renderer_texture.h"
#include <d3d11.h>
#include <memory>
// DX11纹理
class dx_texture : public renderer_texture {
public:
explicit dx_texture(ID3D11Texture2D* texture);
~dx_texture() override;
void* lock() override;
void unlock() override;
bool resize(const Eigen::Vector2i& size) override;
Eigen::Vector2i size() override;
private:
void* m_data = nullptr;
ID3D11Texture2D* m_texture;
};

29
src/renderer/renderer.cpp Normal file
View File

@ -0,0 +1,29 @@
#include "renderer.h"
#ifdef DX_BACKEND
#include "backend/dx/dx_backend.h"
#endif
bool aorii::create_renderer(renderer_api api) {
if (s_renderer)
return true;
switch (api) {
#ifdef DX_BACKEND
case renderer_api::dx11:
s_renderer = new dx_backend();
break;
#endif
#ifdef GL_BACKEND
case renderer_api::opengl:
break;
#endif
#ifdef VK_BACKEND
case renderer_api::vulkan:
break;
#endif
default:
assert(false);
break;
}
return s_renderer->init();
}

26
src/renderer/renderer.h Normal file
View File

@ -0,0 +1,26 @@
#pragma once
#include <memory>
#include <Eigen/Eigen>
class renderer_texture;
enum class renderer_api {
dx11,
opengl,
vulkan,
};
class renderer {
public:
virtual ~renderer() = default;
virtual std::shared_ptr<renderer_texture> create_texture(const Eigen::Vector2i& size) = 0;
virtual void destroy_texture(renderer_texture* texture) = 0;
virtual bool init() = 0;
};
namespace aorii {
inline static renderer* s_renderer = nullptr;
bool create_renderer(renderer_api api);
}

View File

@ -0,0 +1 @@
#include "renderer_buffer.h"

View File

@ -0,0 +1,5 @@
#pragma once
class renderer_buffer {
};

View File

@ -0,0 +1 @@
#include "renderer_texture.h"

View File

@ -0,0 +1,14 @@
#pragma once
#include <Eigen/Eigen>
class renderer_texture {
public:
virtual ~renderer_texture() = default;
virtual void* lock() = 0;
virtual void unlock() = 0;
virtual bool resize(const Eigen::Vector2i& size) = 0;
virtual Eigen::Vector2i size() = 0;
};

View File