This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2021-08-05
Channels
- # announcements (1)
- # babashka (5)
- # beginners (151)
- # calva (43)
- # clj-kondo (23)
- # cljdoc (1)
- # cljs-dev (6)
- # cljsrn (10)
- # clojure (60)
- # clojure-australia (1)
- # clojure-europe (26)
- # clojure-gamedev (14)
- # clojure-nl (1)
- # clojure-spec (10)
- # clojure-uk (80)
- # clojurescript (66)
- # clojureverse-ops (4)
- # community-development (7)
- # conjure (8)
- # datomic (15)
- # deps-new (1)
- # docker (27)
- # emacs (2)
- # fulcro (13)
- # honeysql (13)
- # java (5)
- # jobs-discuss (43)
- # lsp (121)
- # luminus (13)
- # malli (1)
- # off-topic (73)
- # pathom (12)
- # polylith (29)
- # practicalli (4)
- # re-frame (35)
- # reagent (44)
- # remote-jobs (5)
- # rewrite-clj (2)
- # sci (7)
- # shadow-cljs (125)
- # sql (4)
- # tools-deps (9)
- # xtdb (5)
I’m playing with a rewrite of my stateful game to make it a purely functional one and I’m struggling with feeling like I always have to start from the outermost layer to do any changes. For example, in the stateful engine, I have a queue of “steps” that acts as a “last in first out” stack. Each step is a volatile map and has a :complete?
flag, so I can pass the the step into a given function and call (vswap! step assoc :complete? true) when it’s time to pop the step from the queue in the next iteration
However, in the pure version, I pass both the game state and the step into the function and then have to juggle the updating the step inside of the game state and return state and then outside of that function, I have to dive into the state to find the step and check if it is :complete?
. Means I’m constantly performing additional work to look up and update variables that would be a simple mutation in, say, javascript
This relates to the place of friction where in javascript I can do something like this.game = game
and then in my class I just have access to the game object and don’t have to be going from game into X into Y to perform my function.
Maybe I’m just not structuring my data correctly lol
How do y’all handle these issues?
separate but related: in javascript, i can say something like:
const step = this.game.getCurrentStep();
if (!step.continue()) {
this.game.dropCurrentStep();
}
and because step
has a reference to this.game
, i can have step
mutate this.game
while also returning a boolean saying whether it succeeded or not (for instance, if the step requires player input, return false
).what’s best practice for doing the same in clojure? do I return a tuple (`[state success?]`) or set a flag on the game state or is there some other practice I haven’t thought of
the other idea i had was to write a function called current-step-complete?
which checks to see if the step itself is marked as complete
@nbtheduke perhaps you will find some inspiration in this thread: https://clojureverse.org/t/how-are-clojurians-handling-control-flow-on-their-projects/7868
oh hell yeah, that’s great. thank you, i’ll read it over!
I'm avoiding giving more concrete advice, because I've struggled myself with different ways of modeling control flow (outside of gamedev) and while all the examples given have their pros/cons, I don't think any one has flat out won. :)
hah you’re welcome to share how you do it, i promise to not blame you if i use your method and then tear my hair out later
I've basically tried all of them XD, aside from the missionary
approach which I'm still trying to fully grok, so yeah... the more you know, the less you really know.
haha for real. i’m also struggling with the “if i want to rewrite this, i have to do it right” (which leads to not getting anything done) whereas the stateful engine already exists and works well enough that i can continue to hack on it. Joel (joelonsoftware) has talked at length about this, so i’ve resisted so far, but the statefulness of this thing is so deep there’s p much no way for me to gracefully transition to a more pure version