I’ve been scratching my head on this one for a while so I’ve taken the step of stripping back my code to the bare minimum so people can have a go at spot the bug. I am trying to get some specific menus to work as a subclass of a broader Button class and even though I’ve got this working in some other part of my code (deleted here for brevity) the touched function just isn’t being called properly this time. I wonder if it’s a problem with the way I’m using the scene manager that I shamelessly copied from an old post on here. Any ideas, anyone? I’ve tried making all sorts of changes without success.
--# Main
-- Use this function to perform your initial setup
function setup()
supportedOrientations(PORTRAIT)
displayMode(OVERLAY)
sceneManager = SceneManager({MapScreen()})
end
-- This function gets called once every frame
function draw()
sceneManager:draw()
end
function touched(touch)
sceneManager:touched(touch)
end
function keyboard(key)
sceneManager:keyboard(key)
end
function textTop(str,x,y)
local w,h = textSize(str)
text(str,x,y-h)
end
--# Button
Button = class()
function Button:init(displayName)
-- you can accept and set parameters here
self.displayName = displayName
self.pos = vec2(0,0)
self.size = vec2(0,0)
self.action = nil
self.color = color(190, 143, 65, 255)
end
function Button:draw()
pushStyle()
fill(self.color)
font("Baskerville-SemiBold")
fontSize(25)
-- use display name for size
local w,h = textSize(self.displayName)
w = w + 30
h = h + 20
RoundRect(self.pos.x-w/2,
self.pos.y-h/2,
w,h,15)
self.size = vec2(w,h)
textMode(CENTER)
fill(54, 65, 96, 255)
text(self.displayName,self.pos.x+2,self.pos.y-2)
fill(255, 255, 255, 255)
text(self.displayName,self.pos.x,self.pos.y)
popStyle()
end
function Button:hit(p)
local l = self.pos.x - self.size.x/2
local r = self.pos.x + self.size.x/2
local t = self.pos.y + self.size.y/2
local b = self.pos.y - self.size.y/2
if p.x > l and p.x < r and
p.y > b and p.y < t then
return true
end
return false
end
function Button:touched(touch)
-- Codea does not automatically call this method
-- print("wooeee2!")
if touch.state == ENDED and
self:hit(vec2(touch.x,touch.y)) then
if self.action then
self.action()
end
end
end
--# SceneManager
SceneManager = class()
function SceneManager:init(scenes)
-- you can accept and set parameters here
self.scenes = scenes
if (table.maxn(self.scenes) > 0) then
self.currentScene = scenes[1]
end
end
function SceneManager:addScene(scene)
table.insert(self.scenes, scene)
if (table.max (self.scenes) == 1) then
self.currentScene = scenes[1]
end
end
function SceneManager:switchScene(newScene)
faderclockreset()
if (self.currentScene.onExit) then
self.currentScene:onExit()
end
self.currentScene = self.scenes[newScene]
if (self.currentScene.onEnter) then
self.currentScene:onEnter()
end
end
function SceneManager:update()
if (self.currentScene.update) then
self.currentScene:update()
end
end
function SceneManager:draw()
if (self.currentScene.draw) then
self.currentScene:draw()
end
end
function SceneManager:touched(touch)
if (self.currentScene.touched) then
self.currentScene:touched(touch)
end
end
function SceneManager:keyboard(key)
if (self.currentScene.keyboard) then
self.currentScene:keyboard(key)
end
end
--# MapScreen
MapScreen = class()
-- Map
-- Use this function to perform your initial setup
function MapScreen:init()
map_leftbut = MapMenu(2)
map_rightbut = MapMenu(3)
map_leftbut.pos = vec2(150, 200)
map_rightbut.pos = vec2(WIDTH-150, 200)
end
function MapScreen:onEnter()
end
function MapScreen:draw()
background(255, 255, 255, 255)
self:drawButtons()
end
function MapScreen:drawButtons()
pushStyle()
map_leftbut:draw()
map_rightbut:draw()
popStyle()
end
function MapScreen:onExit()
end
function MapScreen:touched(touch)
map_leftbut:touched(touch)
map_rightbut:touched(touch)
end
MapMenu = class(button)
function MapMenu:init(displayName)
Button.init(self, displayName)
self.displayName = displayName
self.action = function() print("HELLO!") end
end
function MapMenu:draw()
-- Codea does not automatically call this method
pushStyle()
fill(73, 125, 30, 255)
font("Baskerville-SemiBold")
fontSize(25)
textWrapWidth(140)
textAlign(CENTER)
-- use display name for size
local x,y = textSize(self.displayName)
w = 180
h = 150
RoundRect(self.pos.x-w/2,
self.pos.y-h/2,
w,h,15)
self.size = vec2(w,h)
textMode(CENTER)
fill(96, 63, 54, 255)
text(self.displayName,self.pos.x+2,self.pos.y+y-2)
fill(235, 232, 226, 255)
text(self.displayName,self.pos.x,self.pos.y+y)
popStyle()
end
--# RoundRect
function RoundRect(x,y,w,h,r)
pushStyle()
pushMatrix()
insetPos = vec2(x+r,y+r)
insetSize = vec2(w-2*r,h-2*r)
--Copy fill into stroke
local red,green,blue,a = fill()
stroke(red,green,blue,a)
noSmooth()
rectMode(CORNER)
rect(insetPos.x,insetPos.y,insetSize.x,insetSize.y)
if r > 0 then
smooth()
lineCapMode(ROUND)
strokeWidth(r*2)
line(insetPos.x, insetPos.y,
insetPos.x + insetSize.x, insetPos.y)
line(insetPos.x, insetPos.y,
insetPos.x, insetPos.y + insetSize.y)
line(insetPos.x, insetPos.y + insetSize.y,
insetPos.x + insetSize.x, insetPos.y + insetSize.y)
line(insetPos.x + insetSize.x, insetPos.y,
insetPos.x + insetSize.x, insetPos.y + insetSize.y)
end
popMatrix()
popStyle()
end