Advertisement
Guest User

Untitled

a guest
Mar 13th, 2019
82
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lisp 3.60 KB | None | 0 0
  1. (in-package #:snake-utils)
  2.  
  3. (defclass snake ()
  4.   ((body
  5.     :accessor snake-body ;; list of snake-parts
  6.     :initarg  :body
  7.     :initform '())
  8.    (length
  9.     :accessor snake-length
  10.     :initarg :length
  11.     :initform 0)
  12.    (head-direction ;; :up, :down, :left, :right
  13.     :accessor snake-head-direction
  14.     :initarg :head-direction
  15.     :initform :down)
  16.    (dead-p
  17.     :accessor snake-dead-p
  18.     :initform nil)
  19.    ;; can later add other fields like power-up-status
  20.    ))
  21.  
  22. (defclass snake-part ()
  23.   ((position
  24.     :accessor sp-position
  25.     :initarg  :position)
  26.    (direction
  27.     :accessor sp-direction
  28.     :initarg  :direction
  29.     :initform :down)
  30.    (previous
  31.     :accessor sp-previous
  32.     :initarg  :previous
  33.     :initform nil)))
  34.  
  35. ;;------------------------------------------------------------
  36. (defun spawn-snake (&key board-dim  (pos '(0 0)) (direction :down) (body-length 3))
  37.   "Create instance of snake on board.
  38. ARGS:
  39. `board-dim'   - a list like '(16 9)
  40. `pos'         - position of snake-head on board e.g.: '(3 5)
  41. `direction'   - :up, :down, :left, :right
  42. `body-length' - how many snake-parts the snake consists of"
  43.   (let ((x-dim (first  board-dim))
  44.         (y-dim (second board-dim))
  45.         (x-pos (first  pos))
  46.         (y-pos (second pos)))
  47.     (labels ((snake-make-body ()
  48.                "create list out of `body-length' snake-parts. Starting from the tail"
  49.                (labels ((calc-x-pos (index)
  50.                           (case direction
  51.                             (:up    x-pos)
  52.                             (:down  x-pos)
  53.                             (:left  (+ x-pos (1- (- body-length index))))
  54.                             (:right (- x-pos (1- (- body-length index))))))
  55.                         (calc-y-pos (index)
  56.                           (case direction
  57.                             (:up    (- y-pos (1- (- body-length index))))
  58.                             (:down  (+ y-pos (1- (- body-length index))))
  59.                             (:left  y-pos)
  60.                             (:right y-pos))))
  61.                  (do* ((i 0 (1+ i))
  62.                        (previous-part nil)
  63.                        (curr-part nil)
  64.                        (result '() (cons curr-part result)))
  65.                       ((= i body-length) result)
  66.                    (setf curr-part (make-instance 'snake-part
  67.                                                   :position `(,(calc-x-pos i) ,(calc-y-pos i))
  68.                                                   :previous previous-part))
  69.                    (setf previous-part curr-part))))
  70.  
  71.              (outside-board-p ()
  72.                "Checks weather the snake fits completely onto the board."
  73.                (labels ((head-not-on-board-p ()
  74.                           (or (or (> 0 x-pos) (>= x-pos x-dim))
  75.                               (or (> 0 y-pos) (>= y-pos y-dim))))
  76.                         (tail-in-wall-p ()
  77.                           (case direction
  78.                             (:up    (> 0     (- y-pos (1- body-length))))
  79.                             (:down  (< y-dim (+ y-pos (1- body-length))))
  80.                             (:left  (< x-dim (+ x-pos (1- body-length))))
  81.                             (:right (> 0     (- x-pos (1- body-length)))))))
  82.                    (or (head-not-on-board-p)
  83.                     (tail-in-wall-p)))))
  84.       ;;----------------------------------------
  85.         (unless (outside-board-p) ;; checks weather the snake can be created
  86.           (make-instance 'snake
  87.                          :body   (snake-make-body)
  88.                          :length body-length
  89.                          :head-direction direction)))))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement