Browse Source

Add creep damage effect and death sound

main v1.0.0
Trevor Slocum 6 months ago
parent
commit
7cad0b3628
  1. 20
      asset/asset.go
  2. 54
      asset/map/m1.tmx
  3. 6
      asset/sound/creep_die/LICENSE
  4. BIN
      asset/sound/creep_die/creep_die.ogg
  5. 5
      component/creep.go
  6. 2
      component/sprite.go
  7. 70
      game/game.go
  8. 1
      go.mod
  9. 2
      go.sum
  10. 19
      main.go
  11. 5
      system/camera.go
  12. 28
      system/creep.go
  13. 6
      system/movement.go
  14. 2
      system/render.go
  15. 76
      world/world.go

20
asset/asset.go

@ -6,6 +6,7 @@ import ( @@ -6,6 +6,7 @@ import (
"image"
"image/color"
_ "image/png"
"io"
"github.com/hajimehoshi/ebiten/v2"
"github.com/hajimehoshi/ebiten/v2/audio"
@ -39,6 +40,8 @@ var ( @@ -39,6 +40,8 @@ var (
SoundBatHit3 *audio.Player
SoundBatHit4 *audio.Player
SoundCreepDie *audio.Player
SoundTitleMusic *audio.Player
SoundLevelMusic *audio.Player
)
@ -54,10 +57,12 @@ func LoadSounds(ctx *audio.Context) { @@ -54,10 +57,12 @@ func LoadSounds(ctx *audio.Context) {
SoundBatHit3 = LoadWAV(ctx, "sound/bat_hit/hit3.wav")
SoundBatHit4 = LoadWAV(ctx, "sound/bonk.wav")
SoundTitleMusic = LoadOGG(ctx, "sound/title_music.ogg")
SoundCreepDie = LoadOGG(ctx, "sound/creep_die/creep_die.ogg", false)
SoundTitleMusic = LoadOGG(ctx, "sound/title_music.ogg", true)
SoundTitleMusic.SetVolume(0.5)
SoundLevelMusic = LoadOGG(ctx, "sound/level_music.ogg")
SoundLevelMusic = LoadOGG(ctx, "sound/level_music.ogg", true)
SoundLevelMusic.SetVolume(0.4)
}
@ -111,7 +116,7 @@ func LoadWAV(context *audio.Context, p string) *audio.Player { @@ -111,7 +116,7 @@ func LoadWAV(context *audio.Context, p string) *audio.Player {
return player
}
func LoadOGG(context *audio.Context, p string) *audio.Player {
func LoadOGG(context *audio.Context, p string, loop bool) *audio.Player {
b := LoadBytes(p)
stream, err := vorbis.DecodeWithSampleRate(sampleRate, bytes.NewReader(b))
@ -119,7 +124,14 @@ func LoadOGG(context *audio.Context, p string) *audio.Player { @@ -119,7 +124,14 @@ func LoadOGG(context *audio.Context, p string) *audio.Player {
panic(err)
}
player, err := context.NewPlayer(audio.NewInfiniteLoop(stream, stream.Length()))
var s io.Reader
if loop {
s = audio.NewInfiniteLoop(stream, stream.Length())
} else {
s = stream
}
player, err := context.NewPlayer(s)
if err != nil {
panic(err)
}

54
asset/map/m1.tmx

@ -1,5 +1,5 @@ @@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<map version="1.5" tiledversion="1.7.2" orientation="orthogonal" renderorder="right-down" width="20" height="120" tilewidth="32" tileheight="32" infinite="0" backgroundcolor="#181818" nextlayerid="7" nextobjectid="129">
<map version="1.5" tiledversion="1.7.2" orientation="orthogonal" renderorder="right-down" width="20" height="120" tilewidth="32" tileheight="32" infinite="0" backgroundcolor="#181818" nextlayerid="7" nextobjectid="156">
<tileset firstgid="1" name="tileset" tilewidth="32" tileheight="32" tilecount="72" columns="9">
<image source="../image/tileset/tileset.png" width="288" height="256"/>
</tileset>
@ -133,9 +133,9 @@ @@ -133,9 +133,9 @@
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
33,33,32,33,2147483679,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,35,36,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,44,45,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
@ -188,7 +188,7 @@ @@ -188,7 +188,7 @@
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,23,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
@ -215,9 +215,9 @@ @@ -215,9 +215,9 @@
5,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,11,0,0,0,0,0,
0,0,0,0,25,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,23,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
@ -245,9 +245,9 @@ @@ -245,9 +245,9 @@
0,13,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,
0,0,0,0,10,0,0,0,0,0,0,0,0,0,0,0,0,0,4,11,
0,2,7,4,0,3,0,0,0,0,0,0,0,0,0,0,0,0,13,0,
5,11,18,13,5,16,23,0,0,0,0,0,0,0,53,0,3,4,3,5,
29,29,29,69,3,6,0,0,0,0,0,0,0,0,0,0,15,13,0,10,
0,52,0,54,1,9,10,0,0,0,0,0,0,0,0,4,0,7,6,19,
5,11,6,13,5,16,4,0,0,0,0,0,0,0,53,0,3,4,3,5,
29,29,29,69,3,6,13,0,0,0,0,0,0,0,0,0,15,13,0,10,
0,52,0,54,1,0,10,0,0,0,0,0,0,0,0,4,0,7,6,19,
0,61,62,63,5,3,0,0,0,0,0,0,0,0,0,13,14,16,1,28
</data>
</layer>
@ -257,14 +257,10 @@ @@ -257,14 +257,10 @@
<object id="53" gid="52" x="96" y="2816" width="32" height="32"/>
<object id="55" gid="50" x="544" y="2304" width="32" height="32"/>
<object id="56" gid="50" x="448" y="2304" width="32" height="32"/>
<object id="61" gid="50" x="160" y="1472" width="32" height="32"/>
<object id="62" gid="50" x="320" y="1536" width="32" height="32"/>
<object id="63" gid="50" x="512" y="1600" width="32" height="32"/>
<object id="64" gid="50" x="448" y="1472" width="32" height="32"/>
<object id="69" gid="52" x="0" y="1088" width="32" height="32"/>
<object id="70" gid="52" x="64" y="1088" width="32" height="32"/>
<object id="71" gid="52" x="96" y="1056" width="32" height="32"/>
<object id="72" gid="52" x="96" y="992" width="32" height="32"/>
<object id="73" gid="52" x="32" y="1152" width="32" height="32"/>
<object id="75" gid="52" x="32" y="992" width="32" height="32"/>
<object id="78" gid="50" x="608" y="1152" width="32" height="32"/>
@ -272,10 +268,8 @@ @@ -272,10 +268,8 @@
<object id="94" gid="52" x="32" y="544" width="32" height="32"/>
<object id="95" gid="52" x="64" y="576" width="32" height="32"/>
<object id="96" gid="52" x="32" y="608" width="32" height="32"/>
<object id="97" gid="50" x="608" y="768" width="32" height="32"/>
<object id="98" gid="50" x="544" y="768" width="32" height="32"/>
<object id="99" gid="50" x="544" y="832" width="32" height="32"/>
<object id="100" gid="50" x="608" y="832" width="32" height="32"/>
<object id="101" gid="50" x="416" y="192" width="32" height="32"/>
<object id="102" gid="50" x="480" y="256" width="32" height="32"/>
<object id="103" gid="50" x="576" y="320" width="32" height="32"/>
@ -300,6 +294,26 @@ @@ -300,6 +294,26 @@
<object id="126" gid="52" x="160" y="32" width="32" height="32"/>
<object id="127" gid="50" x="416" y="32" width="32" height="32"/>
<object id="128" gid="50" x="544" y="64" width="32" height="32"/>
<object id="129" gid="9" x="448" y="3360" width="32" height="32"/>
<object id="132" gid="9" x="64" y="3232" width="32" height="32"/>
<object id="133" gid="18" x="512" y="2944" width="32" height="32"/>
<object id="134" gid="9" x="32" y="2848" width="32" height="32"/>
<object id="135" gid="9" x="160" y="2848" width="32" height="32"/>
<object id="136" gid="18" x="480" y="2752" width="32" height="32"/>
<object id="138" gid="23" x="192" y="2464" width="32" height="32"/>
<object id="139" gid="9" x="320" y="2272" width="32" height="32"/>
<object id="140" gid="9" x="512" y="2208" width="32" height="32"/>
<object id="141" gid="9" x="192" y="2080" width="32" height="32"/>
<object id="142" gid="18" x="64" y="1856" width="32" height="32"/>
<object id="143" gid="18" x="480" y="1696" width="32" height="32"/>
<object id="145" gid="23" x="384" y="1600" width="32" height="32"/>
<object id="146" gid="9" x="448" y="1536" width="32" height="32"/>
<object id="148" gid="9" x="352" y="1280" width="32" height="32"/>
<object id="150" gid="23" x="160" y="1248" width="32" height="32"/>
<object id="151" gid="23" x="160" y="768" width="32" height="32"/>
<object id="152" gid="18" x="384" y="544" width="32" height="32"/>
<object id="153" gid="9" x="96" y="352" width="32" height="32"/>
<object id="154" gid="23" x="448" y="672" width="32" height="32"/>
</objectgroup>
<objectgroup color="#ce0003" id="5" name="HAZARDS">
<object id="1" x="486" y="3392" width="16" height="27"/>
@ -309,8 +323,7 @@ @@ -309,8 +323,7 @@
<object id="5" x="38" y="3602" width="15" height="27"/>
<object id="6" x="6" y="3712" width="17" height="27"/>
<object id="7" x="34" y="3693" width="21" height="34"/>
<object id="8" x="69" y="3725" width="14" height="12"/>
<object id="9" x="195" y="3722" width="22" height="16"/>
<object id="9" x="198" y="3730" width="15" height="26"/>
<object id="10" x="169" y="3687" width="11" height="15"/>
<object id="11" x="136" y="3648" width="12" height="19"/>
<object id="12" x="102" y="3698" width="15" height="27"/>
@ -318,7 +331,6 @@ @@ -318,7 +331,6 @@
<object id="14" x="137" y="3751" width="11" height="15"/>
<object id="15" x="128" y="3776" width="24" height="22"/>
<object id="16" x="200" y="3776" width="12" height="19"/>
<object id="17" x="173" y="3790" width="9" height="8"/>
<object id="18" x="134" y="3808" width="17" height="27"/>
<object id="19" x="169" y="3815" width="11" height="15"/>
<object id="20" x="550" y="3730" width="15" height="27"/>
@ -346,8 +358,6 @@ @@ -346,8 +358,6 @@
<object id="43" x="33" y="1008" width="40" height="20"/>
<object id="44" x="52" y="1022" width="35" height="12"/>
<object id="45" x="6" y="2656" width="17" height="27"/>
<object id="46" x="67" y="2826" width="24" height="16"/>
<object id="47" x="129" y="2769" width="28" height="9"/>
<object id="82" x="0" y="1376" width="7" height="64"/>
<object id="83" x="38" y="1376" width="17" height="28"/>
<object id="84" x="66" y="1453" width="21" height="33"/>
@ -358,7 +368,7 @@ @@ -358,7 +368,7 @@
<object id="89" x="75" y="1557" width="8" height="17"/>
<object id="90" x="422" y="1714" width="15" height="27"/>
<object id="91" x="390" y="1952" width="17" height="27"/>
<object id="92" x="451" y="1898" width="22" height="16"/>
<object id="93" x="617" y="1863" width="11" height="15"/>
<object id="155" x="49" y="176" width="24" height="13"/>
</objectgroup>
</map>

6
asset/sound/creep_die/LICENSE

@ -0,0 +1,6 @@ @@ -0,0 +1,6 @@
This sound clip was made available for use by CGEffex under the
Creative Commons Attribution Noncommercial License.
Source: https://freesound.org/people/Timbre/sounds/156522/
License: http://creativecommons.org/licenses/by-nc/3.0/

BIN
asset/sound/creep_die/creep_die.ogg

Binary file not shown.

5
component/creep.go

@ -8,6 +8,7 @@ import ( @@ -8,6 +8,7 @@ import (
)
type CreepComponent struct {
Type int
Active bool
Health int
@ -26,7 +27,9 @@ type CreepComponent struct { @@ -26,7 +27,9 @@ type CreepComponent struct {
const (
CreepSnowblower = iota + 1
CreepSnowmanHead
CreepSmallRock
CreepMediumRock
CreepLargeRock
)
var CreepComponentID = ECS.NewComponentID()

2
component/sprite.go

@ -26,6 +26,8 @@ type SpriteComponent struct { @@ -26,6 +26,8 @@ type SpriteComponent struct {
LastFrame time.Time
NumFrames int
DamageTicks int
OverrideColorScale bool
ColorScale float64
}

70
game/game.go

@ -2,8 +2,6 @@ package game @@ -2,8 +2,6 @@ package game
import (
"image/color"
"log"
"math"
"math/rand"
"os"
"sync"
@ -17,32 +15,8 @@ import ( @@ -17,32 +15,8 @@ import (
"code.rocketnine.space/tslocum/brownboxbatman/world"
"github.com/hajimehoshi/ebiten/v2"
"github.com/hajimehoshi/ebiten/v2/audio"
"golang.org/x/text/language"
"golang.org/x/text/message"
)
var numberPrinter = message.NewPrinter(language.English)
var startButtons = []ebiten.StandardGamepadButton{
ebiten.StandardGamepadButtonRightBottom,
ebiten.StandardGamepadButtonRightRight,
ebiten.StandardGamepadButtonRightLeft,
ebiten.StandardGamepadButtonRightTop,
ebiten.StandardGamepadButtonFrontTopLeft,
ebiten.StandardGamepadButtonFrontTopRight,
ebiten.StandardGamepadButtonFrontBottomLeft,
ebiten.StandardGamepadButtonFrontBottomRight,
ebiten.StandardGamepadButtonCenterLeft,
ebiten.StandardGamepadButtonCenterRight,
ebiten.StandardGamepadButtonLeftStick,
ebiten.StandardGamepadButtonRightStick,
ebiten.StandardGamepadButtonLeftBottom,
ebiten.StandardGamepadButtonLeftRight,
ebiten.StandardGamepadButtonLeftLeft,
ebiten.StandardGamepadButtonLeftTop,
ebiten.StandardGamepadButtonCenterCenter,
}
const sampleRate = 44100
// game is an isometric demo game.
@ -109,15 +83,12 @@ func (g *game) changeMap(filePath string) { @@ -109,15 +83,12 @@ func (g *game) changeMap(filePath string) {
// Layout is called when the game's layout changes.
func (g *game) Layout(w, h int) (int, int) {
//s := ebiten.DeviceScaleFactor()
//w, h := int(s*float64(outsideWidth)), int(s*float64(outsideHeight))
if !world.World.NativeResolution {
w, h = 640, 480
}
if w != g.w || h != g.h {
world.World.ScreenW, world.World.ScreenH = w, h
g.w, g.h = w, h
//g.messageSystem.SizeUpdated()
}
return g.w, g.h
}
@ -167,37 +138,17 @@ func (g *game) addSystems() { @@ -167,37 +138,17 @@ func (g *game) addSystems() {
ecs := ECS
g.movementSystem = system.NewMovementSystem()
ecs.AddSystem(system.NewPlayerMoveSystem(world.World.Player, g.movementSystem))
ecs.AddSystem(system.NewplayerFireSystem())
ecs.AddSystem(g.movementSystem)
ecs.AddSystem(system.NewCreepSystem())
ecs.AddSystem(system.NewCameraSystem())
ecs.AddSystem(system.NewRailSystem())
/*ecs.AddSystem(system.NewFireWeaponSystem(world.World.Player))
ecs.AddSystem(system.NewRenderBackgroundSystem())*/
g.renderSystem = system.NewRenderSystem()
ecs.AddSystem(g.renderSystem)
/*g.messageSystem = system.NewRenderMessageSystem(world.World.Player)
ecs.AddSystem(g.messageSystem)*/
ecs.AddSystem(system.NewRenderMessageSystem())
ecs.AddSystem(system.NewRenderDebugTextSystem(world.World.Player))
ecs.AddSystem(system.NewProfileSystem(world.World.Player))
// TODO
/*
world.World.MessageVisible = true
world.World.MessageText = "BOMB"
world.World.MessageText = "V & set it with X button."*/
}
func (g *game) loadAssets() error {
@ -206,27 +157,6 @@ func (g *game) loadAssets() error { @@ -206,27 +157,6 @@ func (g *game) loadAssets() error {
return nil
}
func (g *game) WarpTo(x, y float64) {
position := ECS.Component(world.World.Player, component.PositionComponentID).(*component.PositionComponent)
position.X, position.Y = x, y
log.Printf("Warped to %.2f,%.2f", x, y)
}
func (g *game) Exit() {
os.Exit(0)
}
func angle(x1, y1, x2, y2 float64) float64 {
return math.Atan2(y1-y2, x1-x2)
}
func deltaXY(x1, y1, x2, y2 float64) (dx float64, dy float64) {
dx, dy = x1-x2, y1-y2
if dx < 0 {
dx *= -1
}
if dy < 0 {
dy *= -1
}
return dx, dy
}

1
go.mod

@ -6,7 +6,6 @@ require ( @@ -6,7 +6,6 @@ require (
code.rocketnine.space/tslocum/gohan v0.0.0-20211229205912-263cd48bca66
github.com/hajimehoshi/ebiten/v2 v2.2.3
github.com/lafriks/go-tiled v0.6.0
golang.org/x/text v0.3.7
)
require (

2
go.sum

@ -78,8 +78,6 @@ golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9sn @@ -78,8 +78,6 @@ golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9sn
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk=
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=

19
main.go

@ -43,25 +43,6 @@ func main() { @@ -43,25 +43,6 @@ func main() {
g.Exit()
}()
/*go func() {
s := bufio.NewScanner(os.Stdin)
for s.Scan() {
input := s.Text()
if strings.HasPrefix(input, "warp ") {
pos := strings.Split(input[5:], ",")
if len(pos) == 2 {
posX, err := strconv.Atoi(pos[0])
if err == nil {
posY, err := strconv.Atoi(pos[1])
if err == nil {
g.WarpTo(float64(posX), float64(posY))
}
}
}
}
}
}()*/
err = ebiten.RunGame(g)
if err != nil {
log.Fatal(err)

5
system/camera.go

@ -1,6 +1,8 @@ @@ -1,6 +1,8 @@
package system
import (
"math"
"code.rocketnine.space/tslocum/brownboxbatman/component"
"code.rocketnine.space/tslocum/brownboxbatman/world"
"code.rocketnine.space/tslocum/gohan"
@ -36,6 +38,9 @@ func (s *CameraSystem) Update(ctx *gohan.Context) error { @@ -36,6 +38,9 @@ func (s *CameraSystem) Update(ctx *gohan.Context) error {
world.World.CamMoving = world.World.CamY > 0
if world.World.CamMoving {
world.World.CamY -= CameraMoveSpeed
} else {
world.SetMessage("GAME OVER\n\nYOU WIN!", math.MaxInt)
world.World.GameOver = true
}
return nil
}

28
system/creep.go

@ -1,7 +1,9 @@ @@ -1,7 +1,9 @@
package system
import (
"code.rocketnine.space/tslocum/brownboxbatman/asset"
"code.rocketnine.space/tslocum/brownboxbatman/component"
. "code.rocketnine.space/tslocum/brownboxbatman/ecs"
"code.rocketnine.space/tslocum/brownboxbatman/entity"
"code.rocketnine.space/tslocum/brownboxbatman/world"
"code.rocketnine.space/tslocum/gohan"
@ -41,6 +43,9 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error { @@ -41,6 +43,9 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error {
if creep.Health <= 0 {
for i, e := range world.World.CreepEntities {
if e == ctx.Entity {
asset.SoundCreepDie.Rewind()
asset.SoundCreepDie.Play()
world.World.CreepRects = append(world.World.CreepRects[:i], world.World.CreepRects[i+1:]...)
world.World.CreepEntities = append(world.World.CreepEntities[:i], world.World.CreepEntities[i+1:]...)
ctx.RemoveEntity()
@ -82,7 +87,7 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error { @@ -82,7 +87,7 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error {
}
if creep.FireTicks == 0 {
for i := 0; i < 8; i++ {
for i := 0; i < creep.FireAmount; i++ {
vx, vy := randVelocity()
if creep.Rand.Intn(2) == 0 {
@ -95,10 +100,27 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error { @@ -95,10 +100,27 @@ func (s *CreepSystem) Update(ctx *gohan.Context) error {
}
creep.FireTicks = creep.FireRate
}
creep.FireTicks--
// TODO update colorM based on damageticks
if creep.DamageTicks > 0 {
creep.DamageTicks--
sprite := ECS.Component(ctx.Entity, component.SpriteComponentID)
if sprite != nil {
sp := sprite.(*component.SpriteComponent)
if creep.DamageTicks > 0 {
if creep.DamageTicks%2 == 0 {
sp.ColorScale = 100
} else {
sp.ColorScale = .01
}
sp.OverrideColorScale = true
} else {
sp.OverrideColorScale = false
}
}
}
creep.FireTicks--
return nil
}

6
system/movement.go

@ -98,6 +98,10 @@ func (s *MovementSystem) Update(ctx *gohan.Context) error { @@ -98,6 +98,10 @@ func (s *MovementSystem) Update(ctx *gohan.Context) error {
world.World.PlayerX, world.World.PlayerY = position.X, position.Y
// Check player hazard collision.
if world.World.NoClip {
return nil
}
playerRect := image.Rect(int(position.X), int(position.Y), int(position.X+world.World.PlayerWidth), int(position.Y+world.World.PlayerHeight))
for _, r := range world.World.HazardRects {
if playerRect.Overlaps(r) {
@ -157,7 +161,7 @@ func (s *MovementSystem) Update(ctx *gohan.Context) error { @@ -157,7 +161,7 @@ func (s *MovementSystem) Update(ctx *gohan.Context) error {
creep := ECS.Component(world.World.CreepEntities[i], component.CreepComponentID).(*component.CreepComponent)
if creep.Active {
creep.Health--
creep.DamageTicks = 144 / 2
creep.DamageTicks = 6
ctx.RemoveEntity()
return nil
}

2
system/render.go

@ -151,7 +151,7 @@ func (s *RenderSystem) Draw(ctx *gohan.Context, screen *ebiten.Image) error { @@ -151,7 +151,7 @@ func (s *RenderSystem) Draw(ctx *gohan.Context, screen *ebiten.Image) error {
screen.DrawImage(asset.ImgTitle2, s.op)
}
timeC := 144.0 * 4.35
timeC := 144.0 * 4.3
if world.World.GameStartedTicks > int(timeC) {
pct = float64(world.World.GameStartedTicks-int(timeC)) / (144 * 0.5)
if pct > 1 {

76
world/world.go

@ -16,17 +16,6 @@ import ( @@ -16,17 +16,6 @@ import (
"github.com/lafriks/go-tiled"
)
const (
SoundGunshot = iota
SoundVampireDie1
SoundVampireDie2
SoundBat
SoundPlayerHurt
SoundPlayerDie
SoundPickup
SoundMunch
)
var World = &GameWorld{
CamScale: 1,
CamMoving: true,
@ -222,12 +211,25 @@ func LoadMap(filePath string) { @@ -222,12 +211,25 @@ func LoadMap(filePath string) {
}
} else if grp.Name == "HAZARDS" {
for _, obj := range grp.Objects {
World.HazardRects = append(World.HazardRects, ObjectToRect(obj))
r := ObjectToRect(obj)
r.Min.Y += 32
r.Max.Y += 32
World.HazardRects = append(World.HazardRects, r)
}
} else if grp.Name == "CREEPS" {
for _, obj := range grp.Objects {
c := NewCreep(component.CreepSnowblower, int64(obj.ID), float64(obj.X), float64(obj.Y))
World.CreepRects = append(World.CreepRects, ObjectToRect(obj))
creepType := component.CreepSnowblower
switch obj.GID {
case 9:
creepType = component.CreepSmallRock
case 18:
creepType = component.CreepMediumRock
case 23:
creepType = component.CreepLargeRock
}
r := ObjectToRect(obj)
c := NewCreep(creepType, int64(obj.ID), float64(r.Min.X), float64(r.Min.Y))
World.CreepRects = append(World.CreepRects, r)
World.CreepEntities = append(World.CreepEntities, c)
}
}
@ -236,6 +238,7 @@ func LoadMap(filePath string) { @@ -236,6 +238,7 @@ func LoadMap(filePath string) {
func ObjectToRect(o *tiled.Object) image.Rectangle {
x, y, w, h := int(o.X), int(o.Y), int(o.Width), int(o.Height)
y -= 32
return image.Rect(x, y, x+w, y+h)
}
@ -332,17 +335,39 @@ func NewCreep(creepType int, creepID int64, x float64, y float64) gohan.Entity { @@ -332,17 +335,39 @@ func NewCreep(creepType int, creepID int64, x float64, y float64) gohan.Entity {
Y: y,
})
if creepType == component.CreepSnowmanHead {
if creepType == component.CreepSmallRock {
ECS.AddComponent(creep, &component.VelocityComponent{})
ECS.AddComponent(creep, &component.CreepComponent{
Health: 128,
FireAmount: 1,
FireRate: 144 * 1.5,
Type: creepType,
Health: 32,
FireAmount: 2,
FireRate: 144 * 1,
Rand: rand.New(rand.NewSource(creepID)),
})
} else {
} else if creepType == component.CreepMediumRock {
ECS.AddComponent(creep, &component.VelocityComponent{})
ECS.AddComponent(creep, &component.CreepComponent{
Type: creepType,
Health: 64,
FireAmount: 4,
FireRate: 144 * 1,
Rand: rand.New(rand.NewSource(creepID)),
})
} else if creepType == component.CreepLargeRock {
ECS.AddComponent(creep, &component.VelocityComponent{})
ECS.AddComponent(creep, &component.CreepComponent{
Type: creepType,
Health: 96,
FireAmount: 8,
FireRate: 144,
Rand: rand.New(rand.NewSource(creepID)),
})
} else { // CreepSnowblower
ECS.AddComponent(creep, &component.CreepComponent{
Type: creepType,
Health: 64,
FireAmount: 8,
FireRate: 144 / 4,
@ -350,10 +375,15 @@ func NewCreep(creepType int, creepID int64, x float64, y float64) gohan.Entity { @@ -350,10 +375,15 @@ func NewCreep(creepType int, creepID int64, x float64, y float64) gohan.Entity {
})
}
img := asset.ImgBat
if creepType == component.CreepSnowmanHead {
img = World.TileImages[8]
} else if creepType == component.CreepSnowblower {
// TODO handle flipped creep
var img *ebiten.Image
if creepType == component.CreepSmallRock {
img = World.TileImages[9]
} else if creepType == component.CreepMediumRock {
img = World.TileImages[18]
} else if creepType == component.CreepLargeRock {
img = World.TileImages[23]
} else { // CreepSnowblower
img = World.TileImages[50]
}
ECS.AddComponent(creep, &component.SpriteComponent{

Loading…
Cancel
Save