Spring

From CC Wiki
Jump to navigationJump to search

Springs in Vanilla CC

Springs are a mechanic in Celeste Classic and a lot of its Mods.

Springs can be found in several levels in the vanilla game, including 300m and 800m. They can be triggered by landing on one, which will launch madeline upwards.


Vanilla Internal data

Springs give player momentum and move the player a little bit away from them. The player's Y speed is always set to -3, And its X speed is multiplied by 0.2. Its Y position is also set to be 4 Pixels above the spring, before any speed is given.

You can see the movement being triggered here:

hit.move(0,this.y-hit.y-4,1)
hit.spd.x*=0.2
hit.spd.y=-3

Springs also break fall_floor (crumbles) that are below them, to avoid floating springs.

Once hit, springs become inactive for 10 frames, and during this time its sprite is set to sprite 19, showing the spring being depressed into the ground. After this time is over, it returns to its previous state.


Spring object code in Vanilla CC

spring = {
  tile=18,
  init=function(this)
    this.hide_in=0
    this.hide_for=0
  end,
  update=function(this)
    if this.hide_for>0 then
      this.hide_for-=1
      if this.hide_for<=0 then
        this.spr=18
        this.delay=0
      end
    elseif this.spr==18 then
      local hit = this.collide(player,0,0)
      if hit ~=nil and hit.spd.y>=0 then
        this.spr=19
        hit.y=this.y-4
        hit.spd.x*=0.2
        hit.spd.y=-3
        hit.djump=max_djump
        this.delay=10
        init_object(smoke,this.x,this.y)
        
        -- breakable below us
        local below=this.collide(fall_floor,0,1)
        if below~=nil then
          break_fall_floor(below)
        end
        
        psfx(8)
      end
    elseif this.delay>0 then
      this.delay-=1
      if this.delay<=0 then 
        this.spr=18 
      end
    end
    -- begin hiding
    if this.hide_in>0 then
      this.hide_in-=1
      if this.hide_in<=0 then
        this.hide_for=60
        this.spr=0
      end
    end
  end
}


Springs in EverCore

Springs in the EverCore CC Modbase differ slightly. Minus the smaller token size, they also support Left and Right directions. When sprite 19 is placed on the map next to a ground tile, Once the cart is run, It will automatically stick to that wall. On hit, it will bounce the player in the opposite direction. Vertical facing springs (Placed with sprite 18) are still the same as in vanilla


EverCore Internal data

The amount of speed and movement that vertical facing springs give the player is exactly the same as they were in Vanilla CC, But with smoother animation, and the ability to place left and right facing springs. A Horizontal spring, When placed, Will check in each direction if there is a ground tile or other solid object there. It starts with checking LEFT, meaning that if there is a wall or solid object on both sides of the spring, it will face Right.

The amount of speed that a horizontal spring gives you is a fixed number, determined by the springs facing direction. It will always give you 3 speed in the direction it is facing, and -1.5 y speed. It will also move you 4 pixels away from the spring, in its facing direction as well.

The animation of the spring has also changed. Now, The spring has a "Delta" Value, which determines its offset when drawing the sprite. On hit, Its "Delta" Value is set to 8, moving it into the ground by 4 pixels. It remains at four pixels down for 2 frames, and it slowly returns to its original position after 4 more frames. During this 6 frame window, the spring cannot be hit again. The same animation happens to horizontal springs, but they move towards the wall they are stuck to, instead of the ground below.


Spring object code in EverCore

spring={
 init=function(this)
  this.delta=0
  this.dir=this.spr==18 and 0 or this.is_solid(-1,0) and 1 or -1
  this.show=true
  this.layer=-1
 end,
 update=function(this)
  this.delta=this.delta*0.75
  local hit=this.player_here()
  
  if this.show and hit and this.delta<=1 then
   if this.dir==0 then
    hit.move(0,this.y-hit.y-4,1)
    hit.spd.x*=0.2
    hit.spd.y=-3
   else
    hit.move(this.x+this.dir*4-hit.x,0,1)
    hit.spd=vector(this.dir*3,-1.5)
   end
   hit.dash_time=0
   hit.dash_effect_time=0
   hit.djump=max_djump
   this.delta=8
   psfx"8"
   this.init_smoke()
   
   break_fall_floor(this.check(fall_floor,-this.dir,this.dir==0 and 1 or 0))
  end
 end,
 draw=function(this)
  if this.show then
   local delta=min(flr(this.delta),4)
   if this.dir==0 then
    sspr(16,8,8,8,this.x,this.y+delta)
   else
    spr(19,this.dir==-1 and this.x+delta or this.x,this.y,1-delta/8,1,this.dir==1)
   end
  end
end
}

Note the object's smaller code size, while having more features then its vanilla counterpart.