通过预设功能从 Racket 中的 Big-Bang 访问世界状态
Accessing the world-state from Big-Bang in Racket from a preset function
我正在用 Racket 创建一个带有 big bang 函数和四个结构的小游戏。我的结构如下:
(define-struct game_main (tank missile UFO))
(define-struct tank (x aim-x aim-y))
(define-struct missile (x y vel))
(define-struct UFO (x y))
(define a-game
(make-game_main
(make-tank 370 100 100)
(make-missile 500 500 1)
(make-UFO 100 100)))
在为 big bang 函数创建键事件处理程序时,我使用 a 将坦克的 x 位置向左移动,d 将其向右移动,就像这样。附上big-bang函数供参考:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main a-game [tank (make-tank (- (tank-x (game_main-tank a-game)) 7)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game)))])]
[(key=? a-key "d")
(struct-copy game_main a-game [tank (make-tank (+ (tank-x (game_main-tank a-game)) 7)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game)))])]
)
)
(big-bang a-game (to-draw game_init) (on-key controls))
效果很好;但是,它很冗长。我想定义一个函数,例如 "move-tank-left",它只包含世界状态转换器,但定义在事件处理程序之外。但是,它没有直接编辑 big-bang 操纵的结构,而是返回到我全局设置的 a-game game_main 结构并恢复它开始的 x 值。 如何引用当前的 big-bang 函数世界状态,以便您可以在 big-bang 函数之外建立函数来编辑临时状态?
这里是有问题的函数:
(define move-tank-left
(make-tank
(- (tank-x (game_main-tank a-game)) 5)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game))))
您无法引用当前 "big-bang" 状态,因为它不存在于 big-bang
之外。
(即使 big-bang
也没有真正编辑当前状态 –
(struct-copy game_main a-game ...
不修改 a-game
参数,而是创建一个新状态。)
您可以从 controls
函数传递整个游戏状态:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main a-game [tank (move-tank-left a-game)])]
...
(define (move-tank-left game-state)
(make-tank
(- (tank-x (game_main-tank game-state)) 5)
(tank-aim-x (game_main-tank game-state))
(tank-aim-y (game_main-tank game-state))))
但只绕过坦克会产生更少的依赖性,让您更容易添加坦克:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main
a-game
[tank (move-tank-left (game_main-tank a-game))])]
...
(define (move-tank-left tank)
(make-tank
(- (tank-x tank) 5)
(tank-aim-x tank)
(tank-aim-y tank)))
我正在用 Racket 创建一个带有 big bang 函数和四个结构的小游戏。我的结构如下:
(define-struct game_main (tank missile UFO))
(define-struct tank (x aim-x aim-y))
(define-struct missile (x y vel))
(define-struct UFO (x y))
(define a-game
(make-game_main
(make-tank 370 100 100)
(make-missile 500 500 1)
(make-UFO 100 100)))
在为 big bang 函数创建键事件处理程序时,我使用 a 将坦克的 x 位置向左移动,d 将其向右移动,就像这样。附上big-bang函数供参考:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main a-game [tank (make-tank (- (tank-x (game_main-tank a-game)) 7)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game)))])]
[(key=? a-key "d")
(struct-copy game_main a-game [tank (make-tank (+ (tank-x (game_main-tank a-game)) 7)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game)))])]
)
)
(big-bang a-game (to-draw game_init) (on-key controls))
效果很好;但是,它很冗长。我想定义一个函数,例如 "move-tank-left",它只包含世界状态转换器,但定义在事件处理程序之外。但是,它没有直接编辑 big-bang 操纵的结构,而是返回到我全局设置的 a-game game_main 结构并恢复它开始的 x 值。 如何引用当前的 big-bang 函数世界状态,以便您可以在 big-bang 函数之外建立函数来编辑临时状态?
这里是有问题的函数:
(define move-tank-left
(make-tank
(- (tank-x (game_main-tank a-game)) 5)
(tank-aim-x (game_main-tank a-game))
(tank-aim-y (game_main-tank a-game))))
您无法引用当前 "big-bang" 状态,因为它不存在于 big-bang
之外。
(即使 big-bang
也没有真正编辑当前状态 –
(struct-copy game_main a-game ...
不修改 a-game
参数,而是创建一个新状态。)
您可以从 controls
函数传递整个游戏状态:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main a-game [tank (move-tank-left a-game)])]
...
(define (move-tank-left game-state)
(make-tank
(- (tank-x (game_main-tank game-state)) 5)
(tank-aim-x (game_main-tank game-state))
(tank-aim-y (game_main-tank game-state))))
但只绕过坦克会产生更少的依赖性,让您更容易添加坦克:
(define (controls a-game a-key)
(cond
[(key=? a-key "a")
(struct-copy game_main
a-game
[tank (move-tank-left (game_main-tank a-game))])]
...
(define (move-tank-left tank)
(make-tank
(- (tank-x tank) 5)
(tank-aim-x tank)
(tank-aim-y tank)))