aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore2
-rw-r--r--.gitmodules5
-rw-r--r--main/CMakeLists.txt1
-rw-r--r--readme.md20
-rw-r--r--shared/FSM.cpp3
-rw-r--r--shared/FSM.h50
-rw-r--r--shared/FSM.hpp68
-rw-r--r--shared/IBehaviouralState.hpp25
-rw-r--r--test/.gitignore1
-rw-r--r--test/CMakeLists.txt23
-rw-r--r--test/ExampleTest.cpp7
m---------test/lib/googletest0
12 files changed, 204 insertions, 1 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..0902ca8
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,2 @@
+build
+.vscode/** \ No newline at end of file
diff --git a/.gitmodules b/.gitmodules
index 3711bef..c951407 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -3,3 +3,8 @@
url = https://github.com/raspberrypi/pico-sdk
branch = 1.5.1
shallow = true
+[submodule "test/lib/googletest"]
+ path = test/lib/googletest
+ url = https://github.com/google/googletest
+ branch = v1.14.0
+ shallow = true
diff --git a/main/CMakeLists.txt b/main/CMakeLists.txt
index 59d1156..e24d9a5 100644
--- a/main/CMakeLists.txt
+++ b/main/CMakeLists.txt
@@ -20,4 +20,3 @@ pico_enable_stdio_usb(main 1)
pico_add_extra_outputs(main)
target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})
target_link_libraries(main pico_cyw43_arch_lwip_threadsafe_background pico_stdlib)
-
diff --git a/readme.md b/readme.md
index e69de29..01fd063 100644
--- a/readme.md
+++ b/readme.md
@@ -0,0 +1,20 @@
+# puzzle box
+
+Avans University of Applied Sciences project puzzle box.
+
+## Tests
+
+```
+mkdir -p test/build
+cd test/build
+cmake ..
+make
+make test
+```
+
+## ESP
+1. Install ESP-IDF extension in vscode
+2. Install using 'express' option
+3. Install ESP-IDF v5.2.1 (release version)
+4. For windows: https://docs.espressif.com/projects/esp-idf/en/stable/esp32/get-started/windows-setup.html#get-started-windows-first-steps
+5. For Linux: https://docs.espressif.com/projects/esp-idf/en/stable/esp32/get-started/linux-macos-setup.html#get-started-linux-macos-first-steps
diff --git a/shared/FSM.cpp b/shared/FSM.cpp
new file mode 100644
index 0000000..fad7fb3
--- /dev/null
+++ b/shared/FSM.cpp
@@ -0,0 +1,3 @@
+#include "FSM.h"
+
+#include "IBehaviouralState.hpp" \ No newline at end of file
diff --git a/shared/FSM.h b/shared/FSM.h
new file mode 100644
index 0000000..792a44f
--- /dev/null
+++ b/shared/FSM.h
@@ -0,0 +1,50 @@
+#ifndef _FSM_H_
+#define _FSM_H_
+
+#include <map>
+#include <memory>
+
+#include "IBehaviouralState.hpp"
+
+/// <summary>
+///
+/// </summary>
+/// <typeparam name="TState">IBehaviouralState is the only accepted
+/// class.</typeparam>
+template <class TState> class FSM {
+public:
+ template <class... TPState> FSM(TPState &...args) {
+ int i = 0;
+
+ ((void)_states.emplace(i++, args), ...);
+ }
+
+ /// <summary>
+ /// Implement with FSM::act()
+ /// </summary>
+ void act();
+
+ /// <summary>
+ /// Used to check current state.
+ /// </summary>
+ /// <returns>Current state.</returns>
+ std::shared_ptr<TState> &get_state() { return _currentState; }
+
+ /// <summary>
+ /// Used to get all states.
+ /// </summary>
+ /// <returns>Current states.</returns>
+ std::map<int, std::shared_ptr<TState>> get_states();
+
+ /// <summary>
+ /// Sets current state, calls appropiate functions.
+ /// </summary>
+ /// <param name="">State to transition into.</param>
+ void set_state(std::shared_ptr<TState>);
+
+private:
+ std::map<int, std::shared_ptr<TState>> _states;
+ std::shared_ptr<TState> _currentState;
+};
+
+#endif // _FSM_H_ \ No newline at end of file
diff --git a/shared/FSM.hpp b/shared/FSM.hpp
new file mode 100644
index 0000000..c86ed80
--- /dev/null
+++ b/shared/FSM.hpp
@@ -0,0 +1,68 @@
+#ifndef _FSM_HPP_
+#define _FSM_HPP_
+
+#include "FSM.h"
+
+#include <iostream>
+
+/// <summary>
+/// This is a generic update method, unknown classes are not supported.
+/// </summary>
+/// <typeparam name="TState">IBehaviouralState is the only accepted
+/// class.</typeparam>
+template <class TState> void FSM<TState>::act() {
+ // No implementation for unknown class.
+ std::cout << "No implementation for unknown class" << std::endl;
+}
+//
+///// <summary>
+///// Calls the IBehaviouralState act method.
+///// </summary>
+///// <typeparam name="TState">IBehaviouralState is the only accepted
+/// class.</typeparam>
+template <> inline void FSM<IBehaviouralState>::act() { _currentState->act(); }
+
+/// <summary>
+/// This is a generic return of the type.
+/// </summary>
+/// <typeparam name="TState">Any class type works with this return.</typeparam>
+/// <returns>The current IBehaviouralState map.</returns>
+template <class TState>
+std::map<int, std::shared_ptr<TState>> FSM<TState>::get_states() {
+ return _states;
+}
+
+///// <summary>
+///// State transitioning from current state to newState.
+///// Calls Exit on the current state and Enter on the new state.
+///// </summary>
+///// <typeparam name="TState">IBehaviouralState is the only accepted
+/// class.</typeparam>
+///// <param name="newState">New state to transition into.</param>
+template <>
+inline void
+FSM<IBehaviouralState>::set_state(std::shared_ptr<IBehaviouralState> newState) {
+ // We can guarantee all statemachines are based on IBehaviouralState
+ if (_currentState != nullptr)
+ _currentState->exit();
+
+ _currentState = nullptr;
+ _currentState = newState;
+ _currentState->enter();
+}
+
+/// <summary>
+/// State transitioning from current state to newState.
+/// Calls Exit on the current state and Enter on the new state.
+/// </summary>
+/// <typeparam name="TState">IBehaviouralState is the only accepted
+/// class.</typeparam> <param name="newState">New state to transition
+/// into.</param>
+template <class TState>
+void FSM<TState>::set_state(std::shared_ptr<TState> newState) {
+ // We can guarantee all statemachines are based on IBehaviouralState
+ // No implementation for an unknown state change class.
+ std::cout << "No implementation for unknown state change class" << std::endl;
+}
+
+#endif // _FSM_HPP_ \ No newline at end of file
diff --git a/shared/IBehaviouralState.hpp b/shared/IBehaviouralState.hpp
new file mode 100644
index 0000000..c41fef3
--- /dev/null
+++ b/shared/IBehaviouralState.hpp
@@ -0,0 +1,25 @@
+#ifndef _FSM_IBEHAVIOURALSTATE_HPP_
+#define _FSM_IBEHAVIOURALSTATE_HPP_
+
+/// <summary>
+/// Sub class used to define methods implemented by behavioural specific states.
+/// </summary>
+class IBehaviouralState {
+public:
+ /// <summary>
+ /// Enters the current state. Used for setup.
+ /// </summary>
+ virtual void enter() = 0;
+
+ /// <summary>
+ /// Updates the current state, used for physics, etc.
+ /// </summary>
+ virtual void act() = 0;
+
+ /// <summary>
+ /// Exits the state, used for cleanup.
+ /// </summary>
+ virtual void exit() = 0;
+};
+
+#endif // _FSM_IBEHAVIOURALSTATE_HPP_ \ No newline at end of file
diff --git a/test/.gitignore b/test/.gitignore
new file mode 100644
index 0000000..c795b05
--- /dev/null
+++ b/test/.gitignore
@@ -0,0 +1 @@
+build \ No newline at end of file
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
new file mode 100644
index 0000000..a0bd099
--- /dev/null
+++ b/test/CMakeLists.txt
@@ -0,0 +1,23 @@
+cmake_minimum_required(VERSION 3.29)
+
+project(puzzlebox_test C CXX ASM)
+
+set(CMAKE_C_STANDARD 11)
+set(CMAKE_CXX_STANDARD 17)
+set(CMAKE_EXPORT_COMPILE_COMMANDS 1)
+
+add_executable(tests
+ ExampleTest.cpp
+)
+
+enable_testing()
+
+add_subdirectory(lib/googletest)
+
+target_include_directories(tests PRIVATE ${CMAKE_CURRENT_LIST_DIR})
+target_link_libraries(tests PRIVATE gtest_main)
+
+add_test(
+ NAME tests
+ COMMAND tests
+) \ No newline at end of file
diff --git a/test/ExampleTest.cpp b/test/ExampleTest.cpp
new file mode 100644
index 0000000..a3909f5
--- /dev/null
+++ b/test/ExampleTest.cpp
@@ -0,0 +1,7 @@
+#include <gtest/gtest.h>
+
+class ExampleTest : public testing::Test {
+protected:
+};
+
+TEST_F(ExampleTest, Test) { EXPECT_EQ(5, 5); } \ No newline at end of file
diff --git a/test/lib/googletest b/test/lib/googletest
new file mode 160000
+Subproject 5197b1a8e6a1ef9f214f4aa537b0be17cbf9194