# Building a Custom Game Engine from Scratch (C++ & DX12) - Day 4: First Frame Render, Command Lists & Synchronization

**URL:** <https://forums.unrealengine.com/t/building-a-custom-game-engine-from-scratch-c-dx12-day-4-first-frame-render-command-lists-synchronization/2855018>\
**Category:** C++\
**Tags:** unreal-engine, CPP\
**Created:** [November 13, 2026, 11:21am UTC](https://forums.unrealengine.com/t/building-a-custom-game-engine-from-scratch-c-dx12-day-4-first-frame-render-command-lists-synchronization/2855018 "2026-11-13T11:21:39Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![kevinpc\_1](https://d1ap1mz92jnks1.cloudfront.net/user_avatar/forums.unrealengine.com/kevinpc_1/32/1215238_2.png) [@kevinpc\_1](https://forums.unrealengine.com/u/kevinpc_1)\
**Post date:** [November 13, 2026, 11:21am UTC](https://forums.unrealengine.com/t/building-a-custom-game-engine-from-scratch-c-dx12-day-4-first-frame-render-command-lists-synchronization/2855018/1 "2026-11-13T11:21:39Z")

</div>

Hey everyone! 👋

Today marks **Day 4** of my journey building **TitanEngine** completely from scratch using **C++20 and native DirectX 12** , with zero bloated third-party templates or high-level helper wrappers.

After setting up our device, command queue, and swap chain in the previous sessions, today we achieved a major milestone: **rendering our very first frame and clearing the screen with pure hardware control!**

Here is what was implemented today:

- **Command Allocator & List:** Initialized and managed `ID3D12CommandAllocator` and `ID3D12GraphicsCommandList` to record and reset rendering commands frame by frame.

- **Manual Resource Barriers:** Handled `D3D12_RESOURCE_BARRIER` states to transition our back buffers manually between `PRESENT` and `RENDER_TARGET`.

- **First Frame Clear:** Bound our Render Target View using raw descriptor handle pointer arithmetic and cleared the screen with a custom engine background color.

- **Deterministic Synchronization:** Implemented an `ID3D12Fence` alongside native Win32 Event handles (`WaitForSingleObject`) to completely prevent CPU-GPU race conditions.

You can check out the full step-by-step breakdown and code walkthrough in the latest video update here: 📺 **Watch Day 4 on YouTube:** [https://youtu.be/QbUPJpvIqFU](https://youtu.be/QbUPJpvIqFU)

Feedback, architectural thoughts, or questions from fellow engine programmers are always welcome. Let’s keep building low-level! 🚀
