save state

This commit is contained in:
2026-01-15 17:57:24 +01:00
parent 1f8f06de2a
commit 6ad11773dd
8 changed files with 320 additions and 58 deletions

6
.gitignore vendored
View File

@@ -1 +1,7 @@
/build
/.idea
/.vs
/build
/build_test
/cmake-build*
/out

73
AGENTS.md Normal file
View File

@@ -0,0 +1,73 @@
# Mosis Designer Agent Guidelines
## Build, Lint, and Test Commands
### Build Commands
- `cmake --build build --config Debug` - Build the project in debug mode
- `cmake --build build --config Release` - Build the project in release mode
- `cmake -B build` - Configure the build system
- `cmake --build build --parallel 4` - Build with 4 parallel jobs
### Lint Commands
- No specific linting tools configured
- Uses C++23 standard with clang-tidy if available
### Test Commands
- No unit tests configured
- Manual testing required for functionality verification
## Code Style Guidelines
### General
- Follow C++23 standard with modern C++ features
- Use snake_case for variable and function names
- Use camelCase for class and struct names
- Use uppercase for constants and enum values
### Naming Conventions
- Functions: camelCase
- Variables: snake_case
- Classes/Structs: camelCase
- Constants: UPPER_CASE
- Enums: UPPER_CASE with prefix (e.g., `enum class FileType { XML, RML };`)
### Includes and Imports
- Use angle brackets for system headers: `#include <iostream>`
- Use quotes for local headers: `#include "header.h"`
- Group includes: system headers, then local headers
- Sort includes alphabetically within groups
### Formatting
- 4 spaces for indentation (no tabs)
- No trailing whitespace
- Unix line endings (\n)
- One statement per line
- Function definitions: space after function name, no space before opening parenthesis
- If statements: space after keyword, no space before opening parenthesis
### Error Handling
- Use exceptions for error conditions
- Check return values of system calls
- Prefer early returns over nested conditionals
- Use constexpr for compile-time constants
### Memory Management
- Prefer stack allocation over heap
- Use smart pointers (std::unique_ptr, std::shared_ptr)
- Avoid raw pointers when possible
- Use RAII principles
### Documentation
- Document public APIs with comments
- Use Doxygen-style comments for functions and classes
- Keep comments concise and clear
## Special Rules
### Cursor Rules
- No cursor rules configured
- No .cursorrules file found
### Copilot Rules
- No copilot instructions configured
- No .github/copilot-instructions.md file found

55
CLAUDE.md Normal file
View File

@@ -0,0 +1,55 @@
# CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
## Project Overview
Mosis Designer is a Windows desktop application for previewing RML/RCSS files using the RmlUi library. It provides live reloading when files change in the assets directory.
## Build Commands
```bash
# Configure the build (requires vcpkg for glfw3 and freetype)
cmake -B build
# Build debug
cmake --build build --config Debug
# Build release
cmake --build build --config Release
# Build with parallel jobs
cmake --build build --parallel 4
```
## Running the Application
```bash
# Run with an RML file
./build/Debug/mosis-designer.exe assets/demo.rml
```
The application watches the parent directory of the loaded file for changes and automatically reloads.
## Architecture
Single-file C++23 application (`main.cpp`) that:
- Uses RmlUi for rendering HTML/CSS-like markup (RML/RCSS)
- Uses GLFW + OpenGL 3 backend from RmlUi
- Windows-specific file watching via `FindFirstChangeNotification`
- Automatically loads all `.ttf` fonts from the RML file's directory
## Dependencies
- **RmlUi**: Fetched via CMake FetchContent from GitHub
- **GLFW3**: Via vcpkg
- **FreeType**: Via vcpkg
## Code Style
- C++23 standard
- 4 spaces indentation
- snake_case for variables, camelCase for functions/classes
- UPPER_CASE for constants and enums
- Early returns preferred over nested conditionals
- Smart pointers over raw pointers

View File

@@ -4,20 +4,36 @@ project("mosis-designer")
set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(RmlUi CONFIG REQUIRED)
find_package(glfw3 CONFIG REQUIRED)
# Use FetchContent for RmlUi
include(FetchContent)
set(RMLUI_BACKEND "D:/vcpkg/buildtrees/rmlui/src/6.1-fbf6dfc3b5.clean/Backends")
# Fetch RmlUi from GitHub
FetchContent_Declare(
rmlui
GIT_REPOSITORY https://github.com/mikke89/RmlUi.git
GIT_TAG master
)
FetchContent_MakeAvailable(rmlui)
# Find other dependencies via vcpkg
find_package(glfw3 CONFIG REQUIRED)
find_package(freetype CONFIG REQUIRED)
# Get the RmlUi source directory for include paths
FetchContent_GetProperties(rmlui)
set(RMLUI_SOURCE_DIR ${rmlui_SOURCE_DIR})
add_executable(mosis-designer
main.cpp
${RMLUI_BACKEND}/RmlUi_Backend_GLFW_GL3.cpp
${RMLUI_BACKEND}/RmlUi_Platform_GLFW.cpp
${RMLUI_BACKEND}/RmlUi_Renderer_GL3.cpp
${rmlui_SOURCE_DIR}/Backends/RmlUi_Backend_GLFW_GL3.cpp
${rmlui_SOURCE_DIR}/Backends/RmlUi_Platform_GLFW.cpp
${rmlui_SOURCE_DIR}/Backends/RmlUi_Renderer_GL3.cpp
)
target_link_libraries(mosis-designer PUBLIC
RmlUi::RmlUi glfw
RmlUi::RmlUi glfw freetype
)
target_include_directories(mosis-designer PUBLIC
${RMLUI_BACKEND}
)
${RMLUI_SOURCE_DIR}
${RMLUI_SOURCE_DIR}/Backends
)

View File

@@ -1,28 +1,35 @@
<rml>
<head>
<head>
<link type="text/rcss" href="html.rcss"/>
<link type="text/rcss" href="phone.rcss"/>
<title>Fullscreen Mobile UI</title>
</head>
<body>
</head>
<body>
<div id="status-bar">
<span class="time">22:47</span>
<div class="status-icons">
<span class="icon">📶</span>
<span class="icon">🔋</span>
</div>
<span class="time">22:47</span>
<div class="status-icons">
<span class="icon">📶</span>
<span class="icon">🔋</span>
<span class="icon">📶</span>
<span class="icon">🔋</span>
<span class="icon">📶</span>
<span class="icon">🔋</span>
</div>
</div>
<div id="content">
<div class="header-section">
<h1>Activity</h1>
<p>Monday, January 5</p>
</div>
<div class="header-section">
<h1>Hello omar 3 hello! and hello LEO 2 Hello!</h1>
</div>
</div>
<div id="nav-bar">
<div class="nav-item">Home</div>
<div class="nav-item">Apps</div>
<div class="nav-item">Settings</div>
<div class="nav-item">Home</div>
<div class="nav-item">Apps</div>
<div class="nav-item">Settings</div>
<div class="nav-item">Home</div>
<div class="nav-item">Apps</div>
<div class="nav-item">Settings</div>
</div>
</body>
</rml>
</body>
</rml>

93
assets/html.rcss Normal file
View File

@@ -0,0 +1,93 @@
body, div,
h1, h2, h3, h4,
h5, h6, p,
hr, pre,
tabset tabs
{
display: block;
}
h1
{
font-size: 2em;
margin: .67em 0;
}
h2
{
font-size: 1.5em;
margin: .75em 0;
}
h3
{
font-size: 1.17em;
margin: .83em 0;
}
h4, p
{
margin: 1.12em 0;
}
h5
{
font-size: .83em;
margin: 1.5em 0;
}
h6
{
font-size: .75em;
margin: 1.67em 0;
}
h1, h2, h3, h4,
h5, h6, strong
{
font-weight: bold;
}
em
{
font-style: italic;
}
pre
{
white-space: pre;
}
hr
{
border-width: 1px;
}
table
{
box-sizing: border-box;
display: table;
}
tr
{
box-sizing: border-box;
display: table-row;
}
td
{
box-sizing: border-box;
display: table-cell;
}
col
{
box-sizing: border-box;
display: table-column;
}
colgroup
{
display: table-column-group;
}
thead, tbody, tfoot
{
display: table-row-group;
}

View File

@@ -12,19 +12,20 @@ body {
/* Status Bar pinned to top */
#status-bar {
display: block;
height: 40px;
height: 140px;
padding: 10px 20px 0;
background-color: rgba(0, 0, 0, 0.2);
background-color: rgba(255, 0, 0, 0.2);
}
.time {
float: left;
font-weight: bold;
font-size: 1.1em;
font-size: 2em;
}
.status-icons {
float: right;
font-size: 2em;
}
.icon {
@@ -94,8 +95,16 @@ h1 {
.nav-item {
font-size: 1.9em;
color: #888;
background-color: red;
width: 100px;
height: 100px;
text-align: center;
vertical-align: middle;
line-height: 90px;
border-radius: 10px;
}
.nav-item:hover {
color: #3498db;
background-color: blue;
}

View File

@@ -2,39 +2,44 @@
#include <thread>
#include <chrono>
#include <filesystem>
#include <iostream>
#include <RmlUi/Core.h>
#include <RmlUi/Debugger.h>
#include <RmlUi_Backend.h>
#include <RmlUi_Include_Windows.h>
void load_fonts()
void load_fonts(const std::filesystem::path& dir)
{
const Rml::String directory = "assets/";
struct FontFace {
const char* filename;
bool fallback_face;
};
FontFace font_faces[] = {
{"LatoLatin-Regular.ttf", false},
{"LatoLatin-Italic.ttf", false},
{"LatoLatin-Bold.ttf", false},
{"LatoLatin-BoldItalic.ttf", false},
{"NotoEmoji-Regular.ttf", true},
};
for (const FontFace& face : font_faces)
Rml::LoadFontFace(directory + face.filename, face.fallback_face);
for (const auto& file : std::filesystem::directory_iterator(dir))
{
if (file.path().extension() == ".ttf")
{
Rml::LoadFontFace(file.path().string());
}
}
}
int main()
int main(const int argc, const char* argv[])
{
const int window_width = 1024;
const int window_height = 768;
constexpr int window_width = 540;
constexpr int window_height = 960;
if (argc < 2)
{
std::println("Usage: mosis-designer file.rml");
return EXIT_FAILURE;
}
const std::filesystem::path file = argv[1];
if (!std::filesystem::exists(file))
{
std::println("File does not exist");
return EXIT_FAILURE;
}
if (!Backend::Initialize("Load Document Sample", window_width, window_height, true))
{
return -1;
return EXIT_FAILURE;
}
Rml::SetSystemInterface(Backend::GetSystemInterface());
@@ -46,21 +51,19 @@ int main()
{
Rml::Shutdown();
Backend::Shutdown();
return -1;
return EXIT_FAILURE;
}
load_fonts();
const std::filesystem::path assets_path = std::filesystem::absolute(file.parent_path());
load_fonts(assets_path);
Rml::ElementDocument* document = context->LoadDocument("assets/demo.rml");
Rml::ElementDocument* document = context->LoadDocument(file.string());
if (document)
{
document->Show();
}
const std::wstring assets_path = std::filesystem::absolute(
std::filesystem::current_path() / "assets").wstring();
HANDLE hNotif = FindFirstChangeNotification(assets_path.c_str(),
const HANDLE hNotif = FindFirstChangeNotification(assets_path.c_str(),
TRUE, FILE_NOTIFY_CHANGE_LAST_WRITE);
bool running = true;
@@ -73,7 +76,7 @@ int main()
context->UnloadDocument(document);
context->Update();
std::this_thread::sleep_for(std::chrono::milliseconds(100));
document = context->LoadDocument("assets/demo.rml");
document = context->LoadDocument(file.string());
if (document)
{
document->ReloadStyleSheet();