Advertisement
loloof64

Morpion clojure graphic

Aug 27th, 2013
411
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. (ns morpion.graphic
  2.     (:import (javax.swing JPanel JFrame JOptionPane)
  3.                      (java.awt.event MouseListener)
  4.                      (java.awt Color BasicStroke Dimension)
  5.     )
  6.   (:gen-class))
  7.  
  8. (def squares-size 90)
  9. (def board-lines-size 10)
  10. (def cross-lines-width 7)
  11. (def circle-lines-width 5)
  12. (def circle-size 70)
  13. (def circle-color Color/RED)
  14. (def cross-color Color/BLUE)
  15. (def board-lines-color Color/GREEN)
  16. (def board-background-color Color/LIGHT_GRAY)
  17.  
  18. (declare make-board-panel)
  19.  
  20. (defn panel-callback
  21.     "The callback function for the JPanel"
  22.     [frame board was-cell-played?]
  23.     (JOptionPane/showMessageDialog nil "Ok!")
  24. )
  25.  
  26. (defn make-frame
  27.     "Builds the application JFrame."
  28.     []
  29.     (let [frame (JFrame.)]
  30.         (doto frame
  31.             (.setTitle "Morpion game")
  32.             (.setDefaultCloseOperation JFrame/EXIT_ON_CLOSE)
  33.             (.add (make-board-panel ('morpion.core/new-board) :circle (partial panel-callback frame)) )
  34.             (.pack)
  35.         )
  36.         frame
  37.     )
  38. )
  39.  
  40. (defn square-center
  41.     "Gives the square center coordinate matching the given coord (can be either x
  42.  or y integer value))."
  43.     [coord-value]
  44.     {:pre [(>= coord-value 0)]}
  45.     (+
  46.          (* coord-value (+ board-lines-size squares-size))
  47.          (/ squares-size 2)
  48.     )
  49. )
  50.  
  51. (defn paint-elem
  52.     "Paints the given element, at the given coords
  53.     (an hashmap with :x and :y integer values
  54.  and in the given java.awt.Graphics."
  55.     [value coords g]
  56.     {:pre ['morpion.core/valid-coords? coords]}
  57.     (let [square-center-x (square-center (:x coords))
  58.                 square-center-y (square-center (:y coords))
  59.                 half-squares-size (/ squares-size 2)
  60.                 half-circle-size (/ circle-size 2)
  61.                 cross-lines-length (int (* (Math/sqrt 2) squares-size))
  62.                 old-stroke (.getStroke g)] 
  63.         (cond
  64.             (= :cross value)
  65.                 (do
  66.                     (.setColor g cross-color)
  67.                     (.translate g square-center-x square-center-y)
  68.                     (.rotate g 0.79)
  69.                     (.setStroke g (BasicStroke. cross-lines-width BasicStroke/CAP_ROUND BasicStroke/JOIN_ROUND))
  70.                     (.drawLine g (* half-squares-size -1) 0 half-squares-size 0)
  71.                     (.drawLine g 0 (* half-squares-size -1) 0 half-squares-size )
  72.                     (.setStroke g old-stroke)                  
  73.                     (.rotate g -0.79)
  74.                     (.translate g 0 0)         
  75.                 )
  76.             (= :circle value)
  77.                 (do
  78.                     (.setColor g circle-color)
  79.                     (.setStroke g (BasicStroke. circle-lines-width BasicStroke/CAP_ROUND BasicStroke/JOIN_ROUND))
  80.                     (.drawOval g (- square-center-x half-circle-size) (- square-center-y half-circle-size) circle-size circle-size)
  81.                     (.setStroke g old-stroke)
  82.                 )
  83.         )
  84.     )
  85. )
  86.  
  87.  
  88. (defn paint-board-lines
  89.     "Paints the board lines in the given java.awt.Graphics."     
  90.     [g]
  91.     (do
  92.         (.setColor g board-lines-color)
  93.         (dotimes [i 2]
  94.             (.fillRect (+ squares-size (* i (+ board-lines-size squares-size)))
  95.                                  0
  96.                                  (+ squares-size (* i (+ board-lines-size squares-size)))
  97.                                  (+ squares-size (* 3 (+ board-lines-size squares-size)))
  98.             )
  99.             (.fillRect 0
  100.                                  (+ squares-size (* i (+ board-lines-size squares-size)))
  101.                                  (+ squares-size (* 3 (+ board-lines-size squares-size)))
  102.                                  (+ squares-size (* i (+ board-lines-size squares-size)))
  103.             )
  104.         )
  105.     )
  106. )
  107.  
  108. (defn paint-board-elements
  109.     "Paints the given board elements in the given java.awt.Graphics."
  110.     [board g]
  111.     {:pre ('morpion.core/is-board? board)}
  112.     (dotimes [line 3]
  113.         (dotimes [col 3]
  114.             (let [value ((board line) col)]
  115.                 (paint-elem value #{:x col :y line})
  116.             )
  117.         )
  118.     )
  119. )
  120.  
  121. (defn abs-coord-in-cell?
  122.     "Says whether an absolute coordinate relative to the panel is
  123.     in a cell."
  124.     [coord]
  125.     (< squares-size (rem coord (+ squares-size board-lines-size)))
  126. )
  127.  
  128. (defn abs-coord-to-rel
  129.     "Gets a cell coordinate from a panel coordinate :
  130.     converts the x/y value of point in the panel to a value
  131.     which can be 0,1,2 ."
  132.     [coord] {:pre (abs-coord-in-cell? coord)}
  133.     (int (/ coord (+ squares-size board-lines-size)))
  134. )
  135.  
  136. (defn make-board-panel
  137.     "Builds the board JPanel, whose state is given by board argument,
  138.     and turn-piece argument (must be either :circle or :cross, I mean the next
  139.     value to set in the board).
  140.  callback-fn should be a function that takes a board (vector of 3 vectors of 3 values) as
  141.  first argument, and a was-cell-played? (as a boolean). Board will be the updated board
  142.  and was-cell-played? says whether the cell had already a :cross or :circle."
  143.     [board turn-piece callback-fn]
  144.     {:pre ['morpion.core/is-board? board, 'morpion.core/is-a-player-piece? turn-piece]}
  145.     (proxy [JPanel MouseListener] []
  146.         (paintComponent [g]
  147.             (proxy-super paintComponent g)
  148.             (paint-board-lines g)
  149.             (paint-board-elements board g)
  150.         )
  151.         (mouseClicked [e]
  152.             (if (and (abs-coord-in-cell? (.getX e)) (abs-coord-in-cell? (.getY e)) )
  153.                 (let [cell-x (abs-coord-to-rel (.getX e))
  154.                             cell-y (abs-coord-to-rel (.getY e))
  155.                             cell-to-play #{:x cell-x, :y cell-y}
  156.                             was-cell-played? ('morpion.core/cell-played? cell-to-play)]
  157.                     (callback-fn ('morpion.core/play-board board cell-to-play turn-piece) was-cell-played?)
  158.                 )
  159.             )
  160.         )
  161.         (mouseEntered [e])
  162.         (mouseExited [e])
  163.         (mousePressed [e])
  164.         (mouseReleased [e])
  165.         (getPreferredSize []
  166.             (let [panel-dim (+ (* squares-size 3) (* board-lines-size 2))]
  167.                 (Dimension. panel-dim panel-dim)
  168.             )
  169.         )
  170.     )
  171. )
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement