Löve and Lua based on http://nova-fusion.com/2011/06/14/aguide-to-getting-started-with-love2d/ Löve • 2D game framework • simple to use • free Game Structure • • a folder with main.lua, other files to distribute, just create a zip file of the directory contents, and give the zip file a .love extension: • • • cd humpy zip -r ../humpy.love * ... then you can double click the .love file to run it Löve’s API • • • • the “love” module is a Lua table, containing the various other modules (also tables) • audio,image,graphics,mouse, keyboard,physics,etc. many modules contain classes, eg Image callbacks are defined in the love module • • let your program handle events, draw, update,etc you don’t have to define all of them, just the ones you need (exist default versions of each (most do nothing)) callbacks in love module • love.load() -- one-time setup • love.draw() -- to render the frame • love.update() -- to update simulation • love.mousepressed(), love.mousereleased() • love.run() -- main loop • ~tebo/4849/Love/simple function love.update(dt) • player.x = player.x + player.vx * dt • player.y = player.y + player.vy * dt • end • function love.draw() • love.graphics.print( tostring(player.vx), 300,200 ) • love.graphics.print( tostring(player.vy), 350,200 ) • love.graphics.draw ( image, player.x, player.y) love.graphics • for drawing lines, shapes, text • Image and Drawable objects • reading images and fonts • managing framebuffer • special objects like particle systems screen coordinates Points •love.graphics.point ( x, y ) --draws a point •love.graphics.setPointSize ( size ) •love.graphics.setPointStyle ( style ) • for i=1, max_stars do • local x = math.random( 5, love.graphics.getWidth()-5) ~tebo/4849/Love/stars • local y = math.random( 5, love.graphics.getHeight()-5) • stars[i] = {x, y} • end • love.graphics.setPointSize ( 3 ) • love.graphics.setPointStyle ( "smooth" ) • end • function love.draw() • for i=1, #stars do -- loop through all of our stars • love.graphics.point( stars[i][1], stars[i][2]) -- draw each point Lines • love.graphics.line ( x1,y1, x2, y2, ... ) • love.graphics.line (table_of_points) • love.graphics.setLineWidth ( w ) • love.graphics.setLineStyle ( style ) • function love.load() ~tebo/4849/Code/Love/lines • points = { 0, 0 } • end • function love.draw() • x, y = love.mouse.getPosition() • love.graphics.setColor ( 255, 0, 0 ) • love.graphics.line ( 320, 240, x, y ) • points[#points + 1] = x • points[#points + 1] = y • love.graphics.setColor ( 0, 255, 0 ) • love.graphics.line ( points ) • end Drawables • • • drawable = love.graphics.newImage ( “filename” ) drawable = love.graphics.newParticleSystem () love.graphics.draw( drawable, x, y, r, sx, sy, ox, oy ) • • • • • • • function love.load() ~tebo/4849/Code/Love /flyeye • • • • • skyeye = love.graphics.newImage("masonic-eye.jpg") width = skyeye:getWidth() height = skyeye:getHeight() angle = 0 rotvel = 10 end function love.update(dt) angle = angle + rotvel * dt end function love.draw() love.graphics.draw( skyeye, 100, 100, math.rad(angle), 1, 1, width / 2, height / 2) love.audio • ‘Source’ object -- can be played • use OpenAL (directional sources, listener) • (not working on mac???) • sounds are “static” (in RAM) or “stream” • listener.x = 320 • listener.y = 240 • listener.angle = 0 • noisy sound = love.audio.newSource("bing.wav", "static") -- the "static" tells LÖVE to load the file into memory, good for short sound effects • sound:setDirection( 0, 1, 0 ) -- "down" • -- setup listener (not working on macosx at least) • love.audio.setOrientation ( 0,-1,0, 0,0,1 ) -- forward and up vectors • love.audio.setPosition ( listener.x, listener.y, 0 ) • love.audio.setVelocity ( 0, 100, 0 ) • end • function love.mousepressed( x, y, button ) • sound:stop() • -- set source position (doesn't seem to work on macosx?) • sound:setPosition ( x, y, 0 ) • sound:setPitch ( y / 240.0 ) • sound:setVolume ( x / 320.0 ) Lua • can run under embedding application (Love) • can run standalone (lua) • good for experimenting, learning chunks • • • • sequence of lua statements • • needs no separator between consecutive statements line breaks ignored can be read from interactive console can be read from a file both: lua -i filename • starts up console after running chunk from filename identifiers • string of letters, digits, underscores • starts with letter or underscore • dont’ use names like _VERSION • case sensitive • dont use reserved words: • and end break in repeat while false local return do for nil then else function not true elseif if or until comments • • single line comment: starts with -- (2 hyphens) block comments • • • --[[ --]] (disable by adding a hyphen at front of opening comment ---[[ is just a single line comment) Types and Values • • • Lua is dynamically typed • • no type definitions each value carries a type 8 basic types: • nil, boolean, number, string, userdata, function, thread, table the type() function returns a string with the type’s name • • print( type(“Hello World”) ) print ( type(10.4*3)) Nil • a type with a single value, nil • a “non-value” meaning “no useful value” • different from every other value • globals are nil by default (before assignment) • delete a variable by assigning nil to it • return nil Booleans • two values: true and false • conditionals consider nil and false as false • anything else (including 0, “”) is true Numbers • double-precision floating-point • no rounding errors with integers < 10^14 • ex) 4 3.1543 6.25e23 100e-3 Strings • • • • • sequence of characters • can contain any embedded code, incl zero immutable - can’t change strings, just create new ones with changes • • • • a = “one string” b = string.gsub(a, “one”, “another”0 print (a) print (b) can use single or double quotes can include C-like escape sequences (\n, \t, etc) can also use [[ and ]] to delimit multi-line strings strings • • • • • • any numeric operation applied to a string tries to convert the string to a number print (“10” + 1) -- prints 11 if a number is given when a string is expected, lua tries to convert it print(10 .. 20 ) -- prints 1020 • .. operator is string concatenation best to do explicit coercion • • tonumber(string) tostring(number) get string length with the length operator, # • • a = “hello” print(#a) Tables • associative arrays -- indexed with any value except nil • the ONLY data structure in lua • used for arrays, sets, records, queues, etc. • tables are objects table examples • • • • • • • • • a = {} -- creates an empty table k = “x” a[k] = 10 a[20] = “cool” print(a[“x”]) --> 10 k = 20 --> “cool” print(a[k]) a[“x”] = a[“x”] + 1 print(a[“x”]) --> 11 tables • • • • tables grow as needed to hold new values a.name is syntactic sugar for a[“name”] • not a[name] !!! lua convention: arrays start at 1! # gives last index (size) of table (doesn’t count holes...) • • • for i = 1,#a do print (a[i]) end functions • first-class values • can store in variables, • can pass as arguments to other functions • can be returned from functions • “proper lexical scoping” of nested functions userdata and threads • userdata - for arbitrary C data in lua variables • threads - coroutines(?)