Taming ZoG (Part 1: Wolves and Kid)

  • Tutorial
Wolves and KidIn a previous article, I talked about a unique, in my opinion, Zillions of Games project . As I promised, I am starting a short series of training articles on describing the capabilities of a declarative language designed to develop new (and describe existing) games within the framework of this project.

In order not to clutter up the presentation with unnecessary (at this stage) details, I chose a very simple game for implementation. I played it in my childhood. It is called Wolves and Kid. The rules are as follows: Wolves (black pieces) - go one cell diagonally, only forward. The kid (white figure) - also walks one cell diagonally, but in any direction. White's task is to go to any of the four squares of his color of the last horizontal. Black's task is to deprive White of the opportunity to move.

Since Black wins on a standard 8x8 chessboard, we use a 9x9 square board for the game. This game is very simple (and children like it). With the right game, White always wins.

The rule description language (ZRF) is very similar to LISP. As in LISP, it is very important to monitor the balance of opening and closing brackets (otherwise, the game just won’t load). As in LISP, comments begin with a semicolon and continue to the end of the line.

; *****************************************************************
; *** Волки и Козленок
; *****************************************************************
(version "2.0")

Here, in the commentary, we briefly describe the game and indicate the version of Zillions of Games on which it should work. On a younger version of the "engine" the game will not start.

In ZRF, macros are heavily used. They are quite simple, but can use parameters. The following entry is a macro that describes the only possible move in our game - one cell in the indicated direction:

(define checker-shift ($1 (verify empty?) add))

When used in a write code:

(checker-shift ???)

The macro is expanded as follows:

(??? (verify empty?) add)

The meaning of the passed parameter and this entire record I will explain below. For now, it’s important for us to understand that macros save us from a lot of writing and the possibility of errors in the description associated with it.

The following describes the board. Its description is also usually taken out in a macro:

(define board-defs
  (image "images\gluk\Board.bmp")
     (start-rectangle 2 2 48 48)
         ("a/b/c/d/e/f/g/h/i" (48 0)) ; files
         ("9/8/7/6/5/4/3/2/1" (0 48)) ; ranks
     (directions (nw -1 -1) (ne 1 -1) (se 1 1) (sw -1 1))
  (symmetry Black (ne sw) (sw ne) (nw se) (se nw))
  (zone (name goals) (players White) (positions b9 d9 f9 h9) )

The meaning of the description image is understandable - this is the name of the picture file loaded to display the board. The following is a description of a square board (grid). It should be noted that the capabilities of ZRF are not limited to the description of rectangular boards. Using this language, you can describe triangular and hexagonal boards, you can describe multidimensional boards, up to 5 dimensions, you can "glue" the edges of the board, determining its topology, etc. We will not dwell on this now. Details of such descriptions can be found in the chm-file that describes the ZRF language (supplied with the game), as well as in a huge number of already implemented games on various boards.

Three key phrases of the grid description are important for our game: start-rectangle describes how the board “overlays” the loaded picture. The phrase dimensions - describes the dimensions (we have two of them). The lines at the beginning of the description of each dimension are important - they describe the numbering order of the cells (thus defining the coordinate system). The following parameter determines how the “ruler” of measurement is superimposed on the board. It should be said that when using a board image developed independently, it may be difficult to select these numerical values, as well as the values ​​specified in the start-rectangle. It may take many attempts to ensure that the images of the figures fall into the right places on the image of the board.

The following, very important phrase (directions) defines the directions in which the figures can move. We define four directions - northwest (nw), northeast (ne), southwest (sw) and southeast (se). With the phrase symmetry, we define the rules by which these directions are converted for the black player.

The last line (zone) - defines the set of cells, which we will use further, when determining the conditions for the victory of the Whites.

(define game-defs
      (White (WC e2) )
      (Black (BC b9 d9 f9 h9) )
   (win-condition (White) (absolute-config WC (goals)))
   (loss-condition (White Black) stalemated)

In this macro, we define the conditions of the game. The phrase board defines the board previously defined by us (the board-defs macro expands). In the board-setup, the initial positions of the players are determined, after which, the win-condition and loss-condition phrases determine the victory and defeat conditions for the players. By the condition of victory for the Whites, we determine the passage to the zone previously determined by us, and the condition of defeat, for both sides, is the inability to make the next move.

It remains to determine the game:

   (title "Волки и Козленок")
   (description "Провести белую фишку на последнюю горизонталь")
   (players White Black)
   (turn-order White Black)
      (name WC)
      (image White "images\gluk\W.bmp")
      (description "Козленок")
      (help "Ходит на 1 клетку по диагонали вперед и назад")
         (checker-shift ne)
         (checker-shift nw)
         (checker-shift se)
         (checker-shift sw)
      (name BC)
      (image Black "images\gluk\B.bmp")
      (description "Волк")
      (help "Ходит на 1 клетку по диагонали только вперед")
         (checker-shift ne)
         (checker-shift nw)

Most of the definitions here are intuitive. It is worth stopping only a few points. The phrase players describes those same White and Black players that we have already used. There can be more than two players, and one player can be defined in puzzles (it is even possible to identify a player making random moves, but this is a topic for another discussion). The phrase turn-order determines the order of the turn for the players (it may also differ from the simple alternation of the move of two players).

Further, after the description of the game settings (game-defs), the description of the figures used in the game (piece) follows. Most of the descriptions in them are also understandable. The moves section lists all the moves possible for a piece. This is where we use the checker-shift macro that we talked about at the very beginning. As it is easy to see, as a parameter, the possible direction of movement of the figure is transferred to it. As a result of expanding the macro, we get something like the following:

( ne
  (verify empty?)

We take three steps - we move in the indicated direction, check if the cell is empty and put the piece (there is a difficult moment to understand. For myself, I believe that at the beginning of the move the piece is removed from the board, and at the end of the move it returns to the board). In more detail, I plan to tell about the possibilities of describing the rules of moves in the following articles, using more complex games as an example.

The new game is ready. Those who wish can download it from the repository on GitHub .

Important remark
Note: in order to run this code, you will need to somehow unlock the core of Zillions of Games (for example, buy a serial number)

Also popular now: