Game is playable and editable
This commit is contained in:
parent
370d5ebc7e
commit
760815c865
56
edtris.txt
Normal file
56
edtris.txt
Normal file
|
@ -0,0 +1,56 @@
|
||||||
|
Welcome to Edtris, the Editable Tetris!
|
||||||
|
|
||||||
|
This game has a text editor built into it! You are looking at an editor
|
||||||
|
called "lite", which is written in Lua and has been ported to run inside
|
||||||
|
the love2d game engine.
|
||||||
|
|
||||||
|
Edtris is written in Fennel, which is a language in the Lisp family
|
||||||
|
that compiles to Lua.
|
||||||
|
|
||||||
|
To your right is a file called "state.fnl" - this contains a snapshot of
|
||||||
|
all of the information that can change while the game is running. This
|
||||||
|
includes the next piece (represented by the letters O, I, J, L, S, Z, and T),
|
||||||
|
the current piece and its position in the well, the time left before the
|
||||||
|
current piece drops down one level, and the current speed of automatic
|
||||||
|
dropping.
|
||||||
|
|
||||||
|
You can edit state.fnl and, with a simple keystroke, make your changes
|
||||||
|
live in the game! Try the following:
|
||||||
|
|
||||||
|
1. Change the line reading
|
||||||
|
:next-piece "O"
|
||||||
|
(or instead of "O", whatever letter represents the next piece)
|
||||||
|
to say
|
||||||
|
:next-piece "I"
|
||||||
|
2. Hit Ctrl-S to save the file
|
||||||
|
3. Hit Alt-R to "reload" the file. If everything is alright, you will see
|
||||||
|
a message pop up at the bottom of the screen saying "Hotswapping game.state".
|
||||||
|
If an error message pops up instead, hit Ctrl-Z repeatedly to undo all of
|
||||||
|
your changes and try again!
|
||||||
|
4. Hit F1 to go back to the game. Now your next piece will be a long "I"-beam!
|
||||||
|
|
||||||
|
At any time, you can press "E" to come back to this editor and try new things.
|
||||||
|
Feel free to experiment!
|
||||||
|
|
||||||
|
* What happens if you make the well bigger?
|
||||||
|
* What happens if you remove the walls of the well?
|
||||||
|
* Can you draw a picture in the well?
|
||||||
|
|
||||||
|
If you like, you can also run the game and the editor at the same time!
|
||||||
|
If you press Ctrl-Shift-P, type "game" and press enter, a new tab will
|
||||||
|
open with the game running inside.
|
||||||
|
|
||||||
|
If you're feeling adventurous, you can edit the source code for this game while
|
||||||
|
it's running, too! That's how I made it! Most of the interesting rules are
|
||||||
|
defined in game/rules.fnl. You can find this file in the directory tree to the left,
|
||||||
|
or press Ctrl-P, type "rules.fnl", and press enter to jump right to it.
|
||||||
|
|
||||||
|
* Can you add a new piece to the game?
|
||||||
|
* Can you make the up arrow make the piece levitate upwards, instead of rotating?
|
||||||
|
|
||||||
|
This game was made for the Glorious Trainwrecks 15th Anniversary Klik Jam!
|
||||||
|
https://www.glorioustrainwrecks.com/node/12219
|
||||||
|
|
||||||
|
Happy 15th birthday, Glorious Trainwrecks!
|
||||||
|
|
||||||
|
-- Jeremy Penner
|
|
@ -74,17 +74,16 @@
|
||||||
" #"]]})
|
" #"]]})
|
||||||
|
|
||||||
(fn Rules.choose-random-tetromino []
|
(fn Rules.choose-random-tetromino []
|
||||||
(let [possible-values (icollect [k (pairs state.tetrominoes)] k)
|
(let [possible-values (icollect [k (pairs tetrominoes)] k)
|
||||||
ivalue (love.math.random (length possible-values))]
|
ivalue (love.math.random (length possible-values))]
|
||||||
(. possible-values ivalue)))
|
(. possible-values ivalue)))
|
||||||
|
|
||||||
(fn Rules.tetromino [k irotation]
|
(fn Rules.tetromino [k irotation]
|
||||||
(let [rotations (or (. state.tetrominoes k) [])
|
(let [rotations (or (. tetrominoes k) [])
|
||||||
irotation (+ (% (- irotation 1) (length rotations)) 1)]
|
irotation (+ (% (- irotation 1) (length rotations)) 1)]
|
||||||
(. rotations irotation)))
|
(. rotations irotation)))
|
||||||
|
|
||||||
(fn Rules.reset-game []
|
(fn Rules.reset-game []
|
||||||
(set state.tetrominoes tetrominoes)
|
|
||||||
(set state.well (map.new-tilemap 12 21))
|
(set state.well (map.new-tilemap 12 21))
|
||||||
(for [y 0 19]
|
(for [y 0 19]
|
||||||
(map.set-itile-at 0 y state.well "X")
|
(map.set-itile-at 0 y state.well "X")
|
||||||
|
@ -95,6 +94,7 @@
|
||||||
(Rules.play-next-piece))
|
(Rules.play-next-piece))
|
||||||
|
|
||||||
(fn Rules.play-next-piece []
|
(fn Rules.play-next-piece []
|
||||||
|
(Rules.clear-lines)
|
||||||
(let [piece (or state.next-piece (Rules.choose-random-tetromino))
|
(let [piece (or state.next-piece (Rules.choose-random-tetromino))
|
||||||
x (math.floor (/ (- (length (. state.well 1)) 2) 2))]
|
x (math.floor (/ (- (length (. state.well 1)) 2) 2))]
|
||||||
(set state.current {: piece : x :y 0 :irotation 1})
|
(set state.current {: piece : x :y 0 :irotation 1})
|
||||||
|
@ -151,10 +151,32 @@
|
||||||
(set state.current.x x)
|
(set state.current.x x)
|
||||||
(set state.current.irotation irotation)))))))
|
(set state.current.irotation irotation)))))))
|
||||||
|
|
||||||
|
(fn Rules.clear-lines []
|
||||||
|
(let [rows (icollect [irow row (ipairs state.well)] (when (not (row:match "^X%#+X$")) row))
|
||||||
|
first-row (. state.well 1)
|
||||||
|
empty-row (.. :X (string.rep " " (- (length first-row) 2)) :X)
|
||||||
|
cleared-rows (math.max 0 (- (length state.well) (length rows)))]
|
||||||
|
(when (> cleared-rows 0)
|
||||||
|
(for [i 1 cleared-rows]
|
||||||
|
(print i cleared-rows (length state.well))
|
||||||
|
(table.insert rows 1 empty-row))
|
||||||
|
(set state.well rows))))
|
||||||
|
|
||||||
|
(fn Rules.edit-game []
|
||||||
|
(let [modes (require :editor.lovemode)
|
||||||
|
core (require :core)
|
||||||
|
filename "game/state.fnl"
|
||||||
|
f (io.open filename :w)]
|
||||||
|
(f:write (fv state))
|
||||||
|
(f:close)
|
||||||
|
(modes:cycle)
|
||||||
|
(core.root_view:open_doc (core.open_doc filename))))
|
||||||
|
|
||||||
(set Rules.commands
|
(set Rules.commands
|
||||||
{:move Rules.try-move-piece
|
{:move Rules.try-move-piece
|
||||||
:rotate Rules.rotate
|
:rotate Rules.rotate
|
||||||
:reset Rules.reset-game})
|
:reset Rules.reset-game
|
||||||
|
:edit Rules.edit-game})
|
||||||
|
|
||||||
(set Rules.keymap
|
(set Rules.keymap
|
||||||
{:left [:move -1 0]
|
{:left [:move -1 0]
|
||||||
|
@ -163,7 +185,8 @@
|
||||||
:up [:rotate 1]
|
:up [:rotate 1]
|
||||||
:z [:rotate -1]
|
:z [:rotate -1]
|
||||||
:x [:rotate 1]
|
:x [:rotate 1]
|
||||||
:r [:reset]})
|
:r [:reset]
|
||||||
|
:e [:edit]})
|
||||||
|
|
||||||
(fn Rules.run-command [cmd]
|
(fn Rules.run-command [cmd]
|
||||||
(when cmd
|
(when cmd
|
||||||
|
|
|
@ -41,7 +41,7 @@
|
||||||
tile (tile-at tx ty tilemap tileset)
|
tile (tile-at tx ty tilemap tileset)
|
||||||
xt (+ x (* tx dim.tilesize) (/ dim.tilesize 2))
|
xt (+ x (* tx dim.tilesize) (/ dim.tilesize 2))
|
||||||
yt (+ y (* ty dim.tilesize) (/ dim.tilesize 2))]
|
yt (+ y (* ty dim.tilesize) (/ dim.tilesize 2))]
|
||||||
(drawtile tile xt yt)))))
|
(when tile (drawtile tile xt yt))))))
|
||||||
|
|
||||||
(fn world-to-tile [vec]
|
(fn world-to-tile [vec]
|
||||||
(-> vec
|
(-> vec
|
||||||
|
|
Loading…
Reference in a new issue