mirror of
https://github.com/hajimehoshi/ebiten.git
synced 2024-11-10 04:57:26 +01:00
parent
cea0aa72cb
commit
873bb35587
@ -163,6 +163,30 @@ func drawEbitenLogo(screen *ebiten.Image, x, y int) {
|
|||||||
screen.DrawTriangles(vs, is, emptySubImage, op)
|
screen.DrawTriangles(vs, is, emptySubImage, op)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func drawArc(screen *ebiten.Image, count int) {
|
||||||
|
var path vector.Path
|
||||||
|
|
||||||
|
path.MoveTo(350, 100)
|
||||||
|
const cx, cy, r = 450, 100, 70
|
||||||
|
theta := math.Pi * float64(count) / 180
|
||||||
|
x := cx + r*math.Cos(theta)
|
||||||
|
y := cy + r*math.Sin(theta)
|
||||||
|
path.ArcTo(450, 100, float32(x), float32(y), 30)
|
||||||
|
|
||||||
|
op := &ebiten.DrawTrianglesOptions{
|
||||||
|
EvenOdd: true,
|
||||||
|
}
|
||||||
|
vs, is := path.AppendVerticesAndIndicesForFilling(nil, nil)
|
||||||
|
for i := range vs {
|
||||||
|
vs[i].SrcX = 1
|
||||||
|
vs[i].SrcY = 1
|
||||||
|
vs[i].ColorR = 0x33 / float32(0xff)
|
||||||
|
vs[i].ColorG = 0xcc / float32(0xff)
|
||||||
|
vs[i].ColorB = 0x66 / float32(0xff)
|
||||||
|
}
|
||||||
|
screen.DrawTriangles(vs, is, emptySubImage, op)
|
||||||
|
}
|
||||||
|
|
||||||
func maxCounter(index int) int {
|
func maxCounter(index int) int {
|
||||||
return 128 + (17*index+32)%64
|
return 128 + (17*index+32)%64
|
||||||
}
|
}
|
||||||
@ -219,6 +243,7 @@ func (g *Game) Draw(screen *ebiten.Image) {
|
|||||||
screen.Fill(color.White)
|
screen.Fill(color.White)
|
||||||
drawEbitenText(screen)
|
drawEbitenText(screen)
|
||||||
drawEbitenLogo(screen, 20, 90)
|
drawEbitenLogo(screen, 20, 90)
|
||||||
|
drawArc(screen, g.counter)
|
||||||
drawWave(screen, g.counter)
|
drawWave(screen, g.counter)
|
||||||
|
|
||||||
ebitenutil.DebugPrint(screen, fmt.Sprintf("TPS: %0.2f\nFPS: %0.2f", ebiten.CurrentTPS(), ebiten.CurrentFPS()))
|
ebitenutil.DebugPrint(screen, fmt.Sprintf("TPS: %0.2f\nFPS: %0.2f", ebiten.CurrentTPS(), ebiten.CurrentFPS()))
|
||||||
|
@ -18,6 +18,8 @@
|
|||||||
package vector
|
package vector
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"math"
|
||||||
|
|
||||||
"github.com/hajimehoshi/ebiten/v2"
|
"github.com/hajimehoshi/ebiten/v2"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -45,7 +47,10 @@ func (p *Path) LineTo(x, y float32) {
|
|||||||
if len(p.segs) == 0 {
|
if len(p.segs) == 0 {
|
||||||
p.segs = append(p.segs, []point{p.cur})
|
p.segs = append(p.segs, []point{p.cur})
|
||||||
}
|
}
|
||||||
p.segs[len(p.segs)-1] = append(p.segs[len(p.segs)-1], point{x: x, y: y})
|
seg := p.segs[len(p.segs)-1]
|
||||||
|
if seg[len(seg)-1].x != x || seg[len(seg)-1].y != y {
|
||||||
|
p.segs[len(p.segs)-1] = append(seg, point{x: x, y: y})
|
||||||
|
}
|
||||||
p.cur = point{x: x, y: y}
|
p.cur = point{x: x, y: y}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -127,6 +132,56 @@ func (p *Path) cubicTo(x1, y1, x2, y2, x3, y3 float32, level int) {
|
|||||||
p.cubicTo(x123, y123, x23, y23, x3, y3, level+1)
|
p.cubicTo(x123, y123, x23, y23, x3, y3, level+1)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func normalize(x, y float32) (float32, float32) {
|
||||||
|
len := float32(math.Hypot(float64(x), float64(y)))
|
||||||
|
return x / len, y / len
|
||||||
|
}
|
||||||
|
|
||||||
|
// ArcTo adds an arc curve to the path. (x1, y1) is the control point, and (x2, y2) is the destination.
|
||||||
|
//
|
||||||
|
// ArcTo updates the current position to (x2, y2).
|
||||||
|
func (p *Path) ArcTo(x1, y1, x2, y2, radius float32) {
|
||||||
|
x0 := p.cur.x
|
||||||
|
y0 := p.cur.y
|
||||||
|
dx0 := x0 - x1
|
||||||
|
dy0 := y0 - y1
|
||||||
|
dx1 := x2 - x1
|
||||||
|
dy1 := y2 - y1
|
||||||
|
dx0, dy0 = normalize(dx0, dy0)
|
||||||
|
dx1, dy1 = normalize(dx1, dy1)
|
||||||
|
|
||||||
|
// theta is the angle between two vectors (dx0, dy0) and (dx1, dy1).
|
||||||
|
theta := math.Acos(float64(dx0*dx1 + dy0*dy1))
|
||||||
|
// TODO: When theta is bigger than π/2, the arc should be split into two.
|
||||||
|
|
||||||
|
// dist is the distance between the control point and the arc's begenning and ending points.
|
||||||
|
dist := radius / float32(math.Tan(theta/2))
|
||||||
|
|
||||||
|
// TODO: What if dist is too big?
|
||||||
|
|
||||||
|
// (ax0, ay0) is the start of the arc.
|
||||||
|
ax0 := x1 + dx0*dist
|
||||||
|
ay0 := y1 + dy0*dist
|
||||||
|
|
||||||
|
// (ax1, ay1) is the end of the arc.
|
||||||
|
ax1 := x1 + dx1*dist
|
||||||
|
ay1 := y1 + dy1*dist
|
||||||
|
|
||||||
|
p.LineTo(ax0, ay0)
|
||||||
|
|
||||||
|
// Calculate the control points for an approximated Bézier curve.
|
||||||
|
// See https://docs.microsoft.com/en-us/xamarin/xamarin-forms/user-interface/graphics/skiasharp/curves/beziers.
|
||||||
|
alpha := math.Pi - theta
|
||||||
|
l := radius * float32(math.Tan(alpha/4)*4/3)
|
||||||
|
cx0 := ax0 + l*(-dx0)
|
||||||
|
cy0 := ay0 + l*(-dy0)
|
||||||
|
cx1 := ax1 + l*(-dx1)
|
||||||
|
cy1 := ay1 + l*(-dy1)
|
||||||
|
p.CubicTo(cx0, cy0, cx1, cy1, ax1, ay1)
|
||||||
|
|
||||||
|
p.LineTo(x2, y2)
|
||||||
|
}
|
||||||
|
|
||||||
// AppendVerticesAndIndicesForFilling appends vertices and indices to fill this path and returns them.
|
// AppendVerticesAndIndicesForFilling appends vertices and indices to fill this path and returns them.
|
||||||
// AppendVerticesAndIndicesForFilling works in a similar way to the built-in append function.
|
// AppendVerticesAndIndicesForFilling works in a similar way to the built-in append function.
|
||||||
// If the arguments are nils, AppendVerticesAndIndices returns new slices.
|
// If the arguments are nils, AppendVerticesAndIndices returns new slices.
|
||||||
|
Loading…
Reference in New Issue
Block a user