3D editor stable with path tracer

This commit is contained in:
IlyaShurupov 2024-06-18 19:36:47 +03:00 committed by Ilya Shurupov
parent 8bec5d1ab7
commit 5ac4d56d32
11 changed files with 144 additions and 19 deletions

View file

@ -1,24 +1,97 @@
#include "Editor.hpp" #include "Editor.hpp"
#include "GraphicsApi.hpp"
using namespace tp; using namespace tp;
void Editor::loadDefaults() { Editor::Editor() {
mScene.load("rsc/scene/script.lua");
}
uint4 Editor::getViewportTexID() { { // create path tracer gpu texture
return mRasterRenderer.getRenderBufferID(); glGenTextures(1, &mPathRenderTexture);
glBindTexture(GL_TEXTURE_2D, mPathRenderTexture);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA32F, 100, 100, 0, GL_RGBA, GL_FLOAT, nullptr);
glBindTexture(GL_TEXTURE_2D, 0);
}
} }
void Editor::renderViewport() { void Editor::renderViewport() {
mRasterRenderer.render(mScene, mViewportSize); switch (mRenderType) {
case RenderType::RASTER:
mRasterRenderer.render(mScene, mScene.mRenderSettings.size);
break;
case RenderType::PATH_TRACER:
{
// TODO : include in render viewport method
// renderPathFrame();
break;
}
default:
break;
}
}
uint4 Editor::getViewportTexID() {
switch (mRenderType) {
case RenderType::PATH_TRACER:
return mPathRenderTexture;
case RenderType::RASTER:
return mRasterRenderer.getRenderBufferID();
default:
return 0;
}
}
void Editor::loadDefaults() {
mScene.load("rsc/scene/script.lua");
} }
void Editor::setViewportSize(const Vec2F& size) { void Editor::setViewportSize(const Vec2F& size) {
// TODO remove // TODO remove
mScene.mCamera.rotate(0.01f, 0.0); mScene.mCamera.rotate(0.01f, 0.0);
mScene.mRenderSettings.size = size;
mRasterRenderer.getRenderBuffer()->resize(size); mRasterRenderer.getRenderBuffer()->resize(size);
mScene.mCamera.setRatio(size.y / size.x); mScene.mCamera.setRatio(size.y / size.x);
} }
Editor::~Editor() {
glDeleteTextures(1, &mPathRenderTexture);
}
void Editor::renderPathFrame() {
mPathRenderer.render(mScene, mPathTracerBuffers, mScene.mRenderSettings);
{
glBindTexture(GL_TEXTURE_2D, mPathRenderTexture);
const auto size = mPathTracerBuffers.color.size();
glTexImage2D(
GL_TEXTURE_2D,
0,
GL_RGBA32F,
(GLsizei) size.x,
(GLsizei) size.y,
0,
GL_RGBA,
GL_FLOAT,
mPathTracerBuffers.color.getBuff()
);
glBindTexture(GL_TEXTURE_2D, 0);
}
}
void Editor::setRenderType(Editor::RenderType type) {
mRenderType = type;
}

View file

@ -6,21 +6,31 @@
namespace tp { namespace tp {
class Editor { class Editor {
public: public:
Editor() = default; enum class RenderType { RASTER, PATH_TRACER };
public:
Editor();
~Editor();
void loadDefaults(); void loadDefaults();
uint4 getViewportTexID(); uint4 getViewportTexID();
void setViewportSize(const Vec2F& size); void setViewportSize(const Vec2F& size);
void renderViewport(); void renderViewport();
void renderPathFrame();
void setRenderType(RenderType type);
private: private:
Scene mScene; Scene mScene;
RenderType mRenderType = RenderType::RASTER;
RasterRender mRasterRenderer; RasterRender mRasterRenderer;
RayTracer mPathRenderer; RayTracer mPathRenderer;
// TODO move inside the scene RayTracer::OutputBuffers mPathTracerBuffers;
Vec2F mViewportSize; uint4 mPathRenderTexture = 0;
}; };
} }

View file

@ -21,6 +21,8 @@ namespace tp {
void eventDraw(Canvas& canvas) override { void eventDraw(Canvas& canvas) override {
mEditor->renderViewport(); mEditor->renderViewport();
canvas.updateTextureID(mImage, mEditor->getViewportTexID());
canvas.drawImage(this->mArea, &mImage, PI); canvas.drawImage(this->mArea, &mImage, PI);
} }
@ -37,16 +39,38 @@ namespace tp {
EditorWidget(Canvas* canvas, Editor* editor) : EditorWidget(Canvas* canvas, Editor* editor) :
mViewport(canvas, editor) mViewport(canvas, editor)
{ {
mEditor = editor;
this->mChildWidgets.pushBack(&mViewport); this->mChildWidgets.pushBack(&mViewport);
this->mChildWidgets.pushBack(&mSplitView); this->mChildWidgets.pushBack(&mSplitView);
this->mChildWidgets.pushBack(&mSettingsWidget);
mRenderPathTracer.mLabel.mLabel = "Render with Path Tracer";
mRenderRaster.mLabel.mLabel = "Render with Raster";
mSettingsWidget.addWidget(&mRenderPathTracer);
mSettingsWidget.addWidget(&mRenderRaster);
} }
void eventProcess(const Events& events) override { void eventProcess(const Events& events) override {
mSplitView.setArea(this->mArea); mSplitView.setArea(this->mArea);
mViewport.setArea(mSplitView.getFirst()); mViewport.setArea(mSplitView.getFirst());
mSettingsWidget.setArea(mSplitView.getSecond());
if (mRenderPathTracer.isFired()) {
mEditor->renderPathFrame();
mEditor->setRenderType(Editor::RenderType::PATH_TRACER);
} }
void eventDraw(Canvas& canvas) override { canvas.rect(this->mArea, mBaseColor); } if (mRenderRaster.isFired()) {
mEditor->setRenderType(Editor::RenderType::RASTER);
}
}
void eventDraw(Canvas& canvas) override {
canvas.rect(this->mArea, mBaseColor);
}
void eventUpdateConfiguration(WidgetManager& wm) override { void eventUpdateConfiguration(WidgetManager& wm) override {
wm.setActiveId("3DEditor"); wm.setActiveId("3DEditor");
@ -54,9 +78,17 @@ namespace tp {
} }
public: public:
ViewportWidget<Events, Canvas> mViewport; Editor* mEditor = nullptr;
SplitView<Events, Canvas> mSplitView; SplitView<Events, Canvas> mSplitView;
ViewportWidget<Events, Canvas> mViewport;
// Controls
ScrollableWindow<Events, Canvas> mSettingsWidget;
ButtonWidget<Events, Canvas> mRenderPathTracer;
ButtonWidget<Events, Canvas> mRenderRaster;
RGBA mBaseColor; RGBA mBaseColor;
}; };
} }

View file

@ -20,6 +20,6 @@ Lights = {
RenderSettings = { RenderSettings = {
depth = 1, depth = 1,
spray = 3, spray = 1,
multisampling = 16, multisampling = 1,
} }

View file

@ -40,7 +40,7 @@ namespace tp {
void allocateBuffer(Index2D size) { void allocateBuffer(Index2D size) {
deleteBuffer(); deleteBuffer();
mBuff = (tType*) mAlloc.allocate(sizeof(tType) * size.x * size.y); mBuff = (tType*) mAlloc.allocate(sizeof(tType) * size.x * size.y);
for (ualni i = 0; i < mSize.x * mSize.y; i++) { for (ualni i = 0; i < size.x * size.y; i++) {
new (mBuff + i) tType(); new (mBuff + i) tType();
} }
} }

View file

@ -130,6 +130,14 @@ void Canvas::drawImage(const RectF& rec, ImageHandle* image, halnf angle, halnf
#endif #endif
} }
void Canvas::updateTextureID(ImageHandle handle, ualni id) {
auto nvgl = (GLNVGcontext*) nvgInternalParams(mContext->vg)->userPtr;
auto glhandle = nvglImageHandleGL3(mContext->vg, handle.id);
auto tex = glnvg__findTexture(nvgl, handle.id);
tex->tex = id;
}
void Canvas::deleteImageHandle(ImageHandle image) { void Canvas::deleteImageHandle(ImageHandle image) {
if (image.id) { if (image.id) {
nvgDeleteImage(mContext->vg, image.id); nvgDeleteImage(mContext->vg, image.id);

View file

@ -61,6 +61,8 @@ namespace tp {
void text(const char*, const RectF&, halnf size, Align, halnf padding, const RGBA&); void text(const char*, const RectF&, halnf size, Align, halnf padding, const RGBA&);
ImageHandle createImageFromTextId(ualni id, Vec2F size); ImageHandle createImageFromTextId(ualni id, Vec2F size);
void updateTextureID(ImageHandle handle, ualni id);
void deleteImageHandle(ImageHandle image); void deleteImageHandle(ImageHandle image);
void drawImage(const RectF& rec, ImageHandle* image, halnf angle = 0, halnf alpha = 1.f, halnf rounding = 0.f); void drawImage(const RectF& rec, ImageHandle* image, halnf angle = 0, halnf alpha = 1.f, halnf rounding = 0.f);

View file

@ -80,8 +80,6 @@ namespace tp {
bool operator==(const RGBA& in) const { return r == in.r && g == in.g && b == in.b && a == in.a; } bool operator==(const RGBA& in) const { return r == in.r && g == in.g && b == in.b && a == in.a; }
public: public:
flt4 a;
union { union {
RGB rgbs; RGB rgbs;
@ -91,6 +89,8 @@ namespace tp {
flt4 b; flt4 b;
}; };
}; };
flt4 a;
}; };
class HSVA { class HSVA {

View file

@ -15,7 +15,7 @@ uint4 RasterRender::getRenderBufferID() { return mRenderBuffer.texId(); }
Vec2F RasterRender::getBufferSize() { return mRenderBuffer.getSize(); } Vec2F RasterRender::getBufferSize() { return mRenderBuffer.getSize(); }
void RasterRender::render(const Scene& geometry, Vec2F size) { void RasterRender::render(const Scene& geometry, const Vec2<ualni>& size) {
for (auto object : geometry.mObjects) { for (auto object : geometry.mObjects) {
if (!object->mGUPBuffers) { if (!object->mGUPBuffers) {

View file

@ -12,7 +12,7 @@ namespace tp {
RasterRender(); RasterRender();
~RasterRender(); ~RasterRender();
void render(const Scene& geometry, Vec2F size); void render(const Scene& geometry, const Vec2<ualni>& size);
uint4 getRenderBufferID(); uint4 getRenderBufferID();
RenderBuffer* getRenderBuffer(); RenderBuffer* getRenderBuffer();
Vec2F getBufferSize(); Vec2F getBufferSize();

View file

@ -8,7 +8,7 @@ namespace tp {
class ButtonWidget : public Widget<Events, Canvas> { class ButtonWidget : public Widget<Events, Canvas> {
public: public:
ButtonWidget() { ButtonWidget() {
this->setArea({ 0, 0, 100, 100 }); this->setArea({ 0, 0, 100, 30 });
this->mChildWidgets.pushBack(&mLabel); this->mChildWidgets.pushBack(&mLabel);
} }