utf8 = require 'utf8' json = require 'json' require 'app' require 'test' require 'live' require 'keychord' require 'button' -- delegate most business logic to a layer that can be reused by other projects require 'edit' Editor_state = {} -- called both in tests and real run function App.initialize_globals() -- tests currently mostly clear their own state -- a few text objects we can avoid recomputing unless the font changes Text_cache = {} -- blinking cursor Cursor_time = 0 -- for hysteresis in a few places Current_time = 0 Last_focus_time = 0 -- https://love2d.org/forums/viewtopic.php?p=249700 Last_resize_time = 0 end -- called only for real run function App.initialize(arg) love.keyboard.setTextInput(true) -- bring up keyboard on touch screen love.keyboard.setKeyRepeat(true) Editor_state = nil -- not used outside editor tests love.graphics.setBackgroundColor(1,1,1) live.initialize(arg) load_settings() -- TODO: app-specific stuff goes here love.window.setTitle('TODO') if on.initialize then on.initialize(arg) end if rawget(_G, 'jit') then jit.off() jit.flush() end end function love.quit() if on.quit then on.quit() end love.filesystem.write('config', json.encode(settings())) end function settings() local x, y, displayindex = App.screen.position() return { x=x, y=y, displayindex=displayindex, width=App.screen.width, height=App.screen.height, app = on.save_settings and on.save_settings(), } end function load_settings() if love.filesystem.getInfo('config') then local settings = json.decode(love.filesystem.read('config')) local width, height, flags = love.window.getMode() flags.resizable = true flags.minwidth = math.min(width, 200) flags.minheight = math.min(height, 200) App.screen.flags = flags App.screen.width = settings.width App.screen.height = settings.height love.window.setMode(App.screen.width, App.screen.height, App.screen.flags) love.window.setPosition(settings.x, settings.y, settings.displayindex) if on.load_settings then on.load_settings(settings.app) end else local font_height = 20 love.graphics.setFont(love.graphics.newFont(font_height)) -- maximize window love.window.setMode(0, 0) -- maximize App.screen.width, App.screen.height, App.screen.flags = love.window.getMode() -- shrink height slightly to account for window decoration App.screen.height = App.screen.height-100 App.screen.width = 40*App.width(App.newText(love.graphics.getFont(), 'm')) App.screen.flags.resizable = true App.screen.flags.minwidth = math.min(App.screen.width, 200) App.screen.flags.minheight = math.min(App.screen.height, 200) love.window.setMode(App.screen.width, App.screen.height, App.screen.flags) if on.load_settings then on.load_settings() end end end function App.resize(w, h) --? print(("Window resized to width: %d and height: %d."):format(w, h)) App.screen.width, App.screen.height = w, h Last_resize_time = Current_time if on.resize then on.resize(w,h) end end function App.filedropped(file) if on.file_drop then on.file_drop(file) end end function App.draw() if on.draw then on.draw() end end function App.update(dt) Current_time = Current_time + dt -- some hysteresis while resizing if Current_time < Last_resize_time + 0.1 then return end Cursor_time = Cursor_time + dt live.update(dt) if on.update then on.update(dt) end end function App.mousepressed(x,y, mouse_button) Cursor_time = 0 -- ensure cursor is visible immediately after it moves if on.mouse_press then on.mouse_press(x,y, mouse_button) end end function App.mousereleased(x,y, mouse_button) Cursor_time = 0 -- ensure cursor is visible immediately after it moves if on.mouse_release then on.mouse_release(x,y, mouse_button) end end function App.focus(in_focus) if in_focus then Last_focus_time = Current_time end if in_focus then love.graphics.setBackgroundColor(1,1,1) else love.graphics.setBackgroundColor(0.8,0.8,0.8) end if on.focus then on.focus(in_focus) end end -- App.keypressed is defined in keychord.lua function App.keychord_press(chord, key) -- ignore events for some time after window in focus (mostly alt-tab) if Current_time < Last_focus_time + 0.01 then return end Cursor_time = 0 -- ensure cursor is visible immediately after it moves if on.keychord_press then on.keychord_press(chord, key) end end function App.textinput(t) -- ignore events for some time after window in focus (mostly alt-tab) if Current_time < Last_focus_time + 0.01 then return end Cursor_time = 0 -- ensure cursor is visible immediately after it moves if on.text_input then on.text_input(t) end end function App.keyreleased(key, scancode) -- ignore events for some time after window in focus (mostly alt-tab) if Current_time < Last_focus_time + 0.01 then return end Cursor_time = 0 -- ensure cursor is visible immediately after it moves if on.key_release then on.key_release(key, scancode) end end -- use this sparingly function to_text(s) if Text_cache[s] == nil then Text_cache[s] = App.newText(love.graphics.getFont(), s) end return Text_cache[s] end