Slit shift, channel split, pixel sort, corruption, shatter, warp, bit crush and feedback: tearing bands sideways, knocking the colour planes out of register, sorting runs of pixels, damaging blocks the way a broken stream does, breaking the picture into shards, pushing it along a noise field, mangling its bytes and laying it over itself again and again. All eight are pure transforms. None needs sources, so any of them can lead a chain, and like blur they start from a crop of a random source when they do and photographs are loaded. canvasFromSources holds that start once for them. Each draws its whole plan from the rng before touching a pixel, and pixel sort hands every line a seed of its own, so the parallel work never decides anything. The rotations in shatter and feedback take their sine and cosine from a short series of plain multiplications rather than libm, so a seed lands on the same pixels whatever the machine's maths library makes of std::sin. The tests hold every one of them to the same things -- a seed reproduces it, it runs without sources and as a later stage, a sliver of a canvas does not trip it, turned right down it leaves its input alone -- plus a check of what each actually does, and the registry now checks that no two effects declare the same param key. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
74 lines
2.3 KiB
CMake
74 lines
2.3 KiB
CMake
cmake_minimum_required(VERSION 3.20)
|
|
project(effector VERSION 0.1.0 LANGUAGES CXX)
|
|
|
|
set(CMAKE_CXX_STANDARD 20)
|
|
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
|
set(CMAKE_CXX_EXTENSIONS OFF)
|
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
|
|
|
if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
|
|
set(CMAKE_BUILD_TYPE Release CACHE STRING "Build type" FORCE)
|
|
endif()
|
|
|
|
set(CMAKE_CXX_FLAGS_RELEASE "-O3 -DNDEBUG")
|
|
|
|
find_package(PkgConfig REQUIRED)
|
|
pkg_check_modules(GTKMM REQUIRED IMPORTED_TARGET gtkmm-4.0)
|
|
pkg_check_modules(GDKPIXBUF REQUIRED IMPORTED_TARGET gdk-pixbuf-2.0)
|
|
# Pango and Cairo draw the text effect's glyphs. Neither needs a display, so
|
|
# the core stays headless.
|
|
pkg_check_modules(PANGOCAIRO REQUIRED IMPORTED_TARGET pangocairo)
|
|
|
|
find_package(Threads REQUIRED)
|
|
|
|
# --- core: effects and image handling, no GUI ---------------------------------
|
|
add_library(effector_core STATIC
|
|
src/core/canvas.cpp
|
|
src/core/chain.cpp
|
|
src/core/effect.cpp
|
|
src/core/image.cpp
|
|
src/core/params.cpp
|
|
src/core/project.cpp
|
|
src/core/registry.cpp
|
|
src/core/rng.cpp
|
|
src/core/style.cpp
|
|
src/effects/bitcrush.cpp
|
|
src/effects/blur.cpp
|
|
src/effects/channelsplit.cpp
|
|
src/effects/corrupt.cpp
|
|
src/effects/feedback.cpp
|
|
src/effects/grain.cpp
|
|
src/effects/monochrome.cpp
|
|
src/effects/overlay.cpp
|
|
src/effects/pixelsort.cpp
|
|
src/effects/scanlines.cpp
|
|
src/effects/shatter.cpp
|
|
src/effects/slitshift.cpp
|
|
src/effects/text.cpp
|
|
src/effects/tiles.cpp
|
|
src/effects/warp.cpp
|
|
)
|
|
target_include_directories(effector_core PUBLIC src)
|
|
# The core is GUI-free: it only needs gdk-pixbuf for decoding and encoding,
|
|
# so headless rendering works without a display.
|
|
target_link_libraries(effector_core PUBLIC PkgConfig::GDKPIXBUF PkgConfig::PANGOCAIRO Threads::Threads)
|
|
target_compile_options(effector_core PRIVATE -Wall -Wextra -Wpedantic)
|
|
|
|
# --- application --------------------------------------------------------------
|
|
add_executable(effector
|
|
src/main.cpp
|
|
src/cli/options.cpp
|
|
src/gui/app.cpp
|
|
src/gui/window.cpp
|
|
)
|
|
target_link_libraries(effector PRIVATE effector_core PkgConfig::GTKMM)
|
|
target_compile_options(effector PRIVATE -Wall -Wextra -Wpedantic)
|
|
|
|
install(TARGETS effector RUNTIME DESTINATION bin)
|
|
|
|
# --- tests --------------------------------------------------------------------
|
|
include(CTest)
|
|
if(BUILD_TESTING)
|
|
add_subdirectory(tests)
|
|
endif()
|