删除测试代码,升级textBox控件,改进listBox控件,整理代码

This commit is contained in:
MrZ626
2021-06-23 04:49:50 +08:00
parent 27ce516dd9
commit 6c2cbe5f20
3 changed files with 121 additions and 141 deletions

View File

@@ -39,6 +39,11 @@ local largerThen=DOGC{20,20,
{'line',2,2,19,10,2,18},
}
local STW,STH--stencil-wid/hei
local function rectangleStencil()
gc.rectangle('fill',1,1,STW-2,STH-2)
end
local WIDGET={}
local widgetMetatable={
__tostring=function(self)
@@ -542,7 +547,7 @@ function slider:release(x)
self:drag(x)
self.lastTime=0
end
function slider:arrowKey(isLeft)
function slider:move(isLeft)
local p=self.disp()
local u=(self.smooth and .01 or 1)
local P=isLeft and max(p-u,0)or min(p+u,self.unit)
@@ -704,7 +709,7 @@ function selector:press(x)
end
end
end
function selector:arrowKey(isLeft)
function selector:move(isLeft)
local s=self.select
if isLeft and s==1 or not isLeft and s==#self.list then return end
if isLeft then
@@ -881,10 +886,8 @@ end
local textBox={
type='textBox',
dragAble=true,
scrollPos=0,--Which line display at bottom
scrollPix=0,--Hidden wheel move value
scrollPos=0,--Scroll-down-distance
sure=0,--Sure-timer for clear history
new=false,--If there is a new message
}
function textBox:reset()
--haha nothing here, techmino is so fun!
@@ -896,7 +899,6 @@ end
function textBox:clear()
self.texts={}
self.scrollPos=0
self.new=false
SFX.play('fall')
end
function textBox:isAbove(x,y)
@@ -918,8 +920,6 @@ function textBox:push(t)
ins(self.texts,t)
if self.scrollPos==#self.texts-1 then
self.scrollPos=#self.texts
else
self.new=true
end
end
function textBox:press(x,y)
@@ -928,7 +928,6 @@ function textBox:press(x,y)
if not self.fix and x>self.x+self.w-40 and y<self.y+40 then
if self.sure>0 then
self:clear()
self.new=false
self.sure=0
else
self.sure=60
@@ -936,67 +935,56 @@ function textBox:press(x,y)
end
end
function textBox:drag(_,_,_,dy)
_=self.scrollPix+dy
local sign=_>0 and 1 or -1
while abs(_)>self.lineH do
_=_-self.lineH*sign
self:scroll(-sign)
end
self.scrollPix=_
self.scrollPos=max(0,min(self.scrollPos-dy,(#self.texts-self.capacity)*self.lineH))
end
function textBox:scroll(n)
if n<0 then
self.scrollPos=max(self.scrollPos+n,min(#self.texts,self.capacity))
else
self.scrollPos=min(self.scrollPos+n,#self.texts)
end
self.scrollPos=max(0,min(self.scrollPos+n*self.lineH,(#self.texts-self.capacity)*self.lineH))
end
function textBox:draw()
local x,y,w,h=self.x,self.y,self.w,self.h
local texts=self.texts
local scroll=self.scrollPos
local scrollPos=self.scrollPos
local cap=self.capacity
--Update new message status, necessary when hide==true
if self.scrollPos==#self.texts then
self.new=false
end
local lineH=self.lineH
--Background
gc_setColor(0,0,0,.4)
gc_rectangle('fill',x,y,w,h)
--Frame
gc_setLineWidth(4)
gc_setLineWidth(3)
gc_setColor(WIDGET.sel==self and COLOR.lN or COLOR.Z)
gc_rectangle('line',x,y,w,h)
--Slider
if #texts>cap then
gc_setLineWidth(2)
gc_rectangle('line',x-25,y,20,h)
local len=max(h*cap/#texts,26)
gc_rectangle('fill',x-22,y+(h-len-6)*(scroll-cap)/(#texts-cap)+3,14,len)
end
--Clear button
gc_setColor(1,1,1)
if not self.fix then
gc_rectangle('line',x+w-40,y,40,40)
gc_draw(self.sure==0 and clearIcon or sureIcon,x+w-40,y)
end
--Texts
setFont(self.font)
for i=max(scroll-cap+1,1),scroll do
gc_printf(texts[i],x+8,y+h-10-self.lineH*(scroll-i+1),w)
end
gc_push('transform')
gc_translate(x,y)
--New message
if self.new and self.scrollPos~=#texts then
gc_setColor(1,TIME()%.4<.2 and 1 or 0,0)
gc_print("v",x+w-25,y+h-40)
end
--Slider
gc_setColor(1,1,1)
if #texts>cap then
local len=h*h/(#texts*lineH)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#texts-cap)*lineH),12,len)
end
--Clear button
if not self.fix then
gc_rectangle('line',w-40,0,40,40)
gc_draw(self.sure==0 and clearIcon or sureIcon,w-40,0)
end
gc_setStencilTest('equal',1)
STW,STH=w,h
gc_stencil(rectangleStencil)
gc_translate(0,-(scrollPos%lineH))
local pos=int(scrollPos/lineH)
for i=pos+1,min(pos+cap+1,#texts)do
gc_printf(texts[i],10,4,w-16)
gc_translate(0,lineH)
end
gc_setStencilTest()
gc_pop()
end
function textBox:getInfo()
return("x=%d,y=%d,w=%d,h=%d"):format(self.x+self.w*.5,self.y+self.h*.5,self.w,self.h)
@@ -1039,7 +1027,7 @@ end
local listBox={
type='listBox',
dragAble=true,
scrollPos=0,--Which line display at bottom
scrollPos=0,--Scroll-down-distance
selected=0,--Hidden wheel move value
}
function listBox:reset()
@@ -1071,7 +1059,7 @@ function listBox:isAbove(x,y)
y<self.y+self.h
end
function listBox:getCenter()
return self.x+self.w*.5,self.y+self.w
return self.x+self.w*.5,self.y+self.h*.5
end
function listBox:push(t)
ins(self.list,t)
@@ -1080,7 +1068,7 @@ function listBox:press(x,y)
if not(x and y)then return end
self:drag(nil,nil,nil,0)
x,y=x-self.x,y-self.y
y=int(y/40+self.scrollPos)+1
y=int((y+self.scrollPos)/self.lineH)+1
if self.list[y]then
if self.selected~=y then
self.selected=y
@@ -1090,15 +1078,9 @@ function listBox:press(x,y)
end
function listBox:drag(_,_,_,dy)
self.scrollPos=max(0,min(self.scrollPos-dy,(#self.list-self.capacity)*self.lineH))
print(self.scrollPos)
end
function listBox:scroll(n)
self.scrollPos=max(0,min(self.scrollPos-n*self.lineH,(#self.list-self.capacity)*self.lineH))
print(self.scrollPos)
end
local SSW,SSH--stencil-size-w/h
local function listBoxStencil()
gc.rectangle('fill',1,1,SSW-2,SSH-2)
self.scrollPos=max(0,min(self.scrollPos+n*self.lineH,(#self.list-self.capacity)*self.lineH))
end
function listBox:draw()
local x,y,w,h=self.x,self.y,self.w,self.h
@@ -1109,20 +1091,23 @@ function listBox:draw()
gc_push('transform')
gc_translate(x,y)
--Frame
gc_setColor(WIDGET.sel==self and COLOR.lN or COLOR.Z)
gc_setLineWidth(3)
gc_rectangle('line',0,0,w,h)
--Slider
if #list>cap then
gc_setColor(1,1,1)
local len=h*h/(#list*lineH)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#list-cap)*lineH),12,len)
end
--List
gc_setStencilTest('equal',1)
SSW,SSH=w,h
gc_stencil(listBoxStencil)
setFont(35)
STW,STH=w,h
gc_stencil(rectangleStencil)
local pos=int(scrollPos/lineH)
gc_translate(0,-(scrollPos%lineH))
for i=pos+1,min(pos+cap+1,#list)do
@@ -1282,18 +1267,22 @@ function WIDGET.drag(x,y,dx,dy)
end
function WIDGET.release(x,y)
local W=WIDGET.sel
if W and W.type=='slider'then
if W and W.release then
W:release(x,y+WIDGET.scrollPos)
end
end
function WIDGET.keyPressed(k,isRep)
local W=WIDGET.sel
if not isRep and(k=="space"or k=="return")then
WIDGET.press()
elseif kb.isDown("lshift","lalt","lctrl")and(k=="left"or k=="right")then
--When hold [↑], control slider with left/right
if W and W.type=='slider'or W.type=='selector'then
W:arrowKey(k=="left")
if k=="space"or k=="return"then
if not isRep then
WIDGET.press()
end
elseif kb.isDown("lshift","lalt","lctrl")then
if k=="left"or k=="right"then
--When hold shift/ctrl/alt, control slider with left/right
if W and W.arrowKey then W:move(k=="left")end
elseif k=="up"or k=="down"then
if W and W.scroll then W:scroll((k=="up"and -1 or 1)*W.lineH)end
end
elseif k=="up"or k=="down"or k=="left"or k=="right"then
if not W then
@@ -1303,37 +1292,36 @@ function WIDGET.keyPressed(k,isRep)
return
end
end
return
end
if not W.getCenter then return end
local WX,WY=W:getCenter()
local dir=(k=="right"or k=="down")and 1 or -1
local tar
local minDist=1e99
local swap_xy=k=="up"or k=="down"
if swap_xy then WX,WY=WY,WX end -- note that we do not swap them back later
for _,W1 in ipairs(WIDGET.active)do
if W~=W1 and W1.resCtr and not W1.hide then
local L=W1.resCtr
for j=1,#L,2 do
local x,y=L[j],L[j+1]
if swap_xy then x,y=y,x end -- note that we do not swap them back later
local dist=(x-WX)*dir
if dist>10 then
dist=dist+abs(y-WY)*6.26
if dist<minDist then
minDist=dist
tar=W1
elseif W.getCenter then
local WX,WY=W:getCenter()
local dir=(k=="right"or k=="down")and 1 or -1
local tar
local minDist=1e99
local swap_xy=k=="up"or k=="down"
if swap_xy then WX,WY=WY,WX end -- note that we do not swap them back later
for _,W1 in ipairs(WIDGET.active)do
if W~=W1 and W1.resCtr and not W1.hide then
local L=W1.resCtr
for j=1,#L,2 do
local x,y=L[j],L[j+1]
if swap_xy then x,y=y,x end -- note that we do not swap them back later
local dist=(x-WX)*dir
if dist>10 then
dist=dist+abs(y-WY)*6.26
if dist<minDist then
minDist=dist
tar=W1
end
end
end
end
end
end
if tar then
WIDGET.focus(tar)
if tar then
WIDGET.focus(tar)
end
end
else
if W and W.type=='inputBox'then
if W and W.keypress then
W:keypress(k)
end
end

View File

@@ -508,21 +508,6 @@ function NET.updateWS_play()
SFX.play('connected')
elseif res.action==0 then--Fetch rooms
if SCN.cur=="net_rooms"then
for i=1,16 do
res.roomList[i]={
rid="qwe",
roomInfo={
name="Test room "..i,
type="classic",
version=VERSION.short,
description="x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x ",
},
private=i%3==0,
start=i%4==0,
count=i%5,
capacity=5,
}
end
WIDGET.active.roomList:setList(res.roomList)
end
NET.unlock('fetchRoom')
@@ -571,7 +556,7 @@ function NET.updateWS_play()
mode=d.mode,
config=d.config,
}
if SCN.socketRead then SCN.socketRead('join',d)end
if SCN.cur=='net_game'then SCN.socketRead('join',d)end
NET.allReady=false
end
elseif res.action==3 then--Player leave
@@ -584,10 +569,10 @@ function NET.updateWS_play()
netPLY.remove(d.sid)
removePlayer(PLAYERS,d.sid)
removePlayer(PLY_ALIVE,d.sid)
if SCN.socketRead then SCN.socketRead('leave',d)end
if SCN.cur=='net_game'then SCN.socketRead('leave',d)end
end
elseif res.action==4 then--Player talk
if SCN.socketRead then SCN.socketRead('talk',d)end
if SCN.cur=='net_game'then SCN.socketRead('talk',d)end
elseif res.action==5 then--Player change settings
netPLY.setConf(d.uid,d.config)
elseif res.action==6 then--Player change join mode
@@ -600,7 +585,7 @@ function NET.updateWS_play()
NET.connectingStream=true
NET.wsconn_stream(d.srid)
elseif res.action==9 then--Game finished
if SCN.socketRead then SCN.socketRead('finish',d)end
if SCN.cur=='net_game'then SCN.socketRead('finish',d)end
--d.result: list of {place,survivalTime,uid,score}
for _,p in next,d.result do

View File

@@ -1,26 +1,33 @@
local gc=love.graphics
local gc_translate=gc.translate
local gc_setColor,gc_setLineWidth=gc.setColor,gc.setLineWidth
local gc_draw=gc.draw
local gc_rectangle,gc_arc=gc.rectangle,gc.arc
local gc_print,gc_printf=gc.print,gc.printf
local NET=NET
local fetchTimer
local roomList=WIDGET.newListBox{name="roomList",x=50,y=50,w=800,h=440,lineH=40,drawF=function(ifSel,id,item)
setFont(35)
if ifSel then
gc.setColor(1,1,1,.3)
gc.rectangle('fill',0,0,800,40)
gc_setColor(1,1,1,.3)
gc_rectangle('fill',0,0,800,40)
end
gc.setColor(1,1,1)
if item.private then gc.draw(IMG.lock,10,5)end
gc.print(item.count.."/"..item.capacity,670,-4)
gc_setColor(1,1,1)
if item.private then gc_draw(IMG.lock,10,5)end
gc_print(item.count.."/"..item.capacity,670,-4)
gc.setColor(.9,.9,1)
gc.print(id,45,-4)
gc_setColor(.9,.9,1)
gc_print(id,45,-4)
if item.start then
gc.setColor(0,.4,.1)
gc_setColor(0,.4,.1)
else
gc.setColor(1,1,.7)
gc_setColor(1,1,.7)
end
gc.print(item.roomInfo.name,200,-4)
gc_print(item.roomInfo.name,200,-4)
end}
local function hidePW()
local R=roomList:getSel()
@@ -86,30 +93,30 @@ end
function scene.draw()
--Fetching timer
gc.setColor(1,1,1,.12)
gc.arc('fill','pie',250,630,40,-1.5708,-1.5708-.6283*fetchTimer)
gc_setColor(1,1,1,.12)
gc_arc('fill','pie',250,630,40,-1.5708,-1.5708-.6283*fetchTimer)
--Room list
local R=roomList:getSel()
if R then
gc.translate(870,220)
gc.setColor(1,1,1)
gc.setLineWidth(3)
gc.rectangle('line',0,0,385,335)
gc_translate(870,220)
gc_setColor(1,1,1)
gc_setLineWidth(3)
gc_rectangle('line',0,0,385,335)
setFont(25)
gc.print(R.roomInfo.type,10,25)
gc.setColor(1,1,.7)
gc.printf(R.roomInfo.name,10,0,365)
gc_print(R.roomInfo.type,10,25)
gc_setColor(1,1,.7)
gc_printf(R.roomInfo.name,10,0,365)
setFont(20)
gc.setColor(.8,.8,.8)
gc.printf(R.roomInfo.description or"[No description]",10,55,365)
gc_setColor(.8,.8,.8)
gc_printf(R.roomInfo.description or"[No description]",10,55,365)
if R.start then
gc.setColor(0,1,.2)
gc.print(text.started,10,300)
gc_setColor(0,1,.2)
gc_print(text.started,10,300)
end
gc.setColor(1,.2,0)
gc.printf(R.roomInfo.version,10,300,365,'right')
gc.translate(-870,-220)
gc_setColor(1,.2,0)
gc_printf(R.roomInfo.version,10,300,365,'right')
gc_translate(-870,-220)
end
--Profile