filament <2> Draw a Quad


#include <SDL.h>
#include <filament/Engine.h>
#include <filament/FilamentAPI.h>
#include <filament/LightManager.h>
#include <filament/RenderableManager.h>
#include <filament/Scene.h>
#include <filament/View.h>
#include <thread>
#include <utils/EntityManager.h>
#include <filament/TransformManager.h>
#include <math/norm.h>

#include <vector>
#include <fstream>
#include "generated/resources/resources.h"

using namespace filament;
using namespace utils;
using namespace math;
using namespace std;



SDL_Window* createSDLwindow() {

	const uint32_t windowFlags =
		SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI;
	SDL_Window* win =
		SDL_CreateWindow("Hello World!", 100, 100, 1920, 1080, windowFlags);
	if (win == nullptr) {
		std::cout << "SDL_CreateWindow Error: " << SDL_GetError() << std::endl;
		SDL_Quit();
		return NULL;
	}

	return win;
}



#include <utils/Panic.h>
#include <SDL_syswm.h>
void* getNativeWindow(SDL_Window* sdlWindow) {
	SDL_SysWMinfo wmi;
	SDL_VERSION(&wmi.version);
	ASSERT_POSTCONDITION(SDL_GetWindowWMInfo(sdlWindow, &wmi), "SDL version unsupported!");
	HWND win = (HWND)wmi.info.win.window;
	return (void*)win;
}


std::ifstream::pos_type getFileSize(const char* filename) {
	std::ifstream in(filename, std::ifstream::ate | std::ifstream::binary);
	return in.tellg();
}

int main(int argc, char** argv) {
	printf("hello world");

	

	const static uint32_t indices[] = { 0, 1, 2, 2, 3, 0 };

	float3 vertices[] = {
		{ -10, 0, -10 },
		{ -10, 0, 10 },
		{ 10, 0, 10 },
		{ 10, 0, -10 },
	};

	short4 tbn = math::packSnorm16(
		mat3f::packTangentFrame(math::mat3f{ float3{ 1.0f, 0.0f, 0.0f },
										float3{ 0.0f, 0.0f, 1.0f },
										float3{ 0.0f, 1.0f, 0.0f } })
		.xyzw);

	const static math::short4 normals[]{ tbn, tbn, tbn, tbn };
	SDL_Window* window = createSDLwindow();
	Engine* engine = Engine::create();
	SwapChain* swapChain = engine->createSwapChain(getNativeWindow(window));
	Renderer* renderer = engine->createRenderer();

	TransformManager& tcm = engine->getTransformManager();

	Camera* camera = engine->createCamera();
	View* view = engine->createView();
	Scene* scene = engine->createScene();

	view->setCamera(camera);
	// Determine the current size of the window in physical pixels.
	uint32_t w, h;
	SDL_GL_GetDrawableSize(window, (int*)&w, (int*)&h);


	camera->setProjection(45.0, double(w) / h, 0.1, 50, Camera::Fov::VERTICAL);
	view->setViewport({ 0, 0, w, h });

	view->setScene(scene);

	VertexBuffer* vertexBuffer =
		VertexBuffer::Builder()
		.vertexCount(4)
		.bufferCount(2)
		.attribute(VertexAttribute::POSITION, 0,
			VertexBuffer::AttributeType::FLOAT3)
		.attribute(VertexAttribute::TANGENTS, 1,
			VertexBuffer::AttributeType::SHORT4)
		.normalized(VertexAttribute::TANGENTS)
		.build(*engine);

	vertexBuffer->setBufferAt(
		*engine, 0,
		VertexBuffer::BufferDescriptor(vertices, vertexBuffer->getVertexCount() * sizeof(vertices[0])));
	vertexBuffer->setBufferAt(
		*engine, 1,
		VertexBuffer::BufferDescriptor(normals, vertexBuffer->getVertexCount() * sizeof(normals[0])));

	IndexBuffer* indexBuffer =
		IndexBuffer::Builder().indexCount(6).build(*engine);

	indexBuffer->setBuffer(
		*engine, IndexBuffer::BufferDescriptor(indices, indexBuffer->getIndexCount() * sizeof(uint32_t)));

	
	std::string filename = "generated/material/aiDefaultMat.filamat";
	long fileSize = static_cast<long>(getFileSize(filename.c_str()));
	if (fileSize <= 0) {
		return 1;
	}

	Material* material = nullptr;
	MaterialInstance* materialInstance = nullptr;
	std::ifstream in(filename.c_str(), std::ifstream::in);
	if (in.is_open()) {

		std::vector<char> materialBuffer;
		materialBuffer.reserve(static_cast<unsigned long>(fileSize));
		
		in.read(materialBuffer.data(), fileSize);
		material = Material::Builder()
			.package((void*)materialBuffer.data(), (size_t)fileSize)
			.build(*engine);
		materialInstance = material->createInstance();
		
	}
	

	materialInstance->setParameter("baseColor", float3{ 0, 0.8, 0 });
	materialInstance->setParameter("metallic", 0.0f);
	materialInstance->setParameter("roughness", 0.4f);
	materialInstance->setParameter("reflectance", 0.5f);

	Entity renderable = EntityManager::get().create();

	Entity light = EntityManager::get().create();

	LightManager::Builder(LightManager::Type::SUN)
		.color(Color::toLinear<ACCURATE>(sRGBColor(0.98f, 0.92f, 0.89f)))
		.intensity(110000)
		.direction({ 0.7, -1, -0.8 })
		.sunAngularRadius(1.9f)
		.castShadows(true)
		.build(*engine, light);

	scene->addEntity(light);

	// build a quad
	RenderableManager::Builder(1)
		.boundingBox({ { -1, -1, -1 }, { 1, 1, 1 } })
		.material(0, materialInstance)
		.geometry(0, RenderableManager::PrimitiveType::TRIANGLES, vertexBuffer,
			indexBuffer, 0, 6)
		.culling(false)
		.build(*engine, renderable);

	scene->addEntity(renderable);
	mat4f origTransform = math::mat4f::translation(float3{ 0, -1, -100 }) * mat4f::rotation(0.5 * M_PI, float3{ 1, 0, 0 });
	mat4f camTrans = camera->getModelMatrix();
	tcm.setTransform(tcm.getInstance(renderable), origTransform);

	constexpr double speed = 100.0;
	bool run = true;
	double g_discoAngle = 0;
	double g_discoAngularSpeed = 1;
	double lastTime = 0;

	float3 pos = 0;
	while (run) {
		// beginFrame() returns false if we need to skip a frame
		if (renderer->beginFrame(swapChain)) {
			// for each View
			renderer->render(view);
			renderer->endFrame();
		}
		double now = (double)SDL_GetPerformanceCounter() / SDL_GetPerformanceFrequency();
		double dT = now - lastTime;
		SDL_Event event;
		int numEvents = 0;
		while (SDL_PollEvent(&event) && numEvents < 16) {

			switch (event.type) {
			case SDL_QUIT:
				run = false;
				break;
			}
			numEvents++;
		}

		SDL_Delay(16);
		mat4f transform = mat4f::translation(float3{ 0, -1, -50 }) * mat4f::rotation(g_discoAngle, float3{ 0, 0, 1 });
		transform *= origTransform;
		tcm.setTransform(tcm.getInstance(renderable), transform);
		g_discoAngle += g_discoAngularSpeed * dT;

		lastTime = now;
	}

	Engine::destroy(&engine);

	return 0;
}

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Filament引擎是一种现代化的渲染引擎,用于实时渲染图形,特别是用于移动设备和虚拟现实平台。它是由Google公司开发的,旨在为开发者提供高质量、高性能的渲染功能。 Filament引擎的一个重要特点是其卓越的可视效果。它使用基于物理的材质系统,能够模拟光照、阴影、反射等视觉效果,使得渲染出来的图像更加逼真和细腻。同时,Filament引擎还支持更高级的图形功能,如屏幕空间反射、全局光照和泛光效果等,以提供更出色的视觉体验。 除了可视效果外,Filament引擎还注重性能。它采用了先进的渲染技术和算法,以提高渲染速度和效率。该引擎能够在移动设备和虚拟现实平台上运行,而不影响用户体验,并且可以自动适应不同硬件设备的性能和功能。 另外,Filament引擎还提供了灵活的工具和API,使开发者能够更轻松地创建和定制渲染效果。开发者可以使用Filament的材质编辑器和场景编辑器来调整和优化图形效果,也可以通过使用Filament的C++ API来实现更高级的自定义需求。 总之,Filament引擎是一款功能强大、易于使用且性能优越的渲染引擎。它将高质量的视觉效果和高性能相结合,为开发者提供了创建令人惊叹的实时渲染图形的能力。无论是用于移动游戏、虚拟现实应用还是其他图形渲染需求,Filament引擎都能够发挥重要作用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值