summaryrefslogtreecommitdiff
path: root/client/menu.lua
diff options
context:
space:
mode:
Diffstat (limited to 'client/menu.lua')
-rw-r--r--client/menu.lua106
1 files changed, 106 insertions, 0 deletions
diff --git a/client/menu.lua b/client/menu.lua
new file mode 100644
index 0000000..a6eccfb
--- /dev/null
+++ b/client/menu.lua
@@ -0,0 +1,106 @@
+local Pos = require'r.pos'
+local Rect = require'r.rect'
+local class = require'r.class'
+local G = love.graphics
+local utf8 = require'utf8'
+local enet = require'enet'
+local json = require'dkjson'
+local pprint = require'pprint'
+local qw = require'r.qw'
+
+local logo = G.newImage"logo.png" logo:setFilter'nearest'
+
+local function c(...) return {love.math.colorFromBytes(...)} end
+-- taken from breadquest
+local colors = { c(255,64,64), c(255,128,0), c(192,192,64), c(0,192,0),
+ c(0,192,192), c(64,64,255), c(192,0,192), c(128,128,128)}
+
+local state = {color=1,focused=nil,name='Susan',errmsg=nil}
+local rstate = love.filesystem.read'menu.json'
+if rstate then for k,v in pairs(json.decode(rstate)) do state[k]=v end end
+
+local LogoImage = {}
+function LogoImage.draw() G.setColor(1,1,1) G.draw(logo, 120, 50, 0, 12) end
+
+local ColorButton = class()
+function ColorButton.make(cls, idx)
+ local size, gap = 40, 10
+ local tl = Pos(100,240) + (idx-1)*Pos(size+gap,0)
+ local bb = Rect:from_pos(tl,tl+Pos(size,size))
+ return setmetatable({bb=bb,idx=idx},cls) end
+function ColorButton.draw(self)
+ G.setColor(colors[self.idx]) self.bb:draw'fill'
+ if self.idx == state.color then G.setColor(0,0,0) local d=5
+ G.line(self.bb.x0+d,self.bb.y0+d,self.bb.x1-d,self.bb.y1-d)
+ G.line(self.bb.x0+d,self.bb.y1-d,self.bb.x1-d,self.bb.y0+d) end end
+function ColorButton.click(self) state.color = self.idx end
+
+local font = G.newFont(24)
+local bigfont = G.newFont(36)
+local NameField = class()
+function NameField.make(cls,org)
+ local self = setmetatable({org=org},cls) self:setbb() return self end
+function NameField.setbb(self) local width = 12+math.max(200,font:getWidth(state.name))
+ self.bb=Rect:from_xywh(self.org.x,self.org.y,width,font:getHeight()) end
+function NameField.draw(self) G.setColor(0,0,0) self.bb:draw'line' local d=3
+ G.setFont(font) G.print(state.name,self.bb.x0+d,self.bb.y0)
+ if self == state.focused then local w = 2*d+self.bb.x0+font:getWidth(state.name)
+ G.line(w,self.bb.y0+d,w,self.bb.y1-d) end end
+function NameField.input(self,text) state.name = state.name .. text self:setbb() end
+function NameField.key(self,key) if key == 'backspace' and #state.name > 0 then
+ state.name = state.name:sub(1,utf8.offset(state.name,-1)-1) self:setbb() end end
+
+local w,h = bigfont:getWidth"connecting...", bigfont:getHeight()
+local ConnectButton = { bb=Rect:from_xywh(100,400,w,h),c=false }
+function ConnectButton.draw(self) G.setColor(0,1,0.2) self.bb:draw'fill'
+ G.setColor(0,0,0) G.setFont(bigfont)
+ G.print(self.c and 'connecting...' or 'connect',self.bb.tl:vals()) end
+
+local ErrDisp = {draw=function() if state.errmsg then
+ G.setColor(1,0,0) G.setFont(font) G.print(state.errmsg,100,10) end end}
+
+local things = { NameField(Pos(100,300)), LogoImage, ConnectButton, ErrDisp }
+for i=1,#colors do table.insert(things, ColorButton(i)) end
+
+local function draw_ui() for _,thing in ipairs(things) do
+ if thing.draw then thing:draw() end
+ if thing.bb and thing.bb:has(Pos(love.mouse.getPosition())) then
+ G.setColor(0,0,0) thing.bb:draw'line' end end end
+
+local function which(p) for _,thing in ipairs(things) do
+ if thing.bb and thing.bb:has(p) then return thing end end end
+function love.draw() G.clear(1,1,1) draw_ui() end
+function love.mousepressed(x,y,button)
+ local thing = which(Pos(x,y)) if thing then state.focused = thing
+ if thing.click then thing:click() end end end
+love.keyboard.setKeyRepeat(true)
+function love.textinput(text) if state.focused and state.focused.input then
+ state.focused:input(text) end end
+function love.keypressed(key) if state.focused and state.focused.key then
+ state.focused:key(key) end end
+
+local host,conn
+function ConnectButton.click(self)
+ print(love.filesystem.write('menu.json',
+ json.encode{color=state.color,name=state.name}))
+ self.c = true host = enet.host_create() conn=host:connect"localhost:19683"end
+function ConnectButton.unclick(self)
+ self.c = false host=nil conn=nil end
+
+local function switch_scene(modname,...)
+ local mod = require(modname)
+ for k in qw.i"update keypressed textinput mousepressed draw" do
+ love[k] = nil end
+ for k,v in pairs(mod) do love[k] = v end
+ G.reset() if mod.load then mod.load(...) end
+end
+
+function love.update(dt)
+ local ev = host and host:service() while ev do
+ pprint(ev)
+ if ev.type == 'receive' then local j = json.decode(ev.data)
+ if j.type == 'you' then switch_scene('game',host,conn,j) return
+ elseif j.type == 'error' then print('hi') state.errmsg = j.msg conn:disconnect_later() ConnectButton:unclick()
+ end
+ elseif ev.type == 'connect' then conn:send(json.encode{type='hi',name=state.name,color=colors[state.color]}) end
+ ev = host and host:service() end end