Love2d-学习

Youtube 教程

love2d 官方网站

awesome-love2d

安装

在 Archlinux 下, 安装为:

1
sudo pacman -S love

导入到当前环境

1
_G.love = require("love")

三个基本的 stages

包括:

  • load
  • update
  • draw

因此在每一个游戏中, 都需要定义这三个函数:

1
2
3
4
5
6
7
8
9
10
11
12
13
_G.love = require("love")

function love.load()

end

function love.update(dt)

end

function love.draw()

end

love.load 在游戏启动时被调用, 用于初始化游戏的资源和设置.

love.update 在每一帧更新时被调用,用于处理游戏逻辑和更新游戏状态.

dtdata time, 表示距离上一帧经过的时间(以秒为单位),可以用于使游戏的更新速度与实际运行时间保持一致

love.draw 在每一帧绘制时被调用,用于绘制游戏界面和对象.

打印字符串

love.graphics.print 函数:

1
2
3
4
5
6
7
8
9
10
11
12
13
_G.love = require("love")

function love.load()
_G.number = 0
end

function love.update(dt)
number = number + 1
end

function love.draw()
love.graphics.print(number)
end

love2d 配置文件

在每一个项目下都可以创建, 文件名为 conf.lua.

其内容为:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
function love.conf(t)
t.identity = "data/saves"
t.version "1.0.0"
t.console = true
t.externalstorage = true
t.gammacorrect = true
t.audio.mic = true
t.window.title = "Cool Game"
t.window.icon = "icon/game_icon.jpg"
t.window.width = 400
t.window.height = 200
t.window.minwidth = 400
t.window.minheight = 200
t.window.resizeble = true
t.window.borderless = true
t.window.vsync = 1
t.window.display = 1
t.window.fullscreen = true
t.window.fullscreen = true
t.window.x = 100
t.window.y = 100

t.modules.timer = true
end

绘制以及移动图形

正方形

love.graphics.rectangle:

1
2
3
4
5
6
7
8
9
10
11
_G.love = require("love")

function love.load()
end

function love.update(dt)
end

function love.draw()
love.graphics.rectangle("fill", 50, 50, 50, 50)
end

后四个参数分别为 x, y, width, height.

设置正方形颜色

love.graphics.setColor

1
2
3
4
5
6
7
8
9
10
11
12
13
14
_G.love = require("love")

function love.load()
end

function love.update(dt)
end

function love.draw()
-- Red, Green, Blue
-- 0 0 0
love.graphics.setColor(1, 0, 0)
love.graphics.rectangle("fill", 50, 50, 50, 50)
end

三个参数分别为 RGB. 取值为 0~1, 如:

1
love.graphics.setColor(75/255, 148/255, 10/255)

设置背景颜色

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
_G.love = require("love")

function love.load()
love.graphics.setBackgroundColor(0.5, 0.5, 1)
end

function love.update(dt)
end

function love.draw()
-- Red, Green, Blue
-- 0 0 0
love.graphics.setColor(1, 0, 0)
love.graphics.rectangle("fill", 50, 50, 50, 50)
end

圆形

love.graphics.circle("line", 100, 100, 50)

第三个参数为半径.

设置颜色:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
_G.love = require("love")

function love.load()
love.graphics.setBackgroundColor(0.5, 0.5, 1)

end

function love.update(dt)
end

function love.draw()
love.graphics.setColor(75/255, 148/255, 10/255)
love.graphics.rectangle("fill", 50, 50, 100, 50)

love.graphics.setColor(1, 0.7, 0.1)
love.graphics.circle("line", 50, 50, 50)
end

扇形

love.graphics.arc("line", x, y, radius, begin_d, end_d)

注意这里用的是弧度.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
_G.love = require("love")

function love.load()
love.graphics.setBackgroundColor(0.5, 0.5, 1)

end

function love.update(dt)
end

function love.draw()
love.graphics.setColor(75/255, 148/255, 10/255)
love.graphics.rectangle("fill", 50, 50, 100, 50)

love.graphics.setColor(1, 0.7, 0.1)
love.graphics.arc("line", 50, 50, 60, 0, 5)
end

pacman 小游戏

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
_G.love = require("love")

function love.load()
love.graphics.setBackgroundColor(0.5, 0.5, 1)
_G.pacman = {}
pacman.x = 200
pacman.y = 200
pacman.eat = false

_G.food_x = 400
end

function love.update(dt)
pacman.x = pacman.x + 1
if pacman.x >= food_x then pacman.eat = true end
end

function love.draw()
if not pacman.eat then
love.graphics.setColor(75/255, 148/255, 10/255)
love.graphics.rectangle("fill", 400, 180, 50, 50)
end

love.graphics.setColor(1, 0.7, 0.1)
love.graphics.arc("fill", pacman.x, pacman.y, 60, 1, 5)
end

按键检测

检测 keyboard input 事件.

用:

  • love.keyboard.isDown()

如:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
_G.love = require("love")

function love.load()
love.graphics.setBackgroundColor(0.5, 0.5, 1)
_G.pacman = {}
pacman.x = 200
pacman.y = 200
pacman.eat = false

_G.food_x = 400
end

function love.update(dt)
if love.keyboard.isDown("h") then pacman.x = pacman.x - 1 end
if love.keyboard.isDown("l") then pacman.x = pacman.x + 1 end
if love.keyboard.isDown("k") then pacman.y = pacman.y - 1 end
if love.keyboard.isDown("j") then pacman.y = pacman.y + 1 end
if pacman.x >= food_x then pacman.eat = true end
end

function love.draw()
if not pacman.eat then
love.graphics.setColor(75/255, 148/255, 10/255)
love.graphics.rectangle("fill", 400, 180, 50, 50)
end

love.graphics.setColor(1, 0.7, 0.1)
love.graphics.arc("fill", pacman.x, pacman.y, 60, 1, 5)
end

使用 Sprites 精灵图

可获取素材的网站

这里使用的素材

载入一个 sprite 用 love.graphics.newImage("path/to/sprite")

创建 Quad 对象用 love.graphics.newQuad(x, y, width, height, sw, sh)

绘制用 love.graphics.draw(sprite, quad, x, y)
(quad 是可选的)

调整图像大小, 用 love.graphics.scale().

love.graphics.draw 还可将图片翻转:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
_G.love = require("love")

function love.load()
_G.jie = {
x = 0,
y = 0,
sprite = love.graphics.newImage("sprites/spritesheet.png"),
animation = {
direction = "right",
idle = true,
frame = 1,
maxframe = 8,
speed = 20,
timer = 0.1
}
}

SPRITE_WIDTH, SPRITE_HEIGHT = 5352, 569
QUAD_WIDTH = 669
QUAD_HIGHT = SPRITE_HEIGHT

quads = {}

for i = 1, 8 do
quads[i] = love.graphics.newQuad((i-1)*QUAD_WIDTH, 0, QUAD_WIDTH, QUAD_HIGHT, SPRITE_WIDTH, SPRITE_HEIGHT)
end
end

function love.update(dt)
if love.keyboard.isDown("l") then
jie.animation.idle = false
jie.animation.direction = 'right'
elseif love.keyboard.isDown('h') then
jie.animation.idle = false
jie.animation.direction = 'left'
else
jie.animation.idle = true
jie.animation.frame = 1
end

if not jie.animation.idle then
jie.animation.timer = jie.animation.timer + dt

if jie.animation.timer > 0.2 then
jie.animation.timer = 0.1

jie.animation.frame = jie.animation.frame + 1
if jie.animation.direction == 'right' then
jie.x = jie.x + jie.animation.speed
elseif jie.animation.direction == 'left' then
jie.x = jie.x - jie.animation.speed
end

if jie.animation.frame > jie.animation.maxframe then
jie.animation.frame = 1
end
end
end
end

function love.draw()
love.graphics.scale(0.5)
if jie.animation.direction == 'right' then
love.graphics.draw(jie.sprite, quads[jie.animation.frame], jie.x, jie.y)
else
love.graphics.draw(jie.sprite, quads[jie.animation.frame], jie.x, jie.y, 0, -1, 1, QUAD_WIDTH, 0)
end
end

love.graphics.draw 的后四个参数的含义分别为:

  • 旋转角度 radians
  • 水平缩放比例
  • 垂直缩放比例
  • 源矩形区域的偏移量X, 表示从 Quad 对象中裁剪出的矩形区域的偏移量X。
  • 源矩形区域的偏移量Y, 表示从 Quad 对象中裁剪出的矩形区域的偏移量Y

获取光标位置

love.mouse.getPosition(), 其返回 xy 两个值.

示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
local love = require("love")

function love.load()
_G.player = {
radius = 20,
x = 30,
y = 30
}
end

function love.update(dt)
player.x, player.y = love.mouse.getPosition()
end

function love.draw()
love.graphics.circle("fill", player.x, player.y, player.radius)
end

让光标消失

love.mouse.setVisible(false), 即可让光标消失.

获取 FPS 信息

love.timer.getFPS()

获取 window 的宽高信息

love.graphics.getWidth()love.graphics.getHeight()

格式化打印

love.graphics.printf(string, fontsize, x, y, mw), mw 指 max width, 也就是文本的最大宽度.

如:

1
2
3
4
5
love.graphics.printf("FPS: " .. love.timer.getFPS(),
love.graphics.newFont(16),
10,
love.graphics.getHeight() - 26,
love.graphics.getWidth())

退出游戏

调用 love.event.quit

1
love.event.quit

鼠标点击事件

通过定义 love.mousepressed(x, y, button, istouch, presses) 函数:

1
2
3
4
5
6
7
8
9
function love.mousepressed(x, y, button, istouch, presses)
if button == 1 then
-- 这里是左键点击事件的处理代码
print("Left mouse button pressed at (" .. x .. ", " .. y .. ")")
elseif button == 2 then
-- 这里是右键点击事件的处理代码
print("Right mouse button pressed at (" .. x .. ", " .. y .. ")")
end
end
  • x: 鼠标点击位置的 x 坐标。
  • y: 鼠标点击位置的 y 坐标。
  • button: 表示按下的鼠标按钮。1 代表左键,2 代表右键,3 代表中键。
  • istouch: 一个布尔值,表示事件是否由触摸触发。
  • presses: 表示按下的次数,通常用于处理双击事件。

检测 enemy 和 player 的接触

如:

1
2
3
checkTouched = function (self, player_x, player_y, cursor_radius)
return math.sqrt((self.x - player_x)^2 + (self.y - player_y)^2) <= cursor_radius * 2
end,

Love2d-学习
http://example.com/2023/11/14/Love2d-学习/
作者
Jie
发布于
2023年11月14日
许可协议