Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- -- Cette ligne permet d'afficher des traces dans la console pendant l'éxécution
- io.stdout:setvbuf('no')
- -- Empèche Love de filtrer les contours des images quand elles sont redimentionnées
- -- Indispensable pour du pixel art
- love.graphics.setDefaultFilter("nearest")
- -- Cette ligne permet de déboguer pas à pas dans ZeroBraneStudio
- if arg[#arg] == "-debug" then require("mobdebug").start() end
- --Tiles de la map
- local imgTiles = {}
- imgTiles["1"] = love.graphics.newImage ("pictures/tile1.png")
- imgTiles["2"] = love.graphics.newImage ("pictures/tile2.png")
- imgTiles["3"] = love.graphics.newImage ("pictures/tile3.png")
- imgTiles["4"] = love.graphics.newImage ("pictures/tile4.png")
- imgTiles["5"] = love.graphics.newImage ("pictures/tile5.png")
- imgTiles["="] = love.graphics.newImage ("pictures/tile=.png")
- imgTiles["["] = love.graphics.newImage ("pictures/tile[.png")
- imgTiles["]"] = love.graphics.newImage ("pictures/tile].png")
- imgTiles["g"] = love.graphics.newImage ("pictures/tileg.png")
- imgTiles["H"] = love.graphics.newImage ("pictures/tileH.png")
- imgTiles["#"] = love.graphics.newImage ("pictures/tile#.png")
- imgTiles["<"] = love.graphics.newImage ("pictures/tile-arrow-left.png")
- imgTiles[">"] = love.graphics.newImage ("pictures/tile-arrow-right.png")
- imgTiles["#"] = love.graphics.newImage ("pictures/tile#.png")
- imgTiles["c"] = love.graphics.newImage ("pictures/coin/coin1.png")
- -- Image du héros
- imgPlayer = love.graphics.newImage ("pictures/player/idle1.png")
- -- Petite musique pour s'ambiancer
- OstPlatformer = love.audio.newSource ("Audio/laidback.ogg.ogg","stream")
- -- La map avec les niveaux et les sprites
- local map = {}
- local levels = {}
- local currentLevel = 0
- local lstSprites = {}
- local player = nil
- -- CONSTANTES
- local TILESIZE = 16 --Dimensions des tuiles
- local bJumpReady -- si le joueur est prêt à sauter ou non
- local GRAVITY = 1
- function ChargeNiveau (pNum)
- -- sécurité au cas où on dépasse l'index de niveau
- if pNum > #levels then
- print ("There is no level "..tostring(pNum)..".txt")
- end
- currentLevel = pNum
- map = {}
- local filename = "levels/level"..tostring(pNum)..".txt" -- iterator qui permet de charger ses maps via un fichier txt
- for line in love.filesystem.lines (filename) do
- map [#map + 1 ] = line
- end
- -- Look for the sprites in map/ On charge les paramètres des sprites sur la map
- lstSprites = {}
- level = {}
- level.PlayerStart = {}
- level.PlayerStart.col = 5
- level.PlayerStart.lig = 14
- for l = 1, #map do
- for c = 1, #map[1] do
- local char = string.sub (map[l], c, c )
- if char == "P" then
- level.PlayerStart.col = c
- level.PlayerStart.lig = l
- player = CreatePlayer (c,l)
- elseif char == "c" then
- CreateCoin (c, l)
- end
- end
- end
- end
- function isSolid (pID)
- -- sert à déterminer si il y a collision ou non
- if pID == "0" then return false
- elseif pID == "1" then return true end
- return false
- end
- function isJumpThrough (pID)
- if pID == "2" then return true end
- return false
- end
- function isLadder (pID)
- if pID == "H" then return true
- elseif pID == "#" then return true end
- return false
- end
- function CreateSprite (pType,pX, pY)
- --factory/usine à sprite pour les créer
- mySprite = {}
- mySprite.x = pX
- mySprite.y = pY
- mySprite.vx = 0
- mySprite.vy = 0
- mySprite.type = pType
- mySprite.gravity = 0
- mySprite.isJumping = false
- mySprite.standing = false
- mySprite.flip = false-- pour tourner l'image à gauche sans ajouter d'images
- -- Animations des sprites
- mySprite.currentAnimation = ""
- mySprite.frame = 0
- mySprite.animationSpeed = 1/8
- mySprite.animationTimer = mySprite.animationSpeed
- mySprite.Animations = {}
- mySprite.images = {}
- mySprite.AddImages = function (psDir,plstImages) -- fonction qui va ajouter les images des sprites
- for k,v in pairs (plstImages) do
- local fileName = psDir.."/"..v..".png"
- mySprite.images [v] = love.graphics.newImage (fileName)
- end
- end
- mySprite.AddAnimation = function(psDir, psName, plstImages)
- mySprite.AddImages(psDir, plstImages)
- mySprite.Animations[psName] = plstImages
- end
- mySprite.PlayAnimations = function (psName) -- fonction qui va jouer les animations
- if mySprite.currentAnimation ~= psName then
- mySprite.currentAnimation = psName
- mySprite.frame = 1
- end
- end
- table.insert (lstSprites, mySprite )
- return mySprite
- end
- function CreatePlayer(pCol, pLig)
- local myPlayer = CreateSprite("player", (pCol-1) * TILESIZE, (pLig-1) * TILESIZE)
- myPlayer.gravity = 500
- myPlayer.AddAnimation("pictures/player", "idle", { "idle1", "idle2", "idle3", "idle4" })
- myPlayer.AddAnimation("pictures/player", "run", { "run1", "run2", "run3", "run4", "run5", "run6", "run7", "run8", "run9", "run10" })
- myPlayer.AddAnimation("pictures/player", "climb", { "climb1", "climb2" })
- myPlayer.AddAnimation("pictures/player", "climb_idle", { "climb1" })
- myPlayer.PlayAnimation("idle")
- bJumpReady = true
- return myPlayer
- end
- function CreateCoin (pcol, plig )
- local myCoin = CreateSprite ("coin", (pcol -1) *TILESIZE, (plig-1) *TILESIZE )
- myCoin.AddAnimation ("pictures/coin", "idle", { "coin1", "coin2", "coin3", "coin4" } )
- myCoin.PlayAnimations ("idle")
- end
- function InitGame(pNiveau)
- -- Initialisation du niveau
- ChargeNiveau(pNiveau)
- end
- function love.load()
- love.window.setTitle("Mini platformer de BladeRED 2019")
- love.audio.play (OstPlatformer)
- OstPlatformer:isLooping (true)
- Width = love.graphics.getWidth()
- Height = love.graphics.getHeight()
- print ("Chargement du niveau")
- InitGame (1)
- print ("Chargement terminé")
- end
- function AlignOnColumn (pSprite)
- local col = math.floor ((pSprite.x + TILESIZE/2 ) / TILESIZE) + 1 -- determine la position en colonne du sprite lors de la collision
- pSprite.x = (col -1)*TILESIZE -- position du sprite en x post-collision
- end
- function AlignOnLine (pSprite)
- local lig = math.floor ((pSprite.y + TILESIZE/2 ) / TILESIZE) + 1 -- determine la position en ligne du sprite lors de la collision
- pSprite.y = (lig -1)*TILESIZE -- position du sprite en y post-collision
- end
- function updatePlayer(pPlayer, dt)
- -- mise à jour du sprite Player
- -- Locales pour la physique du sprite player
- local accel = 350
- local friction = 120
- local maxSpeed = 120
- local jumpSpeed = -225
- -- Tile under the player / Tuile sous le joueur (pour les échelles)
- local idUnder = getTileAt (pPlayer.x + TILESIZE/2, pPlayer.y + TILESIZE)
- local idOverlap= getTileAt (pPlayer.x + TILESIZE/2, pPlayer.y + TILESIZE - 1 )
- -- Stop, Jump ? / Est-ce que le héros peut sauter ou il y a une échelle au-dessus ?
- if pPlayer.isJumping and (CollideBelow(pPlayer) or isLadder(idUnder)) then
- pPlayer.isJumping = false
- pPlayer.standing = true
- AlignOnLine (pPlayer)
- end
- -- Gestion de Friction
- -- Friction en allant à droite
- if pPlayer.vx > 0 then
- pPlayer.vx = pPlayer.vx - friction*dt
- if pPlayer.vx < 0 then
- pPlayer.vx = 0
- end
- end
- -- Friction en allant à gauche
- if pPlayer.vx < 0 then
- pPlayer.vx = pPlayer.vx + friction*dt
- if pPlayer.vx > 0 then
- pPlayer.vx = 0
- end
- end
- local newAnimation = "idle" -- animation de départ du héros
- --Keyboard
- if love.keyboard.isDown("right") then
- pPlayer.vx = pPlayer.vx + accel*dt
- if pPlayer.vx > maxSpeed then pPlayer.vx = maxSpeed end
- pPlayer.flip = false
- newAnimation = "run"
- end
- if love.keyboard.isDown("left") then
- pPlayer.vx = pPlayer.vx - accel*dt
- if pPlayer.vx < - maxSpeed then pPlayer.vx = - maxSpeed end
- pPlayer.flip = true
- newAnimation = "run"
- end
- -- Check if the player overlap a ladder / On vérifie avant de sauter si le héros chevauche une échelle
- local isOnLadder = isLadder(idUnder) or isLadder (idOverlap)
- if isLadder(idOverlap) == false and isLadder(idUnder) then
- pPlayer.standing = true
- end
- -- Climb
- if isOnLadder and pPlayer.isJumping == false then
- GRAVITY = 0
- pPlayer.vy = 0
- bJumpReady = false
- end
- -- si on est au milieu de l'échelle
- if isLadder (idUnder) and isLadder (idOverlap) then
- newAnimation ="climb_idle"
- end
- -- si on monte à l'échelle
- if love.keyboard.isDown "up" and isOnLadder == true and pPlayer.isJumping == false then
- pPlayer.vy = -50
- newAnimation ="climb"
- end
- -- Jump
- if love.keyboard.isDown("up") and pPlayer.standing and bJumpReady and isLadder(idOverlap) == false then
- pPlayer.isJumping = true
- pPlayer.vy = jumpSpeed
- pPlayer.standing = false
- bJumpReady = false
- end
- --si on descend de l'échelle
- if love.keyboard.isDown("down") and isOnLadder == true then
- pPlayer.vy = 50
- newAnimation = "climb"
- end
- -- Not climbing
- if isOnLadder == false and GRAVITY == 0 and pPlayer.isJumping == false then
- GRAVITY = 500
- end
- -- On prépare le prochain saut
- if love.keyboard.isDown("up") == false and bJumpReady == false and pPlayer.standing == true then
- bJumpReady = true
- end
- pPlayer.PlayAnimations (newAnimation)
- --Move
- pPlayer.x = pPlayer.x + pPlayer.vx* dt
- pPlayer.y = pPlayer.y + pPlayer.vy* dt
- end
- function getTileAt(pX, pY)
- -- permet de retourner l'ID de la tile à la coordonnée indiqué
- local col = math.floor(pX / TILESIZE) + 1
- local lig = math.floor(pY / TILESIZE) + 1
- if col>0 and col<=#map[1] and lig>0 and lig<=#map then
- local id = string.sub(map[lig],col,col)
- return id
- end
- return 0
- end
- -- Fonctions qui détermine les collisions selon le côté du sprite
- function CollideRight(pSprite)
- local id1 = getTileAt(pSprite.x + TILESIZE, pSprite.y + 3)
- local id2 = getTileAt(pSprite.x + TILESIZE, pSprite.y + TILESIZE - 2)
- if isSolid(id1) or isSolid(id2) then return true end
- return false
- end
- function CollideLeft(pSprite)
- local id1 = getTileAt(pSprite.x-1, pSprite.y + 3)
- local id2 = getTileAt(pSprite.x-1, pSprite.y + TILESIZE - 2)
- if isSolid(id1) or isSolid(id2) then return true end
- return false
- end
- function CollideBelow(pSprite)
- local id1 = getTileAt(pSprite.x + 1, pSprite.y + TILESIZE)
- local id2 = getTileAt(pSprite.x + TILESIZE - 2, pSprite.y + TILESIZE)
- if isSolid(id1) or isSolid(id2) then return true end
- if isJumpThrough (id1) or isJumpThrough (id2) then
- local lig = math.floor ((pSprite.y + TILESIZE/2 ) / TILESIZE ) + 1
- local yLine = (lig-1) * TILESIZE
- local distance = pSprite.y - yLine
- if distance > 0 and distance < 10 then
- return true
- end
- end
- return false
- end
- function CollideAbove(pSprite)
- local id1 = getTileAt(pSprite.x + 1, pSprite.y-1)
- local id2 = getTileAt(pSprite.x + TILESIZE - 2, pSprite.y-1)
- if isSolid(id1) or isSolid(id2) then return true end
- return false
- end
- function updateSprite (pSprite, dt)
- --mise à jour des sprites
- -- Locales pour les collisons
- oldX = pSprite.X
- oldY = pSprite.Y
- -- Si le sprite est Player
- if pSprite.type == "player" then
- updatePlayer(pSprite, dt)
- end
- -- Animations
- if pSprite.currentAnimation ~= "" then
- pSprite.animationTimer = pSprite.animationTimer - dt
- if pSprite.animationTimer <= 0 then
- pSprite.frame = pSprite.frame + 1
- pSprite.animationTimer= pSprite.animationSpeed
- if pSprite.frame > #pSprite.Animations[pSprite.currentAnimation] then
- pSprite.frame = 1
- end
- end
- end
- --Collision detection
- local collide = false
- -- On the right/ A droite
- if pSprite.vx > 0 then
- collide = CollideRight (pSprite)
- end
- -- On the left/ A gauche
- if pSprite.vx < 0 then
- collide = CollideLeft (pSprite)
- end
- -- Stop !
- if collide then
- pSprite.vx = 0
- AlignOnColumn (pSprite)
- end
- collide = false
- --Above/ Au-dessus
- if pSprite.vy < 0 then
- collide = CollideAbove (pSprite)
- if collide then
- pSprite.vy = 0
- local lig = math.floor ((pSprite.y + TILESIZE/2 ) / TILESIZE) + 1 -- determine la position en ligne du sprite lors de la collision
- pSprite.y = (lig -1)*TILESIZE -- position du sprite en y post-collision
- end
- end
- --Below/ En dessous (chute)
- if pSprite.standing or pSprite.vy > 0 then
- collide = CollideBelow (pSprite)
- if collide then
- pSprite.standing = true
- pSprite.vy = 0
- AlignOnLine (pSprite)
- else
- pSprite.standing = false
- end
- end
- -- Sprite falling / mouvement de chute du sprite
- if pSprite.standing == false then
- pSprite.vy = pSprite.vy + GRAVITY * dt
- end
- end
- function love.update(dt)
- for nSprite = #lstSprites, 1, -1 do
- local sprite = lstSprites [nSprite]
- updateSprite (sprite, dt )
- end
- end
- function drawSprite (pSprite)
- local imgName = pSprite.Animations [pSprite.currentAnimation][pSprite.frame]
- local img = pSprite.images [imgName]
- local halfwdth = img:getWidth() / 2
- local halfhght = img:getHeight() / 2
- local flipcoef = 1
- if pSprite.flip then flipcoef = -1 end
- love.graphics.draw (img , pSprite.x + halfwdth, pSprite.y + halfhght, 0, 1*flipcoef, 1, halfwdth, halfhght )
- end
- function love.draw()
- -- scale x2 de l'écran
- love.graphics.scale(2,2)
- -- On parcourt la map et on la dessine
- local l,c
- for l = 1, #map do
- for c = 1, #map[1] do
- local char = string.sub (map[l], c,c)
- if tonumber(char) ~= 0 then
- if imgTiles[char] ~= nil then
- love.graphics.draw(imgTiles[char],(c-1)*TILESIZE,(l-1)*TILESIZE)
- end
- end
- end
- end
- -- On parcourt la liste des sprites et on applique la fonction qui les dessine
- for nSprite = #lstSprites, 1, -1 do
- local sprite = lstSprites [nSprite]
- drawSprite (sprite )
- end
- --Affiche l'ID de la tuile avec la souris
- local id = getTileAt(love.mouse.getX(), love.mouse.getY())
- love.graphics.print(id)
- end
- function love.keypressed(key)
- print(key)
- end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement