Golang游戏 图像旋转模拟运动 (ebiten)

运动效果
在这里插入图片描述
首先为Ebiten GeoM结构体(github.com\hajimehoshi\ebiten\v2@v2.0.7\geom.go)添加了一个可以旋转旋转中心的方法

//(x,y)为旋转中心坐标 
// theta 为旋转角度,弧度制
func (g *GeoM) RotateByPoint(x, y, theta float64) {
	if theta == 0 {
		return
	}
	sin, cos := math.Sincos(theta)
	_tx, _ty := g.tx-x, g.ty-y

	a := cos*(g.a_1+1) - sin*g.c
	b := cos*g.b - sin*(g.d_1+1)
	tx := cos*_tx - sin*_ty
	c := sin*(g.a_1+1) + cos*g.c
	d := sin*g.b + cos*(g.d_1+1)
	ty := sin*_tx + cos*_ty

	g.a_1 = a - 1
	g.b = b
	g.c = c
	g.d_1 = d - 1
	g.tx = tx + x
	g.ty = ty + y
}

创建Hamster结构体

package component

import (
	"github.com/hajimehoshi/ebiten/v2"
	"github.com/hajimehoshi/ebiten/v2/ebitenutil"
	_ "image/png"
	"math"
	"time"
)

type Hamster struct {
	Image *ebiten.Image
	Opts  *ebiten.DrawImageOptions
	x     float64
	y     float64
	w     float64
	h     float64
}

func NewHamster(x, y float64) *Hamster {
	image, _, err := ebitenutil.NewImageFromFile("example2/static/image/go.png")
	if err != nil {
		panic(err)
	}
	opts := &ebiten.DrawImageOptions{}
	opts.GeoM.Translate(x, y)
	w, h := image.Size()
	return &Hamster{
		Image: image,
		Opts:  opts,
		x:     x,
		y:     y,
		w:     float64(w),
		h:     float64(h),
	}
}
// Walk方法以下边线中点为旋转中心,循环左右旋转
// 在main中开启协程执行
func (h *Hamster) Walk() {
	for {
		x, y := h.x+h.w/2, h.y+h.h
		h.Opts.GeoM.RotateByPoint(x, y, math.Pi/24)
		time.Sleep(200 * time.Millisecond)
		h.Opts.GeoM.RotateByPoint(x, y, -math.Pi/24)
		time.Sleep(200 * time.Millisecond)
		h.Opts.GeoM.RotateByPoint(x, y, -math.Pi/24)
		time.Sleep(200 * time.Millisecond)
		h.Opts.GeoM.RotateByPoint(x, y, math.Pi/24)
		time.Sleep(200 * time.Millisecond)
	}
}

main.go

package main

import (
	"github.com/hajimehoshi/ebiten/v2"
	"github.com/vua/vGame/example2/component"
	"image/color"
	"log"
)

type Game struct {
	bgc color.Color
	w   int
	h   int
	hamster *component.Hamster
}

func (g *Game) Update() error {
	// Write your game's logical update.
	return nil
}

func (g *Game) Draw(screen *ebiten.Image) {
	screen.Fill(g.bgc)
	screen.DrawImage(g.hamster.Image, g.hamster.Opts)
}

func (g *Game) Layout(outsideWidth, outsideHeight int) (screenWidth, screenHeight int) {
	return g.w, g.h
}

func (g *Game) walk(){
	g.hamster.Walk()
}

func main() {
	game := &Game{
		bgc: color.RGBA{0xff, 0xff, 0xff, 0xff},
		w:   320,
		h:   240,
		hamster: component.NewHamster(149,120),
	}
	go game.walk()

	ebiten.SetWindowSize(640, 480)
	ebiten.SetWindowTitle("vGame")

	if err := ebiten.RunGame(game); err != nil {
		log.Fatal(err)
	}
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
下面是一个简单的购票系统模拟golang实现,主要包括以下功能: 1. 用户选择演出场次和座位 2. 系统检查座位是否已经被预定 3. 系统返回总价并确认订单 ```go package main import ( "fmt" ) // 定义座位结构体 type Seat struct { row int col int price int status bool } // 定义演出场次结构体 type Show struct { name string seats [][]Seat } // 初始化演出场次 func initShow() Show { s := Show{ name: "猪八戒大闹天宫", seats: make([][]Seat, 10), } for i := range s.seats { s.seats[i] = make([]Seat, 10) for j := range s.seats[i] { s.seats[i][j] = Seat{ row: i + 1, col: j + 1, price: 100, status: false, } } } return s } // 显示演出场次座位情况 func showSeats(s Show) { fmt.Println(s.name) for i := range s.seats { for j := range s.seats[i] { if s.seats[i][j].status { fmt.Print("X ") } else { fmt.Print("O ") } } fmt.Println() } } // 计算总价 func calcTotalPrice(seats []Seat) int { total := 0 for _, seat := range seats { total += seat.price } return total } // 预定座位 func bookSeats(s Show, seats []Seat) { for _, seat := range seats { s.seats[seat.row-1][seat.col-1].status = true } } func main() { show := initShow() showSeats(show) // 用户选择座位 var row, col int var selectedSeats []Seat for i := 0; i < 2; i++ { // 每次最多选择2个座位 fmt.Print("请选择座位(行 列):") fmt.Scan(&row, &col) seat := show.seats[row-1][col-1] if seat.status { fmt.Println("该座位已经被预定,请重新选择!") continue } selectedSeats = append(selectedSeats, seat) fmt.Print("是否继续选择座位?(Y/N)") var input string fmt.Scan(&input) if input == "N" { break } } // 显示用户选择的座位和总价 fmt.Println("您选择的座位:") for _, seat := range selectedSeats { fmt.Printf("第%d排第%d列,价格%d元\n", seat.row, seat.col, seat.price) } totalPrice := calcTotalPrice(selectedSeats) fmt.Printf("总价:%d元\n", totalPrice) fmt.Print("确认订单?(Y/N)") var input string fmt.Scan(&input) if input == "Y" { bookSeats(show, selectedSeats) fmt.Println("预定成功!") showSeats(show) } else { fmt.Println("预定已取消!") } } ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值