Remove pointers for concurrency
parent
e20133d5d0
commit
4882cdedf5
|
@ -0,0 +1,15 @@
|
||||||
|
{
|
||||||
|
// Use IntelliSense to learn about possible attributes.
|
||||||
|
// Hover to view descriptions of existing attributes.
|
||||||
|
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Launch Package",
|
||||||
|
"type": "go",
|
||||||
|
"request": "launch",
|
||||||
|
"mode": "auto",
|
||||||
|
"program": "${workspaceFolder}"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
|
@ -1,5 +1,6 @@
|
||||||
game.title = "Project Ely"
|
game.title = "Project Ely"
|
||||||
game.framerate = 60.0
|
game.framerate = 60.0
|
||||||
|
|
||||||
|
log.utcTime = false
|
||||||
log.file = "output.log"
|
log.file = "output.log"
|
||||||
log.writeToFile = false
|
log.writeToFile = false
|
||||||
|
|
|
@ -9,6 +9,7 @@ import (
|
||||||
var defaultConfig gosimpleconf.ConfigMap = gosimpleconf.ConfigMap{
|
var defaultConfig gosimpleconf.ConfigMap = gosimpleconf.ConfigMap{
|
||||||
"game.title": "Project Ely",
|
"game.title": "Project Ely",
|
||||||
"game.framerate": "60.0",
|
"game.framerate": "60.0",
|
||||||
|
"log.utcTime": "false",
|
||||||
"log.writeToFile": "false",
|
"log.writeToFile": "false",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -9,19 +9,24 @@ import (
|
||||||
|
|
||||||
type logWriter struct {
|
type logWriter struct {
|
||||||
writeToFile bool
|
writeToFile bool
|
||||||
|
utcTime bool
|
||||||
logFile *os.File
|
logFile *os.File
|
||||||
}
|
}
|
||||||
|
|
||||||
func (w *logWriter) Write(bytes []byte) (int, error) {
|
func (w *logWriter) Write(bytes []byte) (int, error) {
|
||||||
t := time.Now().UTC().Format(time.RFC3339)
|
t := time.Now()
|
||||||
return fmt.Fprintf(w.logFile, "%v %v", t, string(bytes))
|
if w.utcTime {
|
||||||
|
t = t.UTC()
|
||||||
|
}
|
||||||
|
format := t.Format(time.RFC3339)
|
||||||
|
return fmt.Fprintf(w.logFile, "%v %v", format, string(bytes))
|
||||||
}
|
}
|
||||||
|
|
||||||
func (w *logWriter) Cleanup() {
|
func (w *logWriter) Cleanup() {
|
||||||
defer w.logFile.Close()
|
defer w.logFile.Close()
|
||||||
}
|
}
|
||||||
|
|
||||||
func SetupLogging(writeToFile bool, logFilename string) (*logWriter, error) {
|
func SetupLogging(writeToFile bool, utcTime bool, logFilename string) (*logWriter, error) {
|
||||||
var err error
|
var err error
|
||||||
log.SetFlags(0)
|
log.SetFlags(0)
|
||||||
|
|
||||||
|
@ -35,6 +40,7 @@ func SetupLogging(writeToFile bool, logFilename string) (*logWriter, error) {
|
||||||
|
|
||||||
writer := &logWriter{
|
writer := &logWriter{
|
||||||
writeToFile: writeToFile,
|
writeToFile: writeToFile,
|
||||||
|
utcTime: utcTime,
|
||||||
logFile: logFile,
|
logFile: logFile,
|
||||||
}
|
}
|
||||||
log.SetOutput(writer)
|
log.SetOutput(writer)
|
||||||
|
|
|
@ -6,7 +6,7 @@ import "github.com/veandco/go-sdl2/sdl"
|
||||||
// Since this is only a 2D game with SDL, the projection is relatively simple: window + camera = world.
|
// Since this is only a 2D game with SDL, the projection is relatively simple: window + camera = world.
|
||||||
// https://gamedev.stackexchange.com/a/123844
|
// https://gamedev.stackexchange.com/a/123844
|
||||||
type camera struct {
|
type camera struct {
|
||||||
pos *sdl.Point
|
pos sdl.Point
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewCamera() *camera {
|
func NewCamera() *camera {
|
||||||
|
|
|
@ -5,7 +5,7 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
type SpriteAnimation interface {
|
type SpriteAnimation interface {
|
||||||
Draw(frame int, worldPosition *sdl.Point, angle float64, center *sdl.Point, flip sdl.RendererFlip) error
|
Draw(frame int, worldPosition sdl.Point, angle float64, center sdl.Point, flip sdl.RendererFlip) error
|
||||||
}
|
}
|
||||||
|
|
||||||
// An entityAnimation will take a SpriteAnimation and may manipulate it somehow (e.g. flipped for walking the other direction)
|
// An entityAnimation will take a SpriteAnimation and may manipulate it somehow (e.g. flipped for walking the other direction)
|
||||||
|
@ -15,7 +15,7 @@ type entityAnimation struct {
|
||||||
speed int
|
speed int
|
||||||
length int
|
length int
|
||||||
angle float64
|
angle float64
|
||||||
center *sdl.Point
|
center sdl.Point
|
||||||
flip sdl.RendererFlip
|
flip sdl.RendererFlip
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -24,11 +24,11 @@ func NewEntityAnimation(
|
||||||
speed int,
|
speed int,
|
||||||
length int,
|
length int,
|
||||||
angle float64,
|
angle float64,
|
||||||
center *sdl.Point,
|
center sdl.Point,
|
||||||
flip sdl.RendererFlip,
|
flip sdl.RendererFlip,
|
||||||
) *entityAnimation {
|
) entityAnimation {
|
||||||
|
|
||||||
e := entityAnimation{
|
return entityAnimation{
|
||||||
spriteAnimation: spriteAnimation,
|
spriteAnimation: spriteAnimation,
|
||||||
speed: speed,
|
speed: speed,
|
||||||
length: length,
|
length: length,
|
||||||
|
@ -36,18 +36,23 @@ func NewEntityAnimation(
|
||||||
center: center,
|
center: center,
|
||||||
flip: flip,
|
flip: flip,
|
||||||
}
|
}
|
||||||
|
|
||||||
return &e
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *entityAnimation) Draw(frame int, windowPosition *sdl.Point) error {
|
func (e entityAnimation) Draw(frame int, windowPosition sdl.Point) error {
|
||||||
return e.spriteAnimation.Draw(frame, windowPosition, e.angle, e.center, e.flip)
|
return e.spriteAnimation.Draw(frame, windowPosition, e.angle, e.center, e.flip)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *entityAnimation) GetSpeed() int {
|
func (e entityAnimation) GetSpeed() int {
|
||||||
return e.speed
|
return e.speed
|
||||||
}
|
}
|
||||||
|
|
||||||
func DefineAnimations() {
|
func DefineAnimations() {
|
||||||
DefinePenguinAnimations()
|
DefinePenguinAnimations()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func getCenter(dimensions sdl.Point) sdl.Point {
|
||||||
|
x := dimensions.X / 2
|
||||||
|
y := dimensions.Y / 2
|
||||||
|
|
||||||
|
return sdl.Point{X: x, Y: y}
|
||||||
|
}
|
||||||
|
|
|
@ -5,7 +5,7 @@ import (
|
||||||
"github.com/veandco/go-sdl2/sdl"
|
"github.com/veandco/go-sdl2/sdl"
|
||||||
)
|
)
|
||||||
|
|
||||||
var PenguinAnimations map[int]*entityAnimation
|
var PenguinAnimations map[int]entityAnimation
|
||||||
|
|
||||||
const (
|
const (
|
||||||
PENGUIN_WALK_RIGHT int = iota
|
PENGUIN_WALK_RIGHT int = iota
|
||||||
|
@ -29,21 +29,21 @@ func DefinePenguinAnimations() {
|
||||||
var (
|
var (
|
||||||
dimensions sdl.Point
|
dimensions sdl.Point
|
||||||
offset sdl.Point
|
offset sdl.Point
|
||||||
center *sdl.Point
|
center sdl.Point
|
||||||
length int
|
length int
|
||||||
speed int
|
speed int
|
||||||
border int
|
border int
|
||||||
)
|
)
|
||||||
|
|
||||||
dimensions = sdl.Point{X: 13, Y: 17}
|
dimensions = sdl.Point{X: 13, Y: 17}
|
||||||
PenguinAnimations = make(map[int]*entityAnimation)
|
PenguinAnimations = make(map[int]entityAnimation)
|
||||||
|
|
||||||
// Walking Right is in the spritesheet.
|
// Walking Right is in the spritesheet.
|
||||||
speed = 5
|
speed = 5
|
||||||
offset = sdl.Point{X: 0, Y: 1}
|
offset = sdl.Point{X: 0, Y: 1}
|
||||||
length = 5
|
length = 5
|
||||||
border = 1 // optional border around each sprite
|
border = 1 // optional border around each sprite
|
||||||
center = nil // center is for rotation, nil will default to w/2 h/2
|
center = getCenter(dimensions) // center is for rotation, nil will default to w/2 h/2
|
||||||
walkRight := sprite.NewAnimation(filename, dimensions, offset, length, border)
|
walkRight := sprite.NewAnimation(filename, dimensions, offset, length, border)
|
||||||
PenguinAnimations[PENGUIN_WALK_RIGHT] = NewEntityAnimation(walkRight, speed, length, 0, center, sdl.FLIP_NONE)
|
PenguinAnimations[PENGUIN_WALK_RIGHT] = NewEntityAnimation(walkRight, speed, length, 0, center, sdl.FLIP_NONE)
|
||||||
|
|
||||||
|
|
|
@ -6,7 +6,7 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
type EntityAnimation interface {
|
type EntityAnimation interface {
|
||||||
Draw(step int, windowPosition *sdl.Point) error
|
Draw(step int, windowPosition sdl.Point) error
|
||||||
GetSpeed() int
|
GetSpeed() int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,12 +21,12 @@ const (
|
||||||
// The following are axis direction vectors based on world coordinates.
|
// The following are axis direction vectors based on world coordinates.
|
||||||
// UP/DOWN is intentionally UP = positive (which is different from window coordinates)
|
// UP/DOWN is intentionally UP = positive (which is different from window coordinates)
|
||||||
var (
|
var (
|
||||||
VEC_LEFT = &vector.Vec2F{X: -1, Y: 0}
|
VEC_LEFT = vector.Vec2F{X: -1, Y: 0}
|
||||||
VEC_RIGHT = &vector.Vec2F{X: 1, Y: 0}
|
VEC_RIGHT = vector.Vec2F{X: 1, Y: 0}
|
||||||
VEC_UP = &vector.Vec2F{X: 0, Y: 1}
|
VEC_UP = vector.Vec2F{X: 0, Y: 1}
|
||||||
VEC_DOWN = &vector.Vec2F{X: 0, Y: -1}
|
VEC_DOWN = vector.Vec2F{X: 0, Y: -1}
|
||||||
|
|
||||||
VEC_DIRECTIONS = []*vector.Vec2F{
|
VEC_DIRECTIONS = []vector.Vec2F{
|
||||||
// Prefer left/right animations by checking them first in the list
|
// Prefer left/right animations by checking them first in the list
|
||||||
VEC_LEFT,
|
VEC_LEFT,
|
||||||
VEC_RIGHT,
|
VEC_RIGHT,
|
||||||
|
@ -35,7 +35,7 @@ var (
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
func determineClosestDirection(velocity *vector.Vec2F) int {
|
func determineClosestDirection(velocity vector.Vec2F) int {
|
||||||
closest := DIR_RIGHT
|
closest := DIR_RIGHT
|
||||||
max := 0.0
|
max := 0.0
|
||||||
buffer := 0.5 // This buffer lets us stick to the left/right animations for diagonal movement
|
buffer := 0.5 // This buffer lets us stick to the left/right animations for diagonal movement
|
||||||
|
|
|
@ -20,27 +20,25 @@ type penguin struct {
|
||||||
updateAnimation bool // if false, don't change the animation
|
updateAnimation bool // if false, don't change the animation
|
||||||
|
|
||||||
// Physical parameters
|
// Physical parameters
|
||||||
worldPosition *vector.Vec2F // where is the center of this object
|
worldPosition vector.Vec2F // where is the center of this object
|
||||||
velocity *vector.Vec2F // movement direction to be applied each tick
|
velocity vector.Vec2F // movement direction to be applied each tick
|
||||||
speed float64 // movement magnitude to multiply with the velocity
|
speed float64 // movement magnitude to multiply with the velocity
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewPenguin(renderer *sdl.Renderer) *penguin {
|
func NewPenguin(renderer *sdl.Renderer) penguin {
|
||||||
position := vector.Vec2F{}
|
position := vector.Vec2F{}
|
||||||
velocity := vector.Vec2F{}
|
velocity := vector.Vec2F{}
|
||||||
speed := 1.0
|
speed := 1.0
|
||||||
|
|
||||||
p := penguin{
|
return penguin{
|
||||||
currentAnimation: animation.PenguinAnimations[animation.PENGUIN_DEFAULT],
|
currentAnimation: animation.PenguinAnimations[animation.PENGUIN_DEFAULT],
|
||||||
animationStep: 0,
|
animationStep: 0,
|
||||||
direction: DIR_RIGHT,
|
direction: DIR_RIGHT,
|
||||||
|
|
||||||
worldPosition: &position,
|
worldPosition: position,
|
||||||
speed: speed,
|
speed: speed,
|
||||||
velocity: &velocity,
|
velocity: velocity,
|
||||||
}
|
}
|
||||||
|
|
||||||
return &p
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *penguin) Draw() error {
|
func (p *penguin) Draw() error {
|
||||||
|
@ -48,7 +46,7 @@ func (p *penguin) Draw() error {
|
||||||
|
|
||||||
// TODO
|
// TODO
|
||||||
//windowPosition := worldPosToWindowPos()
|
//windowPosition := worldPosToWindowPos()
|
||||||
windowPosition := &sdl.Point{
|
windowPosition := sdl.Point{
|
||||||
X: int32(math.Round(p.worldPosition.X)),
|
X: int32(math.Round(p.worldPosition.X)),
|
||||||
Y: int32(math.Round(-1 * p.worldPosition.Y)),
|
Y: int32(math.Round(-1 * p.worldPosition.Y)),
|
||||||
}
|
}
|
||||||
|
@ -63,7 +61,7 @@ func (p *penguin) Draw() error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *penguin) SetPosition(vec *vector.Vec2F) {
|
func (p *penguin) SetPosition(vec vector.Vec2F) {
|
||||||
p.worldPosition = vec
|
p.worldPosition = vec
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -91,7 +89,7 @@ func (p *penguin) MoveX(x float64) {
|
||||||
defer p.mx.Unlock()
|
defer p.mx.Unlock()
|
||||||
|
|
||||||
p.velocity.X = x
|
p.velocity.X = x
|
||||||
p.velocity.Normalize()
|
p.velocity = p.velocity.Normalized()
|
||||||
p.updateAnimation = true
|
p.updateAnimation = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -101,7 +99,7 @@ func (p *penguin) MoveY(y float64) {
|
||||||
|
|
||||||
// (0,0) is the top left, so negative y moves up
|
// (0,0) is the top left, so negative y moves up
|
||||||
p.velocity.Y = y
|
p.velocity.Y = y
|
||||||
p.velocity.Normalize()
|
p.velocity.Normalized()
|
||||||
p.updateAnimation = true
|
p.updateAnimation = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -78,7 +78,6 @@ func Run(ctx context.Context, configMap gosimpleconf.ConfigMap) error {
|
||||||
err = fmt.Errorf("failed in InitSpriteCache: %w", err)
|
err = fmt.Errorf("failed in InitSpriteCache: %w", err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
defer sprite.CleanupSpriteCache()
|
|
||||||
|
|
||||||
animation.DefineAnimations()
|
animation.DefineAnimations()
|
||||||
|
|
||||||
|
@ -93,7 +92,7 @@ func Run(ctx context.Context, configMap gosimpleconf.ConfigMap) error {
|
||||||
// Let them control a penguin to start with
|
// Let them control a penguin to start with
|
||||||
player1 := player.NewPlayer(ctx, inputHandler)
|
player1 := player.NewPlayer(ctx, inputHandler)
|
||||||
penguinEntity := types.NewPenguin(renderer)
|
penguinEntity := types.NewPenguin(renderer)
|
||||||
penguinCmdHandler := command.NewCommandHandler(ctx, penguinEntity)
|
penguinCmdHandler := command.NewCommandHandler(ctx, &penguinEntity)
|
||||||
penguinEntity.SetSpeed(2.0)
|
penguinEntity.SetSpeed(2.0)
|
||||||
entityList = append(entityList, penguinCmdHandler)
|
entityList = append(entityList, penguinCmdHandler)
|
||||||
player1.SetEntityChan(penguinCmdHandler.CommandRequest())
|
player1.SetEntityChan(penguinCmdHandler.CommandRequest())
|
||||||
|
@ -105,9 +104,9 @@ func Run(ctx context.Context, configMap gosimpleconf.ConfigMap) error {
|
||||||
|
|
||||||
for i := 0; i < 10; i++ {
|
for i := 0; i < 10; i++ {
|
||||||
entity := types.NewPenguin(renderer)
|
entity := types.NewPenguin(renderer)
|
||||||
entityCmd := command.NewCommandHandler(ctx, entity)
|
entityCmd := command.NewCommandHandler(ctx, &entity)
|
||||||
randomPos := vector.Vec2F{X: rand.Float64() * 500, Y: rand.Float64() * -500}
|
randomPos := vector.Vec2F{X: rand.Float64() * 500, Y: rand.Float64() * -500}
|
||||||
entity.SetPosition(&randomPos)
|
entity.SetPosition(randomPos)
|
||||||
entity.SetAnimation(rand.Intn(animation.PENGUIN_NUM_ANIMS))
|
entity.SetAnimation(rand.Intn(animation.PENGUIN_NUM_ANIMS))
|
||||||
entityList = append(entityList, entityCmd)
|
entityList = append(entityList, entityCmd)
|
||||||
|
|
||||||
|
@ -204,6 +203,8 @@ func Run(ctx context.Context, configMap gosimpleconf.ConfigMap) error {
|
||||||
e.CloseRequests()
|
e.CloseRequests()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sprite.CleanupSpriteCache()
|
||||||
|
|
||||||
wg.Wait()
|
wg.Wait()
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|
|
@ -22,26 +22,24 @@ func NewAnimation(
|
||||||
offset sdl.Point,
|
offset sdl.Point,
|
||||||
length int,
|
length int,
|
||||||
border int,
|
border int,
|
||||||
) *spriteAnimation {
|
) spriteAnimation {
|
||||||
|
|
||||||
spritesheet := GetSpritesheet(filename)
|
spritesheet := GetSpritesheet(filename)
|
||||||
|
|
||||||
a := spriteAnimation{
|
return spriteAnimation{
|
||||||
spritesheet: spritesheet,
|
spritesheet: spritesheet,
|
||||||
dimensions: dimensions,
|
dimensions: dimensions,
|
||||||
offset: offset,
|
offset: offset,
|
||||||
length: length,
|
length: length,
|
||||||
border: border,
|
border: border,
|
||||||
}
|
}
|
||||||
|
|
||||||
return &a
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *spriteAnimation) Draw(
|
func (a spriteAnimation) Draw(
|
||||||
frame int,
|
frame int,
|
||||||
windowPosition *sdl.Point,
|
windowPosition sdl.Point,
|
||||||
angle float64,
|
angle float64,
|
||||||
center *sdl.Point,
|
center sdl.Point,
|
||||||
flip sdl.RendererFlip,
|
flip sdl.RendererFlip,
|
||||||
) error {
|
) error {
|
||||||
|
|
||||||
|
@ -64,7 +62,7 @@ func (a *spriteAnimation) Draw(
|
||||||
H: height,
|
H: height,
|
||||||
}
|
}
|
||||||
|
|
||||||
err := a.checkBounds(§ion)
|
err := a.checkBounds(section)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -76,7 +74,7 @@ func (a *spriteAnimation) Draw(
|
||||||
H: height * 2,
|
H: height * 2,
|
||||||
}
|
}
|
||||||
|
|
||||||
err = a.spritesheet.Draw(§ion, &placement, angle, center, flip)
|
err = a.spritesheet.Draw(section, placement, angle, center, flip)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -84,7 +82,7 @@ func (a *spriteAnimation) Draw(
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *spriteAnimation) checkBounds(section *sdl.Rect) error {
|
func (a spriteAnimation) checkBounds(section sdl.Rect) error {
|
||||||
width := a.spritesheet.surface.W
|
width := a.spritesheet.surface.W
|
||||||
height := a.spritesheet.surface.H
|
height := a.spritesheet.surface.H
|
||||||
|
|
||||||
|
@ -103,7 +101,7 @@ func (a *spriteAnimation) checkBounds(section *sdl.Rect) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
if outOfBounds {
|
if outOfBounds {
|
||||||
return fmt.Errorf("draw section was out of bounds - section: %v, image: %v", *section, a.spritesheet.surface.Bounds())
|
return fmt.Errorf("draw section was out of bounds - section: %v, image: %v", section, a.spritesheet.surface.Bounds())
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|
|
@ -49,39 +49,33 @@ func NewSprite(renderer *sdl.Renderer, filename string) (*spritesheet, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *spritesheet) Cleanup() {
|
func (s *spritesheet) Cleanup() {
|
||||||
// Clean up image
|
sdl.Do(func() {
|
||||||
defer func() {
|
// Clean up spritesheet
|
||||||
if s.surface != nil {
|
|
||||||
sdl.Do(func() {
|
|
||||||
s.surface.Free()
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}()
|
|
||||||
|
|
||||||
// Clean up spritesheet
|
|
||||||
defer func() {
|
|
||||||
if s.texture != nil {
|
if s.texture != nil {
|
||||||
sdl.Do(func() {
|
err := s.texture.Destroy()
|
||||||
err := s.texture.Destroy()
|
if err != nil {
|
||||||
if err != nil {
|
log.Printf("error destroying spritesheet %v: %v\n", s.filename, err)
|
||||||
log.Printf("error destroying spritesheet %v: %v\n", s.filename, err)
|
}
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
}()
|
|
||||||
|
// Clean up image
|
||||||
|
if s.surface != nil {
|
||||||
|
s.surface.Free()
|
||||||
|
}
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *spritesheet) Draw(
|
func (s *spritesheet) Draw(
|
||||||
section *sdl.Rect,
|
section sdl.Rect,
|
||||||
placement *sdl.Rect,
|
placement sdl.Rect,
|
||||||
angle float64,
|
angle float64,
|
||||||
center *sdl.Point,
|
center sdl.Point,
|
||||||
flip sdl.RendererFlip,
|
flip sdl.RendererFlip,
|
||||||
) error {
|
) error {
|
||||||
|
|
||||||
var err error
|
var err error
|
||||||
sdl.Do(func() {
|
sdl.Do(func() {
|
||||||
err = s.renderer.CopyEx(s.texture, section, placement, angle, center, flip)
|
err = s.renderer.CopyEx(s.texture, §ion, &placement, angle, ¢er, flip)
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
@ -90,10 +84,9 @@ func (s *spritesheet) Draw(
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *spritesheet) Bounds() *sdl.Point {
|
func (s *spritesheet) Bounds() sdl.Point {
|
||||||
p := sdl.Point{
|
return sdl.Point{
|
||||||
X: s.surface.W,
|
X: s.surface.W,
|
||||||
Y: s.surface.H,
|
Y: s.surface.H,
|
||||||
}
|
}
|
||||||
return &p
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,20 +28,19 @@ var (
|
||||||
)
|
)
|
||||||
|
|
||||||
func InitSpriteCache(renderer *sdl.Renderer) error {
|
func InitSpriteCache(renderer *sdl.Renderer) error {
|
||||||
var err error
|
|
||||||
|
|
||||||
defaultSprite, err = createDefaultSprite(renderer)
|
|
||||||
if err != nil {
|
|
||||||
log.Printf("failed to create DefaultSprite: %v", err)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
spriteCache = make(map[string]*spritesheet)
|
spriteCache = make(map[string]*spritesheet)
|
||||||
|
|
||||||
for _, filename := range fileList {
|
for _, filename := range fileList {
|
||||||
s, err := NewSprite(renderer, filename)
|
s, err := NewSprite(renderer, filename)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("error creating sprite %v, using DefaultSprite: %v", filename, err)
|
log.Printf("error creating sprite %v, using DefaultSprite: %v", filename, err)
|
||||||
|
|
||||||
|
defaultSprite, err = createDefaultSprite(renderer)
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("failed to create DefaultSprite: %v", err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
spriteCache[filename] = defaultSprite
|
spriteCache[filename] = defaultSprite
|
||||||
} else {
|
} else {
|
||||||
spriteCache[filename] = s
|
spriteCache[filename] = s
|
||||||
|
@ -82,6 +81,7 @@ func createDefaultSprite(renderer *sdl.Renderer) (*spritesheet, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
s := spritesheet{
|
s := spritesheet{
|
||||||
|
filename: "DEFAULT_SPRITE",
|
||||||
renderer: renderer,
|
renderer: renderer,
|
||||||
texture: texture,
|
texture: texture,
|
||||||
surface: surface,
|
surface: surface,
|
||||||
|
|
|
@ -11,24 +11,28 @@ type Vec2F struct {
|
||||||
Y float64
|
Y float64
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Vec2F) Zero() bool {
|
func (v Vec2F) Zero() bool {
|
||||||
return v.X == 0.0 && v.Y == 0.0
|
return v.X == 0.0 && v.Y == 0.0
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Vec2F) LengthSquared() float64 {
|
func (v Vec2F) LengthSquared() float64 {
|
||||||
return v.X*v.X + v.Y*v.Y
|
return v.X*v.X + v.Y*v.Y
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Vec2F) Normalize() {
|
func (v Vec2F) Normalized() Vec2F {
|
||||||
|
output := Vec2F{X: v.X, Y: v.Y}
|
||||||
|
|
||||||
length := math.Hypot(v.X, v.Y)
|
length := math.Hypot(v.X, v.Y)
|
||||||
if length == 0 {
|
if length == 0 {
|
||||||
return
|
return output
|
||||||
}
|
}
|
||||||
|
|
||||||
v.X = v.X / length
|
output.X = v.X / length
|
||||||
v.Y = v.Y / length
|
output.Y = v.Y / length
|
||||||
|
|
||||||
|
return output
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Vec2F) Dot(other *Vec2F) float64 {
|
func (v Vec2F) Dot(other Vec2F) float64 {
|
||||||
return v.X*other.X + v.Y*other.Y
|
return v.X*other.X + v.Y*other.Y
|
||||||
}
|
}
|
||||||
|
|
3
main.go
3
main.go
|
@ -58,8 +58,9 @@ func run(ctx context.Context) error {
|
||||||
|
|
||||||
// Setup logging
|
// Setup logging
|
||||||
writeToFile := gosimpleconf.Bool(configMap["log.writeToFile"])
|
writeToFile := gosimpleconf.Bool(configMap["log.writeToFile"])
|
||||||
|
utcTime := gosimpleconf.Bool(configMap["log.utcTime"])
|
||||||
logFilename := configMap["log.file"]
|
logFilename := configMap["log.file"]
|
||||||
logWriter, err := config.SetupLogging(writeToFile, logFilename)
|
logWriter, err := config.SetupLogging(writeToFile, utcTime, logFilename)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatalf("error setting up logging: %v\n", err)
|
log.Fatalf("error setting up logging: %v\n", err)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue