Take the 2-minute tour ×
Code Review Stack Exchange is a question and answer site for peer programmer code reviews. It's 100% free, no registration required.

I am trying to implement a 2D fighting game in Clojure both for fun and learning.

Since the characters in a fighter game are essentially state machines, I constructed the following code:

(defrecord Frames [frames id])

where "frames" refer to the actual datas (hitboxes texture-names and etc) and "id" will be an atom referencing the "frames" data representing the current frame the character is in.

so I will initialize a frame like this (used :a :b :c just for testing):

(def f (Frames. [:a :b :c :d :e :f :g] (atom 0)))

and will retrieve the current frame by this:

(defn get-current-frame [frames] (nth (:frames frames) @(:id frames)))

and update by:

(defn update-current-frame [frames active] (reset! (:id frames) active))

and it works fine:

(def f (Frames. [:a :b :c :d :e :f :g] (atom 0)))
(update-current-frame f 3)
(get-current-frame f) ;; => :d

Obviously it works, but I am extremely in doubt that this is a good practice.

Due to my poor knowledge with Clojure, I am here asking

  1. Is using atom referencing a vector the best way for representing simple states?
  2. Should I use this kind of data structure for implementing fighting game frames?
  3. If ignoring data structures, am I defining the functions (get-current-frame) and (get-current-frame) in an idiomatic way?
share|improve this question

1 Answer 1

No, you probably don't want to store an atom in the record. You probably want:

(defn get-current-frame [frame]
  (nth (:frames frame) (:id frame)))

(defn update-current-frame [frame active]
  (assoc frame :id active))

(def f (Frames. [:a :b :c :d :e :f :g] 0))

Then

> (get-current-frame f)
:a
> (get-current-frame (update-current-frame f 4))
:e

If you feel the need to have an atom:

brain.core> (def f (atom (Frames. [:a :b :c :d :e :f :g] 0)))
#'brain.core/f
brain.core> (get-current-frame @f)
:a
brain.core> (swap! f update-current-frame 4)
#brain.core.Frames{:frames [:a :b :c :d :e :f :g], :id 4}
brain.core> (get-current-frame @f)
:e
share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.