filament
filament copied to clipboard
Problem showing clear color or triangle
Hi all. I would like to ask for a problem while I was implementing Filament in a simple C++ code.
I tried to implement GLFW, SDL2 or directly HWND but, just setting clear color, like in this guide, my window is always black. What am I missing? I'm using MSVC 14.32 (Visual Studio 2022). Thanks in advance
Code:
// Currently only for WIN32
#include <iostream>
#include <SDL.h>
#include <SDL_syswm.h>
#include <filament/Camera.h>
#include <filament/Engine.h>
#include <filament/View.h>
#include <filament/Viewport.h>
#include <filament/Scene.h>
#include <filament/RenderableManager.h>
#include <filament/Material.h>
#include <filament/VertexBuffer.h>
#include <filament/IndexBuffer.h>
#include <filament/Renderer.h>
#include <math/vec3.h>
#include <utils/EntityManager.h>
#include <utils/Entity.h>
static constexpr uint8_t BAKED_MATERIAL_PACKAGE[] {
#include "material_test/aiDefaultMat.inc"
};
static constexpr filament::math::float3 vertices[] {{-1, 0, -1}, {-1, 0, 1}, {1, 0, 1}, {1, 0, -1}};
static constexpr uint32_t indices[] {0, 1, 2, 2, 3, 0};
int wmain(int argc, wchar_t* argv[]) {
// TODO check if everything is necessary
if (SDL_Init(SDL_INIT_EVERYTHING) != 0) {
std::cout << "SDL_Init Error: " << SDL_GetError() << std::endl;
return 1;
}
uint32_t xRes{1000};
uint32_t yRes{1000};
SDL_Window *window(SDL_CreateWindow("Filament Test", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, static_cast<int>(xRes), static_cast<int>(yRes),
SDL_WINDOW_SHOWN));
if (!window) {
std::cout << "SDL_CreateWindow Error: " << SDL_GetError() << std::endl;
SDL_Quit();
return 1;
}
SDL_SysWMinfo wmInfo;
SDL_VERSION(&wmInfo.version);
SDL_GetWindowWMInfo(window, &wmInfo);
// https://github.com/google/filament/issues/473
// https://github.com/cgmb/hello-filament/blob/master/main.cxx
// https://google.github.io/filament/webgl/reference.html
// https://google.github.io/filament/posts/cocoapods/
std::cout << "Creating engine & scene...\n";
// TODO add all error handling phases
filament::Engine *engine(filament::Engine::create());
filament::SwapChain *swapChain(engine->createSwapChain(wmInfo.info.win.window));
filament::Renderer *renderer(engine->createRenderer());
filament::View *view(engine->createView());
filament::Scene *scene(engine->createScene());
filament::Camera *camera(engine->createCamera(utils::EntityManager::get().create()));
view->setCamera(camera);
view->setScene(scene);
view->setViewport({0, 0, xRes, yRes});
double aspect = static_cast<double>(xRes) / static_cast<double>(yRes);
camera->setProjection(filament::Camera::Projection::ORTHO, -2. * aspect, 2 * aspect, -2., 0., 0., 1.);
renderer->setClearOptions({.clearColor = {0.25f, 0.5f, 1.0f, 1.0f}, .clear = true, .discard = true});
std::cout << "Starting render loop...\n";
// https://www.willusher.io/sdl2%20tutorials/2013/08/20/lesson-4-handling-events
SDL_Event e;
bool quit = false;
while (!quit) {
while (SDL_PollEvent(&e)){
if (e.type == SDL_QUIT){
quit = true;
}
if (e.type == SDL_KEYDOWN){
quit = true;
}
if (e.type == SDL_MOUSEBUTTONDOWN){
quit = true;
}
}
//Render the scene
if (renderer->beginFrame(swapChain)) {
renderer->render(view);
renderer->endFrame();
}
}
engine->destroy(view);
engine->destroy(scene);
engine->destroyCameraComponent(camera->getEntity());
utils::EntityManager::get().destroy(camera->getEntity());
engine->destroy(renderer);
engine->destroy(swapChain);
filament::Engine::destroy(&engine);
SDL_DestroyWindow(window);
SDL_Quit();
return 0;
}
CMake:
cmake_minimum_required(VERSION 3.22)
project(FilamentTest)
set(CMAKE_CXX_STANDARD 23)
set(FILAMENT_DIR "C:/Program Files (x86)/TNT")
set(FILAMENT_INCLUDE "${FILAMENT_DIR}/include")
set(FILAMENT_LIB "${FILAMENT_DIR}/lib/x86_64")
set(SDL_DIR "${CMAKE_SOURCE_DIR}/SDL2-2.0.22")
set(SDL_INCLUDE "${CMAKE_SOURCE_DIR}/SDL2-2.0.22/include")
set(SDL_LIB "${CMAKE_SOURCE_DIR}/SDL2-2.0.22/lib/x64")
set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE}")
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG}")
include_directories(${FILAMENT_INCLUDE})
include_directories(${SDL_INCLUDE})
add_executable(FilamentTest main.cpp)
set_property(TARGET FilamentTest PROPERTY
MSVC_RUNTIME_LIBRARY "MultiThreaded")
target_link_libraries(FilamentTest
opengl32.lib
${SDL_LIB}/SDL2.lib
${FILAMENT_LIB}/backend.lib
${FILAMENT_LIB}/bluegl.lib
${FILAMENT_LIB}/filabridge.lib
${FILAMENT_LIB}/filaflat.lib
${FILAMENT_LIB}/filament.lib
${FILAMENT_LIB}/ibl.lib
${FILAMENT_LIB}/utils.lib
)
Update: I've discovered that being with NVIDIA Optimus (so automatically selecting Intel GPU), window is actually black. Selecting in NVIDIA Control Panel "High Performance" so that NVIDIA GPU is used, it actually shows something.
Is this issue still valid to investigate?
This might be the same as #5737.
I'm getting same result with Vulkan backend.
The Vulkan validation layer complaining about the barrier.
FEngine (64 bits) created at 00000197754B2930 (threading is enabled)
FEngine resolved backend: Vulkan
Vulkan device driver: NVIDIA 528.24
Selected physical device 'NVIDIA GeForce RTX 3060' from 1 physical devices. (vendor 0x10de, device 0x2504, driver 0x84060000, api 1.3)
FEngine feature level: 1
vkCreateSwapchain: 800x450, VK_FORMAT_B8G8R8A8_UNORM, VK_COLOR_SPACE_SRGB_NONLINEAR_KHR, 3, 1
VULKAN WARNING: (UNASSIGNED-BestPractices-ImageBarrierAccessLayout) Validation Warning: [ UNASSIGNED-BestPractices-ImageBarrierAccessLayout ] Object 0: handle = 0x17682f2c080, type = VK_OBJECT_TYPE_DEVICE; | MessageID = 0x849fcec7 | VK_ACCESS_2_COLOR_ATTACHMENT_WRITE_BIT: accessMask is vkCmdPipelineBarrier, but for layout VK_IMAGE_LAYOUT_PRESENT_SRC_KHR expected accessMask are VK_ACCESS_2_NONE.
(repeating the Barrier message when beginFrame())
Additionally, I'm in C# WinForms & C++/CLI instead of bare Win32 but it will be no matter because I had made some Vulkan apps with C# WinForms.
bool Initialize(void* nativeWindowHandle)
{
gEngine = Engine::create(Engine::Backend::DEFAULT);
if (gEngine == nullptr)
{
return false;
}
gSwapChain = gEngine->createSwapChain(nativeWindowHandle);
if (gSwapChain == nullptr)
{
return false;
}
gRenderer = gEngine->createRenderer();
if (gRenderer == nullptr)
{
return false;
}
gView = gEngine->createView();
if (gView == nullptr)
{
return false;
}
gScene = gEngine->createScene();
if (gScene == nullptr)
{
return false;
}
gView->setScene(gScene);
gApp.camera = utils::EntityManager::get().create();
gApp.cam = gEngine->createCamera(gApp.camera);
gView->setCamera(gApp.cam);
filament::Renderer::ClearOptions clearOptions{};
clearOptions.clear = true;
clearOptions.clearStencil = 0;
clearOptions.clearColor = filament::math::float4{ 1.0, 0.0, 0.0, 1.0 };
gRenderer->setClearOptions(clearOptions);
return true;
}
void Render()
{
if (gRenderer == nullptr)
{
return;
}
if (gRenderer->beginFrame(gSwapChain))
{
gRenderer->render(gView);
gRenderer->endFrame();
}
}
I also tried GL as backend, it was also black screen.
I'm using Filament 1.31.2.