]> git.seodisparate.com - jumpartifact.com_demo_0/commitdiff
Create "Screen" abstraction, "test" in TestScreen
authorStephen Seo <seo.disparate@gmail.com>
Mon, 31 Jul 2023 07:27:01 +0000 (16:27 +0900)
committerStephen Seo <seo.disparate@gmail.com>
Mon, 31 Jul 2023 07:27:01 +0000 (16:27 +0900)
Makefile
src/game.cc
src/game.h
src/screen.cc [new file with mode: 0644]
src/screen.h [new file with mode: 0644]
src/screen_test.cc [new file with mode: 0644]
src/screen_test.h [new file with mode: 0644]
wasm_build/Makefile

index 41dedd7546509c7becd649d35a4cd5833075caa1..16658a1d41f5debb0a89b612fcb0ad6c50b00e9b 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -11,10 +11,14 @@ OBJDIR = objdir
 
 SOURCES = \
                src/main.cc \
-               src/game.cc
+               src/game.cc \
+               src/screen.cc \
+               src/screen_test.cc
 
 HEADERS = \
-               src/game.h
+               src/game.h \
+               src/screen.h \
+               src/screen_test.h
 
 OBJECTS = $(addprefix ${OBJDIR}/,$(subst .cc,.cc.o,${SOURCES}))
 
index c290b9daa27c5ba7c27a643d7c73329fd9b45ab2..95324d77be249ed4655d76c1bb3708d6308f8900 100644 (file)
@@ -1,31 +1,20 @@
 #include "game.h"
 
-// standard library includes
-#include <string>
-
-// third party includes
-#include <raylib.h>
+// local includes
+#include "screen_test.h"
 
 Game::Game()
-    : prev_time(std::chrono::steady_clock::now()), TEMP_cached_dt(0.0F) {}
+    : screen_stack(ScreenStack::new_instance()),
+      prev_time(std::chrono::steady_clock::now()) {
+  screen_stack->push_screen<TestScreen>();
+}
 
 void Game::update() {
   auto next_time = std::chrono::steady_clock::now();
   auto duration = std::chrono::duration_cast<std::chrono::microseconds>(
       next_time - prev_time);
   prev_time = next_time;
-  update_impl(((float)duration.count()) / 1000000);
-}
-
-void Game::draw() {
-  std::string dt_string =
-      std::string("Delta-time: ") + std::to_string(TEMP_cached_dt);
-
-  BeginDrawing();
-  ClearBackground(BLACK);
-  DrawText("Testing...", 100, 100, 30, RAYWHITE);
-  DrawText(dt_string.c_str(), 100, 140, 30, RAYWHITE);
-  EndDrawing();
+  screen_stack->update(((float)duration.count()) / 1000000);
 }
 
-void Game::update_impl(float dt) { TEMP_cached_dt = dt; }
+void Game::draw() { screen_stack->draw(); }
index 413641bf966048c3c98a3e844b61081405cba148..b3fd492dcd49c87f46a8633645f5c8a8dad2d744 100644 (file)
@@ -4,6 +4,9 @@
 // standard library includes
 #include <chrono>
 
+// local includes
+#include "screen.h"
+
 class Game {
  public:
   Game();
@@ -20,10 +23,8 @@ class Game {
   void draw();
 
  private:
-  void update_impl(float dt);
-
+  ScreenStack::Ptr screen_stack;
   std::chrono::steady_clock::time_point prev_time;
-  float TEMP_cached_dt;
 };
 
 #endif
diff --git a/src/screen.cc b/src/screen.cc
new file mode 100644 (file)
index 0000000..bd855cf
--- /dev/null
@@ -0,0 +1,34 @@
+#include "screen.h"
+
+Screen::Screen(std::weak_ptr<ScreenStack> stack) : stack(stack) {}
+
+ScreenStack::Ptr ScreenStack::new_instance() {
+  std::shared_ptr<ScreenStack> ptr =
+      std::shared_ptr<ScreenStack>(new ScreenStack{});
+  ptr->self_weak = ptr;
+  return ptr;
+}
+
+void ScreenStack::update(float dt) {
+  auto idx = stack.size();
+  while (idx > 0 && stack.at(--idx)->update(dt)) {
+  }
+}
+
+void ScreenStack::draw() {
+  auto idx = stack.size();
+  while (idx > 0 && stack.at(--idx)->draw()) {
+  }
+}
+
+void ScreenStack::push_screen(Screen::Ptr &&screen) {
+  stack.emplace_back(std::forward<Screen::Ptr>(screen));
+}
+
+void ScreenStack::pop_screen() {
+  if (!stack.empty()) {
+    stack.pop_back();
+  }
+}
+
+ScreenStack::ScreenStack() : self_weak(), stack() {}
diff --git a/src/screen.h b/src/screen.h
new file mode 100644 (file)
index 0000000..679ccd9
--- /dev/null
@@ -0,0 +1,81 @@
+#ifndef JUMPARTIFACT_DOT_COM_DEMO_0_SCREEN_H_
+#define JUMPARTIFACT_DOT_COM_DEMO_0_SCREEN_H_
+
+#include <memory>
+#include <vector>
+
+// Forward declaration.
+class ScreenStack;
+
+class Screen {
+ public:
+  using Ptr = std::unique_ptr<Screen>;
+
+  template <typename SubScreen>
+  static Ptr new_screen(std::weak_ptr<ScreenStack> stack);
+
+  virtual ~Screen() {}
+
+  // No copy.
+  Screen(const Screen&) = delete;
+  Screen& operator=(const Screen&) = delete;
+
+  // Allow move.
+  Screen(Screen&&) = default;
+  Screen& operator=(Screen&&) = default;
+
+  /// Return true if next screen should be updated.
+  virtual bool update(float dt) = 0;
+  /// Return true if next screen should be drawn.
+  virtual bool draw() = 0;
+
+ protected:
+  Screen(std::weak_ptr<ScreenStack> stack);
+
+ private:
+  std::weak_ptr<ScreenStack> stack;
+};
+
+class ScreenStack {
+ public:
+  using Ptr = std::shared_ptr<ScreenStack>;
+  using Weak = std::weak_ptr<ScreenStack>;
+
+  static Ptr new_instance();
+
+  // No copy.
+  ScreenStack(const ScreenStack&) = delete;
+  ScreenStack& operator=(const ScreenStack&) = delete;
+
+  // Allow move.
+  ScreenStack(ScreenStack&&) = default;
+  ScreenStack& operator=(ScreenStack&&) = default;
+
+  void update(float dt);
+  void draw();
+
+  void push_screen(Screen::Ptr&& screen);
+
+  template <typename SubScreen>
+  void push_screen();
+
+  void pop_screen();
+
+ private:
+  ScreenStack();
+
+  Weak self_weak;
+  std::vector<Screen::Ptr> stack;
+};
+
+template <typename SubScreen>
+Screen::Ptr Screen::new_screen(std::weak_ptr<ScreenStack> stack) {
+  return std::unique_ptr<SubScreen>(new SubScreen{stack});
+}
+
+template <typename SubScreen>
+void ScreenStack::push_screen() {
+  stack.emplace_back(Screen::new_screen<SubScreen>(self_weak));
+}
+
+#endif
diff --git a/src/screen_test.cc b/src/screen_test.cc
new file mode 100644 (file)
index 0000000..0bf5569
--- /dev/null
@@ -0,0 +1,28 @@
+#include "screen_test.h"
+
+// standard library includes
+#include <string>
+
+// third party includes
+#include <raylib.h>
+
+TestScreen::TestScreen(ScreenStack::Weak weak_ptr)
+    : Screen(weak_ptr), TEMP_cached_dt(0.0F) {}
+TestScreen::~TestScreen() {}
+
+bool TestScreen::update(float dt) {
+  TEMP_cached_dt = dt;
+  return false;
+}
+
+bool TestScreen::draw() {
+  std::string dt_string =
+      std::string("Delta-time: ") + std::to_string(TEMP_cached_dt);
+
+  BeginDrawing();
+  ClearBackground(BLACK);
+  DrawText("Testing...", 100, 100, 30, RAYWHITE);
+  DrawText(dt_string.c_str(), 100, 140, 30, RAYWHITE);
+  EndDrawing();
+  return false;
+}
diff --git a/src/screen_test.h b/src/screen_test.h
new file mode 100644 (file)
index 0000000..56469c5
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef JUMPARTIFACT_DOT_COM_DEMO_O_TEST_SCREEN_H_
+#define JUMPARTIFACT_DOT_COM_DEMO_O_TEST_SCREEN_H_
+
+#include "screen.h"
+
+class TestScreen : public Screen {
+ public:
+  TestScreen(ScreenStack::Weak weak_ptr);
+  ~TestScreen() override;
+
+  bool update(float dt) override;
+  bool draw() override;
+
+ private:
+  float TEMP_cached_dt;
+};
+
+#endif
index 482aae28a3873155cf3b3ae4a29aecf044951375..f4ffefea6bbed4466847ab06259265b0921cd7f2 100644 (file)
@@ -7,11 +7,15 @@ endif
 SOURCES = \
                ../src/main.cc \
                ../src/ems.cc \
-               ../src/game.cc
+               ../src/game.cc \
+               ../src/screen.cc \
+               ../src/screen_test.cc
 
 HEADERS = \
                ../src/ems.h \
-               ../src/game.h
+               ../src/game.h \
+               ../src/screen.h \
+               ../src/screen_test.h
 
 CXX = source ${HOME}/git/emsdk/emsdk_env.sh && em++