sprites

package module
v0.0.3 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 22, 2024 License: Apache-2.0 Imports: 15 Imported by: 0

README

Golang Sprites

Go Reference Go CI Go Report Card Coverage Badge

Go Sprites is for simulating actor model sprites in a 2D world

Golang Sprites is a reimagining of Scratch created by MIT Media Lab. Every entity on the screen is a sprite that can be programmed independently.

The goals are many:

  • Remove the complexity of the game loop handling
  • A super easy game engine
    • See the falling turtles example
  • A package for visualizing a simulation
    • See the double pendulum example

Install

Go 1.22 or later is required.

Ebitengine is the main dependency. Check here for the system specific instructions.

Example

Random Walk

A really simple example is to create turtles that each perform a random walk.

main(...) start the sim with the window size parameters. Ebiten eats the main thread, so the function to run once Ebiten starts is passed as an additional parameter.

simStartFunc(...) Adds one sprite image and then starts go routines for each sprite. A new sprite will be started every half second.

turtleRandomWalk(...) is the main function for each sprite. A new sprite is created and setup. Then it enters an infinite loop where a random velocity is added in the x and y directions. That velocity is integrated into position. The position and angle are updated. And finally, the sprite sleeps. If the sprite gets too far off screen then it is deleted.

package main

import (
	"math"
	"math/rand"
	"time"

	"github.com/gary23b/sprites"
)

func main() {
	params := sprites.SimParams{Width: 500, Height: 500}
	sprites.Start(params, simStartFunc)
}

func simStartFunc(sim sprites.Sim) {
	sim.AddCostume(sprites.DecodeCodedSprite(sprites.TurtleImage), "t")

	for {
		go turtleRandomWalk(sim)
		time.Sleep(time.Millisecond * 500)
	}
}

func turtleRandomWalk(sim sprites.Sim) {
	s := sim.AddSprite("")
	s.Costume("t")
	s.Visible(true)

	x, y := 0.0, 0.0
	velX, velY := 0.0, 0.0

	for {
		velX += (rand.Float64()*2 - 1) * .05
		velY += (rand.Float64()*2 - 1) * .05
		x += velX
		y += velY
		s.Pos(x, y)
		s.Angle(180.0 / math.Pi * math.Atan2(velY, velX))

		if max(math.Abs(x), math.Abs(y)) > 1000 {
			s.DeleteSprite()
			return
		}
		time.Sleep(time.Millisecond * 10)
	}
}

Golang Sprites simulation of turtle source random walk

Double Pendulum

Here is a simulation of a double pendulum.

go run github.com/gary23b/sprites/examples/DoublePendulum@latest

Golang Sprites simulation of a double pendulum

Falling Turtles

This example is a really simple game where you have to click on each turtle before it reaches the bottom of the screen. At the end, your final score is displayed.

go run github.com/gary23b/sprites/examples/fallingturtles@latest
Tumbler

Here is a simulation of a rotating box filled with circles, boxes, and rounded rectangles. This uses the library github.com/jakecoffman/cp for the physics simulation. The sprites are being drawn using Golang Sprites.

This is a recreation of https://jakecoffman.com/cp-ebiten/tumble/ except without drawing the shapes using ebiten and cp directly. Here, cp is only performing the physics updates. The original code can be found here

go run github.com/gary23b/sprites/examples/tumbler@latest

Golang Sprites simulation of a rotating box filled with circles, boxes, and rounded rectangles

Build Executable

To get the list of go build targets use the following command:

go tool dist list
Window
GOOS=windows GOARCH=amd64 go build ./examples/fallingturtles/
Linux
GOOS=linux  GOARCH=amd64 go build ./examples/fallingturtles/
WASM
GOOS=js  GOARCH=wasm go build ./examples/fallingturtles/

Things to Research

Documentation

Index

Constants

This section is empty.

Variables

View Source
var (
	// Black to white
	Black     color.RGBA = color.RGBA{0x00, 0x00, 0x00, 0xFF} // #000000
	DarkGray  color.RGBA = color.RGBA{0x26, 0x26, 0x26, 0xFF} // #262626
	Gray      color.RGBA = color.RGBA{0x80, 0x80, 0x80, 0xFF} // #808080
	LightGray color.RGBA = color.RGBA{0xD3, 0xD3, 0xD3, 0xFF} // #D3D3D3
	White     color.RGBA = color.RGBA{0xFF, 0xFF, 0xFF, 0xFF} // #FFFFFF

	// Primary Colors
	Red  color.RGBA = color.RGBA{0xFF, 0x00, 0x00, 0xFF} // #FF0000
	Lime color.RGBA = color.RGBA{0x00, 0xFF, 0x00, 0xFF} // #00FF00
	Blue color.RGBA = color.RGBA{0x00, 0x00, 0xFF, 0xFF} // #0000FF

	// half strength primary colors
	Maroon   color.RGBA = color.RGBA{0x80, 0x00, 0x00, 0xFF} // #800000
	Green    color.RGBA = color.RGBA{0x00, 0x80, 0x00, 0xFF} // #008000
	NavyBlue color.RGBA = color.RGBA{0x00, 0x00, 0x80, 0xFF} // #000080

	// full strength primary mixes
	Yellow  color.RGBA = color.RGBA{0xFF, 0xFF, 0x00, 0xFF} // #FFFF00
	Aqua    color.RGBA = color.RGBA{0x00, 0xFF, 0xFF, 0xFF} // #00FFFF
	Cyan               = Aqua                               // #00FFFF
	Magenta color.RGBA = color.RGBA{0xFF, 0x00, 0xFF, 0xFF} // #FF00FF
	Fuchsia            = Magenta                            // #FF00FF

	// half strength primary mixes
	Olive  color.RGBA = color.RGBA{0x80, 0x80, 0x00, 0xFF} // #808000
	Purple color.RGBA = color.RGBA{0x80, 0x00, 0x80, 0xFF} // #800080
	Teal   color.RGBA = color.RGBA{0x00, 0x80, 0x80, 0xFF} // #008080

	// Other interesting colors
	Orange      color.RGBA = color.RGBA{0xFF, 0xA5, 0x00, 0xFF} // #FFA500
	Indigo      color.RGBA = color.RGBA{0x4B, 0x00, 0x82, 0xFF} // #4B0082
	Violet      color.RGBA = color.RGBA{0xEE, 0x82, 0xEE, 0xFF} // #EE82EE
	Gold        color.RGBA = color.RGBA{0xFF, 0xD7, 0x00, 0xFF} // #FFD700
	SkyBlue     color.RGBA = color.RGBA{0x87, 0xCE, 0xEB, 0xFF} // #87CEEB
	SaddleBrown color.RGBA = color.RGBA{0x8B, 0x45, 0x13, 0xFF} // #8B4513
	Tan         color.RGBA = color.RGBA{0xD2, 0xB4, 0x8C, 0xFF} // #D2B48C
	Crimson     color.RGBA = color.RGBA{0xDC, 0x14, 0x3C, 0xFF} // #DC143C
	Pink        color.RGBA = color.RGBA{0xFF, 0xC0, 0xCB, 0xFF} // #FFC0CB
	Salmon      color.RGBA = color.RGBA{0xFA, 0x80, 0x72, 0xFF} // #FA8072
	Turquoise   color.RGBA = color.RGBA{0x40, 0xE0, 0xD0, 0xFF} // #40E0D0
)

A basic set of colors based on the colors found here: https://www.w3schools.com/colors/colors_names.asp

View Source
var (
	TurtleImage string = "" /* 9244-byte string literal not displayed */
	ArrowImage  string = "" /* 1004-byte string literal not displayed */
)

Created from ./cmd/convertimages/convertImages.go

Functions

func CreateGif added in v0.0.2

func CreateGif(
	sim Sim,
	delayBetweenScreenshots time.Duration,
	delayBetweenGifFrames time.Duration,
	outputGifFilePath string,
	frameCount int,
)

Start this as a go routine to create a GIF of your creation.

func CreateGifDithered added in v0.0.2

func CreateGifDithered(
	sim Sim,
	delayBetweenScreenshots time.Duration,
	delayBetweenGifFrames time.Duration,
	outputGifFilePath string,
	frameCount int,
)

Start this as a go routine to create a GIF of your creation.

func DecodeCodedSprite added in v0.0.2

func DecodeCodedSprite(in string) image.Image

func GetNewestJustPressedFromChan

func GetNewestJustPressedFromChan(justPressedChan chan *spritesmodels.UserInput) *spritesmodels.UserInput

This returns nil if there is no new data. This will throw away all but the newest set of data available. So this should be called faster that the game update rate (60Hz), otherwise sim.PressedUserInput() should be used instead.

func LoadSpriteFile added in v0.0.2

func LoadSpriteFile(path string) (image.Image, error)

func NewSprite added in v0.0.2

func NewSprite(sim Sim, uniqueName string, spriteID int) *sprite

func Start

func Start(params SimParams, simStartFunc func(Sim))

The drawFunc will be started as a go routine.

func TakeScreenshot added in v0.0.2

func TakeScreenshot(sim Sim, outputPNGPath string) error

func TakeScreenshotVideo added in v0.0.2

func TakeScreenshotVideo(
	sim Sim,
	delayBetweenScreenshots time.Duration,
	frameCount int,
) []image.Image

Types

type Sim added in v0.0.2

type Sim interface {
	GetWidth() int
	GetHeight() int

	AddCostume(img image.Image, name string)
	AddSprite(UniqueName string) Sprite // If no name is given, a random name is generated.
	DeleteSprite(Sprite)
	DeleteAllSprites()

	SpriteUpdatePosAngle(in Sprite)
	SpriteUpdateFull(in Sprite)

	AddSound(path, name string)
	PlaySound(name string, volume float64) // volume must be between 0 and 1.

	PressedUserInput() *spritesmodels.UserInput
	SubscribeToJustPressedUserInput() chan *spritesmodels.UserInput
	UnSubscribeToJustPressedUserInput(in chan *spritesmodels.UserInput)

	GetSpriteID(UniqueName string) int
	GetSpriteInfo(UniqueName string) spritesmodels.SpriteState
	GetSpriteInfoByID(id int) spritesmodels.SpriteState

	WhoIsNearMe(x, y, distance float64) []spritesmodels.NearMeInfo
	SendMsg(toSpriteID int, msg any)

	GetScreenshot() image.Image

	Exit()
}

type SimParams added in v0.0.2

type SimParams struct {
	Width   int  // Window Width in pixels
	Height  int  // Window Height in pixels
	ShowFPS bool // Show Frame-Rate and Update-Rate information in top left corner of window
}

type Sprite added in v0.0.2

type Sprite interface {
	GetSpriteID() int
	GetUniqueName() string
	Clone(UniqueName string) Sprite

	// Updates
	Costume(name string)
	SetType(newType int)
	Angle(angleDegrees float64)
	Pos(cartX, cartY float64) // Cartesian (x,y). Center in the middle of the window
	Z(int)                    //
	Visible(visible bool)
	Scale(scale float64) // Sets xScale and yScale together
	XYScale(xScale, yScale float64)
	Opacity(opacityPercent float64) // 0 is completely transparent and 100 is completely opaque
	All(in spritesmodels.SpriteState)

	// Info
	GetState() spritesmodels.SpriteState

	// Click Body
	GetClickBody() spritesmodels.ClickOnBody
	ReplaceClickBody(in spritesmodels.ClickOnBody)

	// User Input
	PressedUserInput() *spritesmodels.UserInput
	JustPressedUserInput() *spritesmodels.UserInput

	// Interact With other sprites
	WhoIsNearMe(distance float64) []spritesmodels.NearMeInfo
	SendMsg(toSpriteID int, msg any)
	GetMsgs() []any
	AddMsg(msg any)

	// exit
	DeleteSprite()
}

Directories

Path Synopsis
cmd
convertimages command
runinweb command
examples
DoublePendulum command
ecosim command
fallingturtles command
marblemachine command
play1 command
play2 command
play3 command
randomwalk command
tumbler command

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL