From 9faa77797285ccbf630d1043983333905d34df68 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Renaud=20Casenave-P=C3=A9r=C3=A9?= Date: Fri, 14 Nov 2014 20:29:39 +0900 Subject: [PATCH] Rewrite modules functions as macro This let us recompile initialize/finalize/update functions during runtime without having to register them once again. --- src/debug.lisp | 8 ++++---- src/game/game.lisp | 8 ++++---- src/jobs.lisp | 8 ++++---- src/modules.lisp | 45 +++++++++++++++++++++++++----------------- src/render/render.lisp | 8 ++++---- src/stoe.lisp | 18 ++++++++++++++--- 6 files changed, 58 insertions(+), 37 deletions(-) diff --git a/src/debug.lisp b/src/debug.lisp index c7da09f..e026c48 100644 --- a/src/debug.lisp +++ b/src/debug.lisp @@ -7,7 +7,9 @@ (defpackage stoe.debug (:nicknames :debug) (:use :cl - :utils)) + :utils) + (:import-from :modules + :defmodule)) (in-package :stoe.debug) (defvar *swank-server-port* 4006) @@ -46,6 +48,4 @@ start the swank server to accept remote connection." (setf time-counter 0.0) (setf frames-counter 0)))) -(modules:register-initialize-fun #'initialize) -(modules:register-finalize-fun #'finalize) -(modules:register-update-fun #'update) +(defmodule debug) diff --git a/src/game/game.lisp b/src/game/game.lisp index a97bbd9..2827524 100644 --- a/src/game/game.lisp +++ b/src/game/game.lisp @@ -8,7 +8,9 @@ (:use :cl) (:nicknames :game) (:export :get-world-origin - :get-current-camera)) + :get-current-camera) + (:import-from :modules + :defmodule)) (in-package :stoe.game) (defconstant +loop-step-time+ 16000.0 @@ -51,9 +53,7 @@ Advance the world by `delta-time', +loop-step-time+ at a time." (decf delta-time +loop-step-time+))) (setf *last-frame-remaining-time* delta-time)) -(modules:register-initialize-fun #'initialize) -(modules:register-finalize-fun #'finalize) -(modules:register-update-fun #'update) +(defmodule game) (defun get-world-origin () *world-origin*) (defun get-current-camera () *current-camera*) diff --git a/src/jobs.lisp b/src/jobs.lisp index 9252383..ace8f76 100644 --- a/src/jobs.lisp +++ b/src/jobs.lisp @@ -14,7 +14,9 @@ :job-result :push-job :wait-for-job - :cancel-job)) + :cancel-job) + (:import-from :modules + :defmodule)) (in-package :stoe.jobs) (defstruct job @@ -82,9 +84,7 @@ If a thread is available, assign a new job to it." (if (not (thread-alive-p (thread-thread thread))) (finalize-thread thread)))))) -(modules:register-initialize-fun #'initialize) -(modules:register-finalize-fun #'finalize) -(modules:register-update-fun #'update) +(defmodule jobs) (defun push-job (fun args) "Create a new job using `fun' and `data' and push it into the job-list." diff --git a/src/modules.lisp b/src/modules.lisp index 4dde004..67d732d 100644 --- a/src/modules.lisp +++ b/src/modules.lisp @@ -8,8 +8,10 @@ (:nicknames :modules) (:use :cl :utils) - (:export :register-initialize-fun :register-finalize-fun :register-update-fun - :initialize :finalize :update)) + (:export :initialize :finalize :update + :defmodule) + (:import-from :alexandria + :once-only)) (in-package :stoe.modules) (defparameter *initialize-hook* nil @@ -25,25 +27,32 @@ the program argv.") Functions attached to this hook should expect an argument containing the time since last frame.") -(defun initialize (&optional argv) +(defmacro initialize (&optional argv) "Perform the engine and subsystems initialization process." - (format t "Initialize...~%") - (run-hook *initialize-hook* argv)) + `(progn + (format t "Initialize...~%") + ,@(loop for fun in *initialize-hook* + collect (list fun argv)))) -(defun finalize () +(defmacro finalize () "Perform the engine and subsystems finalization process." - (format t "Finalize...~%") - (run-hook *finalize-hook*)) + `(progn + (format t "Finalize...~%") + ,@(loop for fun in *finalize-hook* + collect (list fun)))) -(defun update (delta-time) +(defmacro update (delta-time) "Update the modules each loop." - (run-hook *update-hook* delta-time)) + `(progn + ,@(loop for fun in *update-hook* + collect (list fun delta-time)))) -(defun register-initialize-fun (fun) - (add-hook *initialize-hook* fun 'append)) - -(defun register-finalize-fun (fun) - (add-hook *finalize-hook* fun)) - -(defun register-update-fun (fun) - (add-hook *update-hook* fun 'append)) +(defmacro defmodule (module) + "Register a new module. +The module is expected to have at least `initialize', `update', and `finalize' functions. +`initialize' accepts an optional `argv' argument, +`update' accepts a delta-time argument." + `(progn + (setf *initialize-hook* (append *initialize-hook* (list (intern "INITIALIZE" ',module)))) + (push (intern "FINALIZE" ',module) *finalize-hook*) + (setf *update-hook* (append *update-hook* (list (intern "UPDATE" ',module)))))) diff --git a/src/render/render.lisp b/src/render/render.lisp index 47f69fe..7ce8b6e 100644 --- a/src/render/render.lisp +++ b/src/render/render.lisp @@ -8,7 +8,9 @@ (:nicknames :render) (:use :cl :utils) - (:export :poll-events)) + (:export :poll-events) + (:import-from :modules + :defmodule)) (in-package :stoe.render) (defvar *window* nil) @@ -60,9 +62,7 @@ Render a frame and swap buffers." (render-scene (game:get-world-origin)) (glop:swap-buffers *window*)) -(modules:register-initialize-fun #'initialize) -(modules:register-finalize-fun #'finalize) -(modules:register-update-fun #'update) +(defmodule render) (defun poll-events () "Poll events from the window manager. diff --git a/src/stoe.lisp b/src/stoe.lisp index 7007b2a..c88d659 100644 --- a/src/stoe.lisp +++ b/src/stoe.lisp @@ -22,7 +22,7 @@ continue unless `unprotected' is t." (update-current-time) (update-clock clock (get-delta-time)) (render:poll-events) - (modules:update (clock-delta clock)))))) + (update (clock-delta clock)))))) (defun quit () "Quit the main loop." @@ -55,11 +55,23 @@ continue unless `unprotected' is t." (go:attach (go:make-object :mesh (with-input-from-string (s f) (mesh:make-mesh (read s)))) (game:get-world-origin)))) +(defun initialize (&optional argv) + "Initialize all the modules passing the optional argv" + (modules:initialize argv)) + +(defun finalize () + "Finalize all the modules" + (modules:finalize)) + +(defun update (delta-time) + "Update all the modules passing the delta time since the last frame" + (modules:update delta-time)) + (defun main (&optional argv) "Run the program." - (modules:initialize argv) + (initialize argv) (unwind-protect (progn (game-start) (main-loop)) - (modules:finalize))) + (finalize)))