Adds visual shader example

Introduces a visual shader example to demonstrate node-based shader creation.

This commit includes:
- Core node editor implementation with node dragging, linking, and selection
- Example nodes for color, perlin noise, add, multiply, and output
- Dynamic input pins to showcase node extension capabilities
- Integration with OpenGL for rendering node previews
This commit is contained in:
2025-10-16 10:33:01 -05:00
parent 724783bbaa
commit 627e6a93ea
8 changed files with 1694 additions and 708 deletions

25
.vscode/settings.json vendored Normal file
View File

@@ -0,0 +1,25 @@
{
"files.associations": {
"*.pyx": "python",
"*.js": "javascript",
"*.c": "c",
"*.scene": "yaml",
"*.cene": "yaml",
"*.h": "cpp",
"*.cpfb": "yaml",
"*.cproj": "yaml",
"*.oxprj": "yaml",
"*.oxsn": "yaml",
"*.oxmat": "yaml",
".oxdir": "yaml",
"*.prj": "yaml",
"*.proj": "yaml",
"*.pfapk": "yaml",
"*.pfprj": "yaml",
"*.pfscn": "yaml",
"*.pfproj": "yaml",
"*.pfab": "yaml",
"functional": "cpp",
"xstring": "cpp"
}
}

Binary file not shown.

View File

@@ -1,8 +1,24 @@
# ninja log v6 # ninja log v6
84 2052 7822408837196735 CMakeFiles/example.dir/examples/example_main.cpp.obj f3a7a0019cfc07e0 3090 3339 7822433156978395 libImNodeEditor.a 456ddb6c40baee90
15 3089 7822433126235298 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
268 4005 7822404087150964 _deps/glfw-build/src/CMakeFiles/glfw.dir/osmesa_context.c.obj d67a9ec78171ce20
84 3887 7822404085317893 _deps/glfw-build/src/CMakeFiles/glfw.dir/init.c.obj f3e1a6814fab5dfc
185 4056 7822404086327762 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_time.c.obj a242e57d2cf643f9
225 3913 7822404086725697 _deps/glfw-build/src/CMakeFiles/glfw.dir/wgl_context.c.obj 32037dfad6bdfb8d
424 4685 7822404089079832 CMakeFiles/imgui_backend.dir/_deps/imgui-src/backends/imgui_impl_opengl3.cpp.obj 5514e978228e1ebc
198 4015 7822404086442677 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_thread.c.obj 80dc1b59b95dd011
118 3764 7822404085675800 _deps/glfw-build/src/CMakeFiles/glfw.dir/vulkan.c.obj 1f8233e6b0ed7b50
131 4170 7822404085775287 _deps/glfw-build/src/CMakeFiles/glfw.dir/window.c.obj a90551e2d2b7521a
298 6400 7822404087453491 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui_draw.cpp.obj 29137eb50526d0e8
241 4208 7822404087050376 _deps/glfw-build/src/CMakeFiles/glfw.dir/egl_context.c.obj 9f0c92f4adf7bee
412 5114 7822404088600652 CMakeFiles/imgui_backend.dir/_deps/imgui-src/backends/imgui_impl_glfw.cpp.obj 9f4e9d49710cc85f
78 2061 7822433307832734 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
280 8823 7822404087330383 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui.cpp.obj 4fd7dc0f51068106
97 4033 7822404085455308 _deps/glfw-build/src/CMakeFiles/glfw.dir/input.c.obj 8cde78b708d9857d 97 4033 7822404085455308 _deps/glfw-build/src/CMakeFiles/glfw.dir/input.c.obj 8cde78b708d9857d
173 3851 7822404086205247 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_monitor.c.obj 9a0ac4f83887e8c7 173 3851 7822404086205247 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_monitor.c.obj 9a0ac4f83887e8c7
211 4144 7822404086577929 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_window.c.obj f9f6c4b3d1a1cbf8 211 4144 7822404086577929 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_window.c.obj f9f6c4b3d1a1cbf8
71 932 7822405013517257 _deps/glfw-build/src/libglfw3.a 66bf7edb872517f6
2063 2448 7822433327670595 example.exe 24050db2cb3fbf91
160 4051 7822404086076538 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_joystick.c.obj 5c3dadb99d89a7fd 160 4051 7822404086076538 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_joystick.c.obj 5c3dadb99d89a7fd
147 3983 7822404085950460 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_init.c.obj 89969a6ac4d02692 147 3983 7822404085950460 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_init.c.obj 89969a6ac4d02692
73 3910 7822404085205660 _deps/glfw-build/src/CMakeFiles/glfw.dir/context.c.obj d1ccfc4b99f23bc8 73 3910 7822404085205660 _deps/glfw-build/src/CMakeFiles/glfw.dir/context.c.obj d1ccfc4b99f23bc8
@@ -10,30 +26,57 @@
109 4024 7822404085555437 _deps/glfw-build/src/CMakeFiles/glfw.dir/monitor.c.obj af90e7682b0a4aed 109 4024 7822404085555437 _deps/glfw-build/src/CMakeFiles/glfw.dir/monitor.c.obj af90e7682b0a4aed
308 5363 7822404088336001 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui_tables.cpp.obj 2d674cd285f2fd5c 308 5363 7822404088336001 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui_tables.cpp.obj 2d674cd285f2fd5c
934 1169 7822405022132394 libimgui_backend.a 6a386f098e1fce40 934 1169 7822405022132394 libimgui_backend.a 6a386f098e1fce40
71 932 7822405013517257 _deps/glfw-build/src/libglfw3.a 66bf7edb872517f6 56 1956 7822472713077226 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
280 8823 7822404087330383 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui.cpp.obj 4fd7dc0f51068106 45 2964 7822472712957255 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
412 5114 7822404088600652 CMakeFiles/imgui_backend.dir/_deps/imgui-src/backends/imgui_impl_glfw.cpp.obj 9f4e9d49710cc85f 2965 3558 7822472742153217 libImNodeEditor.a 456ddb6c40baee90
241 4208 7822404087050376 _deps/glfw-build/src/CMakeFiles/glfw.dir/egl_context.c.obj 9f0c92f4adf7bee 3559 3995 7822472748098701 example.exe 24050db2cb3fbf91
298 6400 7822404087453491 CMakeFiles/imgui_backend.dir/_deps/imgui-src/imgui_draw.cpp.obj 29137eb50526d0e8 16 3867 7822537375416577 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
131 4170 7822404085775287 _deps/glfw-build/src/CMakeFiles/glfw.dir/window.c.obj a90551e2d2b7521a 81 289 7822538572226218 libImNodeEditor.a 456ddb6c40baee90
118 3764 7822404085675800 _deps/glfw-build/src/CMakeFiles/glfw.dir/vulkan.c.obj 1f8233e6b0ed7b50 96 3613 7822538572377335 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
198 4015 7822404086442677 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_thread.c.obj 80dc1b59b95dd011 3614 4044 7822538607547984 example.exe 24050db2cb3fbf91
424 4685 7822404089079832 CMakeFiles/imgui_backend.dir/_deps/imgui-src/backends/imgui_impl_opengl3.cpp.obj 5514e978228e1ebc 73 3510 7822541963289939 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
225 3913 7822404086725697 _deps/glfw-build/src/CMakeFiles/glfw.dir/wgl_context.c.obj 32037dfad6bdfb8d 3512 3727 7822541997680276 libImNodeEditor.a 456ddb6c40baee90
185 4056 7822404086327762 _deps/glfw-build/src/CMakeFiles/glfw.dir/win32_time.c.obj a242e57d2cf643f9 3727 4144 7822541999826322 example.exe 24050db2cb3fbf91
84 3887 7822404085317893 _deps/glfw-build/src/CMakeFiles/glfw.dir/init.c.obj f3e1a6814fab5dfc 90 3505 7822543710487466 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
268 4005 7822404087150964 _deps/glfw-build/src/CMakeFiles/glfw.dir/osmesa_context.c.obj d67a9ec78171ce20 78 3612 7822543710364331 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
113 2030 7822411801848076 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b 3612 3859 7822543745707185 libImNodeEditor.a 456ddb6c40baee90
87 2028 7822412934443910 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b 3860 4272 7822543748185225 example.exe 24050db2cb3fbf91
73 2948 7822412934323990 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c 25 3627 7822546097864252 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
2949 3143 7822412963070225 libImNodeEditor.a 456ddb6c40baee90 15 3766 7822546097754110 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
71 2117 7822413270987313 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b 3767 3962 7822546135274529 libImNodeEditor.a 456ddb6c40baee90
2118 2520 7822413291451011 example.exe 24050db2cb3fbf91 3962 4412 7822546137227874 example.exe 24050db2cb3fbf91
62 3579 7822428527763633 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c 79 3638 7822547190525516 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
3581 4167 7822428562950218 libImNodeEditor.a 456ddb6c40baee90 3640 3843 7822547226141759 libImNodeEditor.a 456ddb6c40baee90
4168 4647 7822428568807417 example.exe 24050db2cb3fbf91 3844 4248 7822547228177764 example.exe 24050db2cb3fbf91
25 2053 7822433126382984 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b 69 3436 7822548462021629 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
15 3089 7822433126235298 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c 3438 3635 7822548495705128 libImNodeEditor.a 456ddb6c40baee90
3090 3339 7822433156978395 libImNodeEditor.a 456ddb6c40baee90 3636 4036 7822548497688442 example.exe 24050db2cb3fbf91
78 2061 7822433307832734 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b 76 3326 7822549532299254 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
2063 2448 7822433327670595 example.exe 24050db2cb3fbf91 3328 3737 7822549564806395 example.exe 24050db2cb3fbf91
17 3335 7822549995306928 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
3337 3766 7822550028507266 example.exe 24050db2cb3fbf91
76 3457 7822550151294439 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
3459 3875 7822550185121303 example.exe 24050db2cb3fbf91
143 10357 7823306611699607 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
10359 10962 7823306713830722 libImNodeEditor.a 456ddb6c40baee90
10963 11678 7823306719877596 example.exe 24050db2cb3fbf91
67 3789 7823309506953785 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
3791 4017 7823309544178794 libImNodeEditor.a 456ddb6c40baee90
4018 4453 7823309546449824 example.exe 24050db2cb3fbf91
74 3509 7823312301146837 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
3510 3712 7823312335498111 libImNodeEditor.a 456ddb6c40baee90
85 3923 7823312301247986 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
3924 4365 7823312339642751 example.exe 24050db2cb3fbf91
12 3198 7823312851788484 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
3200 3614 7823312883658864 example.exe 24050db2cb3fbf91
78 3308 7823313965970563 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
68 3353 7823313965862794 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
3354 3523 7823313998716119 libImNodeEditor.a 456ddb6c40baee90
3524 3934 7823314000418284 example.exe 24050db2cb3fbf91
70 3482 7823317096605838 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
66 274 7823317294518774 libImNodeEditor.a 456ddb6c40baee90
84 3437 7823317294696793 CMakeFiles/example.dir/examples/example_main.cpp.obj c467c4ef9fc3e04b
3438 3916 7823317328239747 example.exe 24050db2cb3fbf91
67 3679 7823317603097648 CMakeFiles/ImNodeEditor.dir/src/ImNodeEditor.cpp.obj 966712c70001063c
3680 3852 7823317639232460 libImNodeEditor.a 456ddb6c40baee90
3853 4274 7823317640952473 example.exe 24050db2cb3fbf91

View File

@@ -1,37 +1,37 @@
# ninja log v6 # ninja log v6
138 5894 7822401371777906 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-download 7f735ebbdc7771c4 937 1113 7822471952263472 CMakeFiles/glfw-populate-complete 4cddece201ec9188
341 476 7822407174966710 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e 697 819 7822471949318212 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
477 618 7822407176388114 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d 820 937 7822471950496521 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
1023 1178 7822407181983705 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188
31 341 7822407170652486 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
138 5894 7822401371777906 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-download 7f735ebbdc7771c4
31 341 7822407170652486 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
888 1022 7822407180454144 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
1023 1178 7822407181983705 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188
3 137 7822401314240238 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-mkdir c4bf650da1719139
619 752 7822407177737595 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
477 618 7822407176388114 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d
619 752 7822407177737595 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
752 887 7822407179084371 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
1023 1178 7822407181983705 CMakeFiles/glfw-populate-complete 4cddece201ec9188
752 887 7822407179084371 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
888 1022 7822407180454144 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
3 137 7822401314240238 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-mkdir c4bf650da1719139 3 137 7822401314240238 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-mkdir c4bf650da1719139
1023 1178 7822407181983705 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/CMakeFiles/glfw-populate-complete 4cddece201ec9188 326 437 7822471945495306 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e
341 476 7822407174966710 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e 937 1113 7822471952263472 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/CMakeFiles/glfw-populate-complete 4cddece201ec9188
30 307 7822411484831447 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05 29 326 7822471941544161 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
30 307 7822411484831447 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05 138 5894 7822401371777906 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-download 7f735ebbdc7771c4
307 426 7822411488702147 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e 937 1113 7822471952263472 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188
307 426 7822411488702147 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e 29 326 7822471941544161 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
426 543 7822411489838979 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d 326 437 7822471945495306 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e
426 543 7822411489838979 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d 437 572 7822471946850704 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d
543 669 7822411491102420 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4 138 5894 7822401371777906 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-download 7f735ebbdc7771c4
543 669 7822411491102420 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4 697 819 7822471949318212 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
669 786 7822411492254658 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a 572 697 7822471948083024 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
669 786 7822411492254658 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a 437 572 7822471946850704 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d
786 932 7822411493727986 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003 572 697 7822471948083024 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
786 932 7822411493727986 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003 3 137 7822401314240238 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-mkdir c4bf650da1719139
933 1097 7822411495399413 CMakeFiles/glfw-populate-complete 4cddece201ec9188 937 1113 7822471952263472 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188
933 1097 7822411495399413 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188 820 937 7822471950496521 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
933 1097 7822411495399413 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/CMakeFiles/glfw-populate-complete 4cddece201ec9188 29 279 7822472263960994 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
933 1097 7822411495399413 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188 29 279 7822472263960994 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-update 51a2c9a7e2c01d05
280 414 7822472267686654 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e
280 414 7822472267686654 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-patch befe706765e06c7e
415 532 7822472268853692 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d
415 532 7822472268853692 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-configure c6363d4a42b7216d
532 662 7822472270162231 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
532 662 7822472270162231 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-build fc4a2343fc48d7e4
662 807 7822472271606708 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
662 807 7822472271606708 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-install 2beb8017f4dd468a
808 936 7822472272904603 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
808 936 7822472272904603 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-test aafb314e77508003
937 1091 7822472274467529 CMakeFiles/glfw-populate-complete 4cddece201ec9188
937 1091 7822472274467529 glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188
937 1091 7822472274467529 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/CMakeFiles/glfw-populate-complete 4cddece201ec9188
937 1091 7822472274467529 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/glfw-subbuild/glfw-populate-prefix/src/glfw-populate-stamp/glfw-populate-done 4cddece201ec9188

View File

@@ -1,37 +1,37 @@
# ninja log v6 # ninja log v6
2793 2907 7822407216228415 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
2907 3020 7822407217366371 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
2793 2907 7822407216228415 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
2451 2567 7822407212823982 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
3 145 7822403684378952 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-mkdir f89c51b70f7badb6
3021 3180 7822407218975940 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145
31 2451 7822407187572036 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
31 2451 7822407187572036 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
3021 3180 7822407218975940 CMakeFiles/imgui-populate-complete a8b496480a89f145
146 21510 7822403898057628 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-download 857718ddc22f5ad4
2679 2792 7822407215072628 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
146 21510 7822403898057628 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-download 857718ddc22f5ad4
3021 3180 7822407218975940 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/CMakeFiles/imgui-populate-complete a8b496480a89f145
3 145 7822403684378952 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-mkdir f89c51b70f7badb6
2567 2679 7822407213936795 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2679 2792 7822407215072628 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
2907 3020 7822407217366371 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
2567 2679 7822407213936795 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2451 2567 7822407212823982 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
3021 3180 7822407218975940 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145
26 2605 7822411501572845 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
26 2605 7822411501572845 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
2606 2730 7822411528493762 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
2606 2730 7822411528493762 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
2730 2864 7822411529846716 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2730 2864 7822411529846716 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2864 3001 7822411531225109 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
2864 3001 7822411531225109 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
3002 3115 7822411532339106 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
3002 3115 7822411532339106 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f 3002 3115 7822411532339106 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
2730 2864 7822411529846716 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2864 3001 7822411531225109 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
3115 3239 7822411533595996 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793 3115 3239 7822411533595996 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
3115 3239 7822411533595996 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793 2730 2864 7822411529846716 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
3239 3415 7822411535322548 CMakeFiles/imgui-populate-complete a8b496480a89f145 2606 2730 7822411528493762 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
3239 3415 7822411535322548 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145 3239 3415 7822411535322548 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145
3239 3415 7822411535322548 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/CMakeFiles/imgui-populate-complete a8b496480a89f145 3 145 7822403684378952 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-mkdir f89c51b70f7badb6
3239 3415 7822411535322548 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145 3239 3415 7822411535322548 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145
26 2605 7822411501572845 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
146 21510 7822403898057628 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-download 857718ddc22f5ad4
2864 3001 7822411531225109 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
3002 3115 7822411532339106 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
3115 3239 7822411533595996 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
2606 2730 7822411528493762 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
3 145 7822403684378952 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-mkdir f89c51b70f7badb6
3239 3415 7822411535322548 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/CMakeFiles/imgui-populate-complete a8b496480a89f145
146 21510 7822403898057628 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-download 857718ddc22f5ad4
3239 3415 7822411535322548 CMakeFiles/imgui-populate-complete a8b496480a89f145
26 2605 7822411501572845 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
30 2391 7822472280584745 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
30 2391 7822472280584745 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-update 8ab8390382dbffc1
2392 2512 7822472305278911 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
2392 2512 7822472305278911 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-patch e4059445e234262b
2512 2635 7822472306524491 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2512 2635 7822472306524491 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-configure 4386e735d761763
2635 2745 7822472307633470 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
2635 2745 7822472307633470 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-build 33fca7b05f71ffce
2746 2856 7822472308738885 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
2746 2856 7822472308738885 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-install e11a74d4e3841e6f
2856 2966 7822472309826870 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
2856 2966 7822472309826870 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-test e890b28039c12793
2967 3112 7822472311300107 CMakeFiles/imgui-populate-complete a8b496480a89f145
2967 3112 7822472311300107 imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145
2967 3112 7822472311300107 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/CMakeFiles/imgui-populate-complete a8b496480a89f145
2967 3112 7822472311300107 C:/Users/spenc/OneDrive/Documents/GitHub/ImNodeEditor/build/_deps/imgui-subbuild/imgui-populate-prefix/src/imgui-populate-stamp/imgui-populate-done a8b496480a89f145

View File

@@ -1,4 +1,17 @@
#include <cstdio> #include <cstdio>
#include <vector>
#include <array>
#include <cmath>
#include <cstdint>
#include <unordered_map>
#include <unordered_set>
#include <optional>
#include <random>
#include <algorithm>
#include <cstdlib> // std::rand
#define _USE_MATH_DEFINES
#include <math.h>
// GLEW must come before GLFW / any GL header // GLEW must come before GLFW / any GL header
#include <GL/glew.h> #include <GL/glew.h>
@@ -10,13 +23,448 @@
#include "ImNodeEditor.h" #include "ImNodeEditor.h"
static void glfw_error_callback(int error, const char* desc) { // -------------------------------------------------
// Window / ImGui boilerplate
// -------------------------------------------------
static void glfw_error_callback(int error, const char *desc)
{
std::fprintf(stderr, "GLFW error %d: %s\n", error, desc); std::fprintf(stderr, "GLFW error %d: %s\n", error, desc);
} }
int main() { // -------------------------------------------------
// Tiny GL helpers
// -------------------------------------------------
static GLuint CreateTextureRGBA8(int w, int h, const void *pixels = nullptr)
{
GLuint tex = 0;
glGenTextures(1, &tex);
glBindTexture(GL_TEXTURE_2D, tex);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
return tex;
}
static void UpdateTextureRGBA8(GLuint tex, int w, int h, const void *pixels)
{
glBindTexture(GL_TEXTURE_2D, tex);
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, w, h, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
}
// -------------------------------------------------
// Simple 2D Perlin noise for 128x128 previews.
// -------------------------------------------------
struct Perlin2D
{
std::array<int, 512> p{};
explicit Perlin2D(uint32_t seed = 0xC0FFEE)
{
std::vector<int> perm(256);
for (int i = 0; i < 256; i++)
perm[i] = i;
std::mt19937 rng(seed);
std::shuffle(perm.begin(), perm.end(), rng);
for (int i = 0; i < 512; i++)
p[i] = perm[i & 255];
}
static inline float fade(float t) { return t * t * t * (t * (t * 6 - 15) + 10); }
static inline float lerp(float a, float b, float t) { return a + t * (b - a); }
static inline float grad(int h, float x, float y)
{
switch (h & 3)
{
case 0:
return x + y;
case 1:
return -x + y;
case 2:
return x - y;
default:
return -x - y;
}
}
float noise(float x, float y) const
{
int X = (int)floorf(x) & 255;
int Y = (int)floorf(y) & 255;
x -= floorf(x);
y -= floorf(y);
float u = fade(x);
float v = fade(y);
int A = p[X] + Y;
int B = p[X + 1] + Y;
float n00 = grad(p[A], x, y);
float n10 = grad(p[B], x - 1, y);
float n01 = grad(p[A + 1], x, y - 1);
float n11 = grad(p[B + 1], x - 1, y - 1);
float nx0 = lerp(n00, n10, u);
float nx1 = lerp(n01, n11, u);
return lerp(nx0, nx1, v); // ~[-1,1]
}
};
// -------------------------------------------------
// Node runtime / evaluation
// -------------------------------------------------
using namespace ImNodeEditor;
enum class NodeKind
{
Color,
Perlin,
Add, // dynamic fan-in
Multiply, // 2 inputs
Output
};
static constexpr int kPrevW = 128;
static constexpr int kPrevH = 128;
struct NodeRuntime
{
NodeKind kind{};
std::vector<uint8_t> rgba; // kPrevW*kPrevH*4
GLuint tex = 0;
bool dirty = true;
// params
ImVec4 color{1, 0, 0, 1}; // Color
float perlinScale = 6.0f; // Perlin
uint32_t perlinSeed = 1337; // Perlin
// For Add dynamic pins we keep a list of input pin IDs (UI helper)
std::vector<int> dynamicInputs;
};
// storage: nodeId -> runtime
static std::unordered_map<int, NodeRuntime> gNodeData;
static NodeRuntime &GetData(int nodeId)
{
auto it = gNodeData.find(nodeId);
if (it == gNodeData.end())
{
it = gNodeData.emplace(nodeId, NodeRuntime{}).first;
it->second.rgba.resize(kPrevW * kPrevH * 4, 0);
it->second.tex = CreateTextureRGBA8(kPrevW, kPrevH, it->second.rgba.data());
it->second.dirty = true;
}
return it->second;
}
// Evaluate a single node into its preview texture (assumes upstream ready)
static void EvalNode(Editor &ed, int nodeId)
{
Node *n = ed.GetNode(nodeId);
if (!n)
return;
NodeRuntime &data = GetData(nodeId);
if (!data.dirty)
return;
auto &px = data.rgba;
px.assign(kPrevW * kPrevH * 4, 0);
switch (data.kind)
{
case NodeKind::Color:
{
const uint8_t r = (uint8_t)std::roundf(std::clamp(data.color.x, 0.0f, 1.0f) * 255.0f);
const uint8_t g = (uint8_t)std::roundf(std::clamp(data.color.y, 0.0f, 1.0f) * 255.0f);
const uint8_t b = (uint8_t)std::roundf(std::clamp(data.color.z, 0.0f, 1.0f) * 255.0f);
const uint8_t a = (uint8_t)std::roundf(std::clamp(data.color.w, 0.0f, 1.0f) * 255.0f);
for (int i = 0; i < kPrevW * kPrevH; i++)
{
px[i * 4 + 0] = r;
px[i * 4 + 1] = g;
px[i * 4 + 2] = b;
px[i * 4 + 3] = a;
}
}
break;
case NodeKind::Perlin:
{
Perlin2D p{data.perlinSeed};
for (int y = 0; y < kPrevH; y++)
{
for (int x = 0; x < kPrevW; x++)
{
float fx = (float)x / (float)kPrevW;
float fy = (float)y / (float)kPrevH;
float v = p.noise(fx * data.perlinScale, fy * data.perlinScale); // [-1,1]
float g = 0.5f * (v + 1.0f); // [0,1]
uint8_t c = (uint8_t)std::roundf(g * 255.0f);
int i = (y * kPrevW + x) * 4;
px[i + 0] = c;
px[i + 1] = c;
px[i + 2] = c;
px[i + 3] = 255;
}
}
}
break;
case NodeKind::Add:
{
// Gather upstream pixels for each input
std::vector<const std::vector<uint8_t> *> upstreamPx;
for (int inPid : n->inputs)
{
for (int lid : ed.GetLinksForPin(inPid))
{
const Link *L = ed.GetLink(lid);
if (!L)
continue;
const Pin *sp = ed.GetPin(L->aPin);
if (!sp)
continue;
auto it = gNodeData.find(sp->node);
if (it != gNodeData.end())
upstreamPx.push_back(&it->second.rgba);
}
}
if (!upstreamPx.empty())
{
for (int i = 0; i < kPrevW * kPrevH; i++)
{
int accR = 0, accG = 0, accB = 0, accA = 0;
for (auto *v : upstreamPx)
{
accR += (*v)[i * 4 + 0];
accG += (*v)[i * 4 + 1];
accB += (*v)[i * 4 + 2];
accA += (*v)[i * 4 + 3];
}
px[i * 4 + 0] = (uint8_t)std::min(accR, 255);
px[i * 4 + 1] = (uint8_t)std::min(accG, 255);
px[i * 4 + 2] = (uint8_t)std::min(accB, 255);
px[i * 4 + 3] = (uint8_t)std::min(accA, 255);
}
}
}
break;
case NodeKind::Multiply:
{
// Expect 2 inputs: A * B, clamp to [0,1]
std::vector<const std::vector<uint8_t> *> upstreamPx;
for (int inPid : n->inputs)
{
for (int lid : ed.GetLinksForPin(inPid))
{
const Link *L = ed.GetLink(lid);
if (!L)
continue;
const Pin *sp = ed.GetPin(L->aPin);
if (!sp)
continue;
auto it = gNodeData.find(sp->node);
if (it != gNodeData.end())
upstreamPx.push_back(&it->second.rgba);
}
}
if (upstreamPx.size() >= 2)
{
auto *A = upstreamPx[0];
auto *B = upstreamPx[1];
for (int i = 0; i < kPrevW * kPrevH; i++)
{
float r = ((*A)[i * 4 + 0] / 255.0f) * ((*B)[i * 4 + 0] / 255.0f);
float g = ((*A)[i * 4 + 1] / 255.0f) * ((*B)[i * 4 + 1] / 255.0f);
float b = ((*A)[i * 4 + 2] / 255.0f) * ((*B)[i * 4 + 2] / 255.0f);
float a = ((*A)[i * 4 + 3] / 255.0f) * ((*B)[i * 4 + 3] / 255.0f);
px[i * 4 + 0] = (uint8_t)std::roundf(std::clamp(r, 0.0f, 1.0f) * 255.0f);
px[i * 4 + 1] = (uint8_t)std::roundf(std::clamp(g, 0.0f, 1.0f) * 255.0f);
px[i * 4 + 2] = (uint8_t)std::roundf(std::clamp(b, 0.0f, 1.0f) * 255.0f);
px[i * 4 + 3] = (uint8_t)std::roundf(std::clamp(a, 0.0f, 1.0f) * 255.0f);
}
}
}
break;
case NodeKind::Output:
{
// Output mirrors its first input (or black if not connected)
const std::vector<uint8_t> *src = nullptr;
if (!n->inputs.empty())
{
int inPid = n->inputs[0];
for (int lid : ed.GetLinksForPin(inPid))
{
const Link *L = ed.GetLink(lid);
if (!L)
continue;
const Pin *sp = ed.GetPin(L->aPin);
if (!sp)
continue;
auto it = gNodeData.find(sp->node);
if (it != gNodeData.end())
src = &it->second.rgba;
}
}
if (src)
{
px.assign(src->begin(), src->end());
}
}
break;
}
UpdateTextureRGBA8(data.tex, kPrevW, kPrevH, px.data());
ed.SetNodeImage(nodeId, (ImTextureID)(intptr_t)data.tex, ImVec2((float)kPrevW, (float)kPrevH));
data.dirty = false;
}
static void EvaluateGraph(Editor &ed)
{
auto order = ed.TopoSort();
std::unordered_set<int> inOrder(order.begin(), order.end());
for (auto &kv : gNodeData)
{
if (!inOrder.count(kv.first))
order.push_back(kv.first);
}
for (int nid : order)
{
EvalNode(ed, nid);
}
}
static void BuildGraph(Editor &editor)
{
auto PreviewSize = [](const ImRect& local) {
// Make previews smaller so pins/labels stay inside node
float w = local.Max.x - local.Min.x;
return ImMin(w, 110.0f); // cap to 110 px
};
// Color node
const int nColor = editor.AddNode("Color", ImVec2(80, 80));
const int nColorOut = editor.AddPin(nColor, PinKind::Output, PinType::Texture);
editor.SetPinLabel(nColorOut, "Tex");
{
auto &D = GetData(nColor);
D.kind = NodeKind::Color;
editor.SetNodeDrawFunction(nColor, [&](const ImRect &local, Node &node)
{
auto& d = GetData(node.id);
float s = PreviewSize(local);
ImGui::Image((ImTextureID)(intptr_t)d.tex, ImVec2(s, s));
if (ImGui::ColorEdit4("Color", &d.color.x, ImGuiColorEditFlags_NoInputs))
d.dirty = true;
});
}
// Perlin noise node
const int nNoise = editor.AddNode("Perlin Noise", ImVec2(80, 270));
const int nNoiseOut = editor.AddPin(nNoise, PinKind::Output, PinType::Texture);
editor.SetPinLabel(nNoiseOut, "Tex");
{
auto &D = GetData(nNoise);
D.kind = NodeKind::Perlin;
editor.SetNodeDrawFunction(nNoise, [&](const ImRect &local, Node &node)
{
auto& d = GetData(node.id);
float s = PreviewSize(local);
ImGui::Image((ImTextureID)(intptr_t)d.tex, ImVec2(s, s));
ImGui::TextUnformatted("Scale"); ImGui::SameLine();
if (ImGui::SliderFloat("##perlin_scale", &d.perlinScale, 1.0f, 32.0f))
d.dirty = true;
if (ImGui::Button("Reseed")) { d.perlinSeed = (uint32_t)std::rand(); d.dirty = true; }
});
}
// Add node (dynamic inputs)
const int nAdd = editor.AddNode("Add (Dynamic)", ImVec2(360, 120));
const int addInA = editor.AddPin(nAdd, PinKind::Input, PinType::Texture);
const int addInB = editor.AddPin(nAdd, PinKind::Input, PinType::Texture);
const int addOut = editor.AddPin(nAdd, PinKind::Output, PinType::Texture);
editor.SetPinLabel(addInA, "A");
editor.SetPinLabel(addInB, "B");
editor.SetPinLabel(addOut, "Tex");
{
auto &D = GetData(nAdd);
D.kind = NodeKind::Add;
D.dynamicInputs = {addInA, addInB};
editor.SetNodeDrawFunction(nAdd, [&](const ImRect &local, Node &node)
{
auto& d = GetData(node.id);
float s = PreviewSize(local);
ImGui::Image((ImTextureID)(intptr_t)d.tex, ImVec2(s, s));
if (ImGui::Button("+ Input")) {
int newIn = editor.AddPin(node.id, PinKind::Input, PinType::Texture);
editor.SetPinLabel(newIn, ("In " + std::to_string((int)node.inputs.size()-1)).c_str());
d.dynamicInputs.push_back(newIn);
d.dirty = true;
}
ImGui::SameLine();
if (!d.dynamicInputs.empty()) {
if (ImGui::Button("- Input")) {
int pid = d.dynamicInputs.back();
bool connected = false;
for (int lid : editor.GetLinksForPin(pid)) { (void)lid; connected = true; break; }
if (!connected && node.inputs.size() > 1) {
d.dynamicInputs.pop_back();
d.dirty = true;
}
}
}
});
}
// Multiply (normalized)
const int nMul = editor.AddNode("Multiply (Normalized)", ImVec2(360, 320));
const int mulInA = editor.AddPin(nMul, PinKind::Input, PinType::Texture);
const int mulInB = editor.AddPin(nMul, PinKind::Input, PinType::Texture);
const int mulOut = editor.AddPin(nMul, PinKind::Output, PinType::Texture);
editor.SetPinLabel(mulInA, "A");
editor.SetPinLabel(mulInB, "B");
editor.SetPinLabel(mulOut, "Tex");
{
auto &D = GetData(nMul);
D.kind = NodeKind::Multiply;
editor.SetNodeDrawFunction(nMul, [&](const ImRect &local, Node &node)
{
auto &d = GetData(node.id);
float s = PreviewSize(local);
ImGui::Image((ImTextureID)(intptr_t)d.tex, ImVec2(s, s));
});
}
// Output node
const int nOut = editor.AddNode("Output", ImVec2(680, 220));
const int outIn = editor.AddPin(nOut, PinKind::Input, PinType::Texture);
editor.SetPinLabel(outIn, "In");
{
auto &D = GetData(nOut);
D.kind = NodeKind::Output;
editor.SetNodeDrawFunction(nOut, [&](const ImRect &local, Node &node)
{
auto& d = GetData(node.id);
float s = PreviewSize(local);
ImGui::Image((ImTextureID)(intptr_t)d.tex, ImVec2(s, s));
});
}
// Example wiring
editor.AddLink(nColorOut, addInA);
editor.AddLink(nNoiseOut, addInB);
editor.AddLink(addOut, mulInA);
editor.AddLink(nColorOut, mulInB);
editor.AddLink(mulOut, outIn);
}
int main()
{
glfwSetErrorCallback(glfw_error_callback); glfwSetErrorCallback(glfw_error_callback);
if (!glfwInit()) return 1; if (!glfwInit())
return 1;
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
@@ -25,15 +473,20 @@ int main() {
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
#endif #endif
GLFWwindow* window = glfwCreateWindow(1280, 720, "ImNodeEditor - Example", nullptr, nullptr); GLFWwindow *window = glfwCreateWindow(1280, 720, "ImNodeEditor - Visual Shader Example", nullptr, nullptr);
if (!window) { glfwTerminate(); return 2; } if (!window)
{
glfwTerminate();
return 2;
}
glfwMakeContextCurrent(window); glfwMakeContextCurrent(window);
glfwSwapInterval(1); glfwSwapInterval(1);
// ---- GLEW init ---- // ---- GLEW init ----
glewExperimental = GL_TRUE; glewExperimental = GL_TRUE;
GLenum err = glewInit(); GLenum err = glewInit();
if (err != GLEW_OK) { if (err != GLEW_OK)
{
std::fprintf(stderr, "GLEW init error: %s\n", glewGetErrorString(err)); std::fprintf(stderr, "GLEW init error: %s\n", glewGetErrorString(err));
return 3; return 3;
} }
@@ -42,47 +495,28 @@ int main() {
// ImGui // ImGui
IMGUI_CHECKVERSION(); IMGUI_CHECKVERSION();
ImGui::CreateContext(); ImGui::CreateContext();
ImGuiIO& io = ImGui::GetIO(); (void)io; ImGuiIO &io = ImGui::GetIO();
(void)io;
io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard | ImGuiConfigFlags_DockingEnable; io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard | ImGuiConfigFlags_DockingEnable;
ImGui::StyleColorsDark(); ImGui::StyleColorsDark();
ImGui_ImplGlfw_InitForOpenGL(window, true); ImGui_ImplGlfw_InitForOpenGL(window, true);
ImGui_ImplOpenGL3_Init("#version 330 core"); ImGui_ImplOpenGL3_Init("#version 330 core");
using namespace ImNodeEditor;
Editor editor; Editor editor;
BuildGraph(editor);
// Seed example nodes/links with types
const int n1 = editor.AddNode("Number", ImVec2(100, 120));
const int n1_out = editor.AddPin(n1, PinKind::Output, PinType::Float);
const int n2 = editor.AddNode("Multiply", ImVec2(380, 160));
const int n2_inA = editor.AddPin(n2, PinKind::Input, PinType::Float);
const int n2_inB = editor.AddPin(n2, PinKind::Input, PinType::Float);
const int n2_out = editor.AddPin(n2, PinKind::Output, PinType::Float);
const int n3 = editor.AddNode("Output", ImVec2(700, 200));
const int n3_in = editor.AddPin(n3, PinKind::Input, PinType::Float);
// Texture node to showcase color/type (not connected by default)
const int n4 = editor.AddNode("Texture", ImVec2(120, 300));
const int n4_out = editor.AddPin(n4, PinKind::Output, PinType::Texture);
editor.AddLink(n1_out, n2_inA);
editor.AddLink(n2_out, n3_in);
bool show_demo_window = false; bool show_demo_window = false;
bool show_editor_window = true; bool show_editor_window = true;
while (!glfwWindowShouldClose(window)) { while (!glfwWindowShouldClose(window))
{
glfwPollEvents(); glfwPollEvents();
ImGui_ImplOpenGL3_NewFrame(); ImGui_ImplOpenGL3_NewFrame();
ImGui_ImplGlfw_NewFrame(); ImGui_ImplGlfw_NewFrame();
ImGui::NewFrame(); ImGui::NewFrame();
// DockSpace // DockSpace
{ {
ImGuiWindowFlags flags = ImGuiWindowFlags_MenuBar | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags flags = ImGuiWindowFlags_MenuBar | ImGuiWindowFlags_NoDocking |
@@ -90,7 +524,7 @@ int main() {
ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove |
ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoNavFocus; ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoNavFocus;
const ImGuiViewport* viewport = ImGui::GetMainViewport(); const ImGuiViewport *viewport = ImGui::GetMainViewport();
ImGui::SetNextWindowPos(viewport->Pos); ImGui::SetNextWindowPos(viewport->Pos);
ImGui::SetNextWindowSize(viewport->Size); ImGui::SetNextWindowSize(viewport->Size);
ImGui::SetNextWindowViewport(viewport->ID); ImGui::SetNextWindowViewport(viewport->ID);
@@ -99,27 +533,34 @@ int main() {
ImGui::Begin("RootDock", nullptr, flags); ImGui::Begin("RootDock", nullptr, flags);
ImGui::PopStyleVar(2); ImGui::PopStyleVar(2);
ImGuiID dockspace_id = ImGui::GetID("RootDockSpace"); ImGuiID dockspace_id = ImGui::GetID("RootDockSpace");
ImGui::DockSpace(dockspace_id, ImVec2(0,0)); ImGui::DockSpace(dockspace_id, ImVec2(0, 0));
if (ImGui::BeginMenuBar()) { if (ImGui::BeginMenuBar())
if (ImGui::BeginMenu("File")) { {
if (ImGui::MenuItem("Save Graph")) { if (ImGui::BeginMenu("File"))
{
if (ImGui::MenuItem("Save Graph"))
{
std::string s = editor.SaveToString(); std::string s = editor.SaveToString();
std::puts("---- SAVE ----"); std::puts("---- SAVE ----");
std::puts(s.c_str()); std::puts(s.c_str());
} }
if (ImGui::MenuItem("Load Minimal")) { if (ImGui::MenuItem("Load Minimal"))
const char* text = {
const char *text =
"NODE 1 100 100 A\n" "NODE 1 100 100 A\n"
"NODE 2 300 160 B\n" "NODE 2 300 160 B\n"
"PIN 1 1 1 0 1\n" "PIN 1 1 1 0 1\n"
"PIN 2 2 0 0 1\n" "PIN 2 2 0 0 1\n"
"LINK 1 1 2\n"; "LINK 1 1 2\n";
editor.LoadFromString(text); editor.LoadFromString(text);
// NOTE: If you load an external graph, rebuild gNodeData/kinds accordingly.
} }
if (ImGui::MenuItem("Quit")) glfwSetWindowShouldClose(window, GLFW_TRUE); if (ImGui::MenuItem("Quit"))
glfwSetWindowShouldClose(window, GLFW_TRUE);
ImGui::EndMenu(); ImGui::EndMenu();
} }
if (ImGui::BeginMenu("View")) { if (ImGui::BeginMenu("View"))
{
ImGui::MenuItem("Show ImGui Demo", nullptr, &show_demo_window); ImGui::MenuItem("Show ImGui Demo", nullptr, &show_demo_window);
ImGui::EndMenu(); ImGui::EndMenu();
} }
@@ -128,8 +569,15 @@ int main() {
ImGui::End(); ImGui::End();
} }
if (show_editor_window) { if (show_editor_window)
{
ImGui::Begin("Node Editor", nullptr, ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_NoScrollbar); ImGui::Begin("Node Editor", nullptr, ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_NoScrollbar);
// For simplicity, re-eval each frame (mark dirty)
for (auto &kv : gNodeData)
kv.second.dirty = true;
EvaluateGraph(editor);
ImVec2 avail = ImGui::GetContentRegionAvail(); ImVec2 avail = ImGui::GetContentRegionAvail();
editor.Draw("MainCanvas", avail); editor.Draw("MainCanvas", avail);
ImGui::End(); ImGui::End();
@@ -145,6 +593,13 @@ int main() {
glfwSwapBuffers(window); glfwSwapBuffers(window);
} }
for (auto &kv : gNodeData)
{
if (kv.second.tex)
glDeleteTextures(1, &kv.second.tex);
}
gNodeData.clear();
ImGui_ImplOpenGL3_Shutdown(); ImGui_ImplOpenGL3_Shutdown();
ImGui_ImplGlfw_Shutdown(); ImGui_ImplGlfw_Shutdown();
ImGui::DestroyContext(); ImGui::DestroyContext();

File diff suppressed because it is too large Load Diff

View File

@@ -63,12 +63,17 @@ struct EditorConfig {
ColorTheme colors{}; ColorTheme colors{};
}; };
struct Node;
using NodeDrawFn = std::function<void(const ImRect& screenContentRect, Node& node)>;
struct Pin { struct Pin {
int id = 0; int id = 0;
int node = 0; int node = 0;
PinKind kind = PinKind::Input; PinKind kind = PinKind::Input;
int order = 0; int order = 0;
PinType type = PinType::Any; PinType type = PinType::Any;
std::string label; // optional label (shown near pin)
ImVec2 localPos{}; ImVec2 localPos{};
ImRect rect{}; ImRect rect{};
}; };
@@ -81,6 +86,14 @@ struct Node {
std::vector<int> inputs; std::vector<int> inputs;
std::vector<int> outputs; std::vector<int> outputs;
bool selected = false; bool selected = false;
NodeDrawFn draw;
void* userData = nullptr; // arbitrary pointer you manage
ImTextureID image = 0;
ImVec2 imageSize{0,0}; // natural size (for aspect-fit)
ImVec2 imageUV0{0,0};
ImVec2 imageUV1{1,1};
}; };
struct Link { struct Link {
@@ -138,6 +151,40 @@ public:
const EditorConfig& GetConfig() const { return m_cfg; } const EditorConfig& GetConfig() const { return m_cfg; }
void SetConfig(const EditorConfig& cfg) { m_cfg = cfg; } void SetConfig(const EditorConfig& cfg) { m_cfg = cfg; }
// -------- New: convenience APIs --------
// Set a node's custom draw callback (body content).
void SetNodeDrawFunction(int nodeId, NodeDrawFn fn);
// Set an image to be drawn in the node body (aspect-fit inside the content rect).
void SetNodeImage(int nodeId, ImTextureID tex, ImVec2 naturalSize,
ImVec2 uv0 = ImVec2(0,0), ImVec2 uv1 = ImVec2(1,1));
// Label a pin (shown near the circle).
void SetPinLabel(int pinId, const std::string& label);
// Graph traversal utilities (simple & convenient):
// For a pin, get all link IDs attached to it.
std::vector<int> GetLinksForPin(int pinId) const;
// For a node, get nodes that feed INTO this node (via its input pins).
std::vector<int> GetUpstreamNodes(int nodeId) const;
// For a node, get nodes that this node feeds INTO (via its output pins).
std::vector<int> GetDownstreamNodes(int nodeId) const;
// For a node, iterate each input edge: calls cb(srcNodeId, srcPinId, linkId, dstPinId).
template<typename Fn>
void ForEachInputEdge(int nodeId, Fn cb) const;
// For a node, iterate each output edge: calls cb(dstNodeId, dstPinId, linkId, srcPinId).
template<typename Fn>
void ForEachOutputEdge(int nodeId, Fn cb) const;
// Topological sort of the graph (assuming it is a DAG). Returns a list of node IDs.
std::vector<int> TopoSort() const;
private: private:
// Drawing // Drawing
void DrawCanvasBackground(ImDrawList* dl, const ImRect& canvas); void DrawCanvasBackground(ImDrawList* dl, const ImRect& canvas);
@@ -195,4 +242,40 @@ private:
HoverInfo m_hover{}; HoverInfo m_hover{};
}; };
// ---------- template implementations ----------
template<typename Fn>
inline void Editor::ForEachInputEdge(int nodeId, Fn cb) const
{
const Node* n = GetNode(nodeId);
if (!n) return;
for (int inPid : n->inputs) {
for (auto& kv : m_links) {
const Link& L = kv.second;
if (L.bPin == inPid) {
const Pin* srcPin = GetPin(L.aPin);
if (!srcPin) continue;
cb(srcPin->node, srcPin->id, L.id, inPid);
}
}
}
}
template<typename Fn>
inline void Editor::ForEachOutputEdge(int nodeId, Fn cb) const
{
const Node* n = GetNode(nodeId);
if (!n) return;
for (int outPid : n->outputs) {
for (auto& kv : m_links) {
const Link& L = kv.second;
if (L.aPin == outPid) {
const Pin* dstPin = GetPin(L.bPin);
if (!dstPin) continue;
cb(dstPin->node, dstPin->id, L.id, outPid);
}
}
}
}
} // namespace ImNodeEditor } // namespace ImNodeEditor