commit 0d42589648765d7edbdacc98d2d4f58d297a4264 Author: Alexander Kobjolke Date: Tue Apr 18 13:10:45 2023 +0200 Initial import diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..5dae8de --- /dev/null +++ b/.envrc @@ -0,0 +1,4 @@ +watch_file devenv.nix +watch_file devenv.yaml +watch_file devenv.lock +eval "$(devenv print-dev-env)" \ No newline at end of file diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..715bef4 --- /dev/null +++ b/.gitignore @@ -0,0 +1,5 @@ + +# Devenv +.devenv* +devenv.local.nix + diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..b60321a --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,20 @@ +cmake_minimum_required (VERSION 3.15) + +project (elm CXX) + +set (CMAKE_EXPORT_COMPILE_COMMANDS ON) + +if (CMAKE_CXX_COMPILER_ID MATCHES ".*Clang") + add_compile_options(-fcolor-diagnostics) +elseif(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + add_compile_options(-fdiagnostics-color=always) +else() + message(STATUS "No colored compiler diagnostic set for '${CMAKE_CXX_COMPILER_ID}' compiler.") +endif() + +# Link this 'library' to set the c++ standard / compile-time options requested +add_library(project_options INTERFACE) +target_compile_features(project_options INTERFACE cxx_std_17) + +add_executable (elmarch main.cpp) +target_link_libraries (elmarch PRIVATE project_options) diff --git a/devenv.lock b/devenv.lock new file mode 100644 index 0000000..c645797 --- /dev/null +++ b/devenv.lock @@ -0,0 +1,138 @@ +{ + "nodes": { + "devenv": { + "locked": { + "dir": "src/modules", + "lastModified": 1677763711, + "narHash": "sha256-Zki/zzU3890JGZvDcAAv83soyGqDnP/15KZrAsJt7rI=", + "owner": "cachix", + "repo": "devenv", + "rev": "8489b4d98c0144a4d58a51ab5a857fede4c45f42", + "type": "github" + }, + "original": { + "dir": "src/modules", + "owner": "cachix", + "repo": "devenv", + "type": "github" + } + }, + "flake-compat": { + "flake": false, + "locked": { + "lastModified": 1673956053, + "narHash": "sha256-4gtG9iQuiKITOjNQQeQIpoIB6b16fm+504Ch3sNKLd8=", + "owner": "edolstra", + "repo": "flake-compat", + "rev": "35bb57c0c8d8b62bbfd284272c928ceb64ddbde9", + "type": "github" + }, + "original": { + "owner": "edolstra", + "repo": "flake-compat", + "type": "github" + } + }, + "flake-utils": { + "locked": { + "lastModified": 1667395993, + "narHash": "sha256-nuEHfE/LcWyuSWnS8t12N1wc105Qtau+/OdUAjtQ0rA=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "5aed5285a952e0b949eb3ba02c12fa4fcfef535f", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "gitignore": { + "inputs": { + "nixpkgs": [ + "pre-commit-hooks", + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1660459072, + "narHash": "sha256-8DFJjXG8zqoONA1vXtgeKXy68KdJL5UaXR8NtVMUbx8=", + "owner": "hercules-ci", + "repo": "gitignore.nix", + "rev": "a20de23b925fd8264fd7fad6454652e142fd7f73", + "type": "github" + }, + "original": { + "owner": "hercules-ci", + "repo": "gitignore.nix", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1677655566, + "narHash": "sha256-I8G8Lmpp3YduYl4+pkiIJFGT1WKw+8ZMH2QwANkTu2U=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "ae8bdd2de4c23b239b5a771501641d2ef5e027d0", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs-stable": { + "locked": { + "lastModified": 1673800717, + "narHash": "sha256-SFHraUqLSu5cC6IxTprex/nTsI81ZQAtDvlBvGDWfnA=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "2f9fd351ec37f5d479556cd48be4ca340da59b8f", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-22.11", + "repo": "nixpkgs", + "type": "github" + } + }, + "pre-commit-hooks": { + "inputs": { + "flake-compat": "flake-compat", + "flake-utils": "flake-utils", + "gitignore": "gitignore", + "nixpkgs": [ + "nixpkgs" + ], + "nixpkgs-stable": "nixpkgs-stable" + }, + "locked": { + "lastModified": 1677722096, + "narHash": "sha256-7mjVMvCs9InnrRybBfr5ohqcOz+pyEX8m22C1XsDilg=", + "owner": "cachix", + "repo": "pre-commit-hooks.nix", + "rev": "61a3511668891c68ebd19d40122150b98dc2fe3b", + "type": "github" + }, + "original": { + "owner": "cachix", + "repo": "pre-commit-hooks.nix", + "type": "github" + } + }, + "root": { + "inputs": { + "devenv": "devenv", + "nixpkgs": "nixpkgs", + "pre-commit-hooks": "pre-commit-hooks" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/devenv.nix b/devenv.nix new file mode 100644 index 0000000..613a63d --- /dev/null +++ b/devenv.nix @@ -0,0 +1,14 @@ +{ pkgs, ... }: + +{ + packages = [ pkgs.git ]; #pkgs.clang pkgs.clang-tidy ]; + + # https://devenv.sh/languages/ + languages.cplusplus.enable = true; + + # https://devenv.sh/pre-commit-hooks/ + # pre-commit.hooks.shellcheck.enable = true; + + # https://devenv.sh/processes/ + # processes.ping.exec = "ping example.com"; +} diff --git a/devenv.yaml b/devenv.yaml new file mode 100644 index 0000000..8de0039 --- /dev/null +++ b/devenv.yaml @@ -0,0 +1,4 @@ +inputs: + nixpkgs: + url: github:NixOS/nixpkgs/nixpkgs-unstable +# can't point to the local modules here as it's used as a template \ No newline at end of file diff --git a/main.cpp b/main.cpp new file mode 100644 index 0000000..1579ce9 --- /dev/null +++ b/main.cpp @@ -0,0 +1,114 @@ +#include +#include +#include +#include +#include +#include +#include +#include + +using namespace std::chrono_literals; + +template struct ConsoleIO { + static auto ReadlineS(std::istream& is, std::function f) { + return [=,&is] { + std::string line; + std::getline(is, line); + return f(line); + }; + } + + static std::function + Readline(std::function f) { + return ReadlineS (std::ref(std::cin), f); + } + + static std::function + Prompt(std::string prompt, std::function f) { + return [=] { + std::cout << prompt << std::flush; + return Readline (f)(); + }; + } +}; + +template struct AppT { + using Model = ModelT; + using Message = MessageT; + using Command = std::function; + using InitResult = std::tuple>; + using UpdateResult = InitResult; + using ViewResult = std::string; + using ReadLine = std::function; + using Console = ConsoleIO; + + using Init = std::function; + using Update = std::function; + using View = std::function; + using Done = std::function; + + struct Config { + Init init; + Update update; + View view; + Done done; + }; + + int run (const Config & cfg) { + auto const& [init, update, view, done] = cfg; + auto [state, cmds] = init(); + + while (! done (state)) { + std::cout << view(state) << "\n"; + + if (!cmds.empty()) { + auto [newstate, newcmds] = update (state, cmds.front()()); + cmds.erase (cmds.begin()); + cmds.insert (cmds.end(), std::begin(newcmds), std::end (newcmds)); + + state = newstate; + } + std::this_thread::sleep_for (100ms); + } + + std::cout << "app finished with " << cmds.size() << " pending commands and final state: \n" << view(state) << '\n'; + + return 0; + } +}; + +// user defined + +using Model = int; + +struct SetState { + Model s; +}; + +using Message = std::variant; + +auto strToState (const std::string& s) -> Message { + std::stringstream sstr(s); + int r; + sstr >> r; + return SetState { r }; + } + +int main() { + using App = AppT; + App app; + return app.run(App::Config{ + []() -> App::InitResult { + return {23, {App::Console::Prompt("> ", strToState)}}; + }, // init + [](const App::Model &state, + const App::Message &msg) -> App::UpdateResult { + return {std::get(msg).s, + {App::Console::Prompt("> ", strToState)}}; + }, // update + [](const App::Model &state) -> App::ViewResult { + return "Model " + std::to_string(state); + }, // view + [](const App::Model &state) -> bool { return state == 42; } // done + }); +}