added transformations, translate, scale, rotate

This commit is contained in:
Thomas Friedel 2018-01-29 16:04:56 +01:00
parent 6480345a60
commit 395ef95009
3 changed files with 37 additions and 14 deletions

View file

@ -63,13 +63,18 @@ func New(x, y, w, h int) *Canvas {
stateStack: make([]drawState, 0, 20),
}
cv.state.stroke.lineWidth = 1
cv.state.transform = lm.Mat3x3Identity()
return cv
}
func (cv *Canvas) xToGL(x float32) float32 { return x*2/cv.fw - 1 }
func (cv *Canvas) yToGL(y float32) float32 { return -y*2/cv.fh + 1 }
func (cv *Canvas) ptToGL(x, y float32) (fx, fy float32) { return x*2/cv.fw - 1, -y*2/cv.fh + 1 }
func (cv *Canvas) vecToGL(v lm.Vec2) (fx, fy float32) { return v[0]*2/cv.fw - 1, -v[1]*2/cv.fh + 1 }
func (cv *Canvas) ptToGL(x, y float32) (fx, fy float32) {
return cv.vecToGL(lm.Vec2{x, y})
}
func (cv *Canvas) vecToGL(v lm.Vec2) (fx, fy float32) {
v, _ = v.MulMat3x3(cv.state.transform)
return v[0]*2/cv.fw - 1, -v[1]*2/cv.fh + 1
}
// Activate makes the canvas active and sets the viewport. Only needs
// to be called if any other GL code changes the viewport
@ -214,6 +219,18 @@ func (cv *Canvas) Restore() {
cv.stateStack = cv.stateStack[:l-1]
}
func (cv *Canvas) Scale(x, y float32) {
cv.state.transform = cv.state.transform.Mul(lm.Mat3x3Scale(lm.Vec2{x, y}))
}
func (cv *Canvas) Translate(x, y float32) {
cv.state.transform = cv.state.transform.Mul(lm.Mat3x3Translate(lm.Vec2{x, y}))
}
func (cv *Canvas) Rotate(angle float32) {
cv.state.transform = cv.state.transform.Mul(lm.Mat3x3Rotate(angle))
}
// FillRect fills a rectangle with the active color
func (cv *Canvas) FillRect(x, y, w, h float32) {
cv.activate()
@ -221,10 +238,12 @@ func (cv *Canvas) FillRect(x, y, w, h float32) {
gli.UseProgram(sr.id)
x0f, y0f := cv.ptToGL(x, y)
x1f, y1f := cv.ptToGL(x+w, y+h)
x1f, y1f := cv.ptToGL(x, y+h)
x2f, y2f := cv.ptToGL(x+w, y+h)
x3f, y3f := cv.ptToGL(x+w, y)
gli.BindBuffer(gl_ARRAY_BUFFER, buf)
data := [8]float32{x0f, y0f, x0f, y1f, x1f, y1f, x1f, y0f}
data := [8]float32{x0f, y0f, x1f, y1f, x2f, y2f, x3f, y3f}
gli.BufferData(gl_ARRAY_BUFFER, len(data)*4, unsafe.Pointer(&data[0]), gl_STREAM_DRAW)
gli.VertexAttribPointer(sr.vertex, 2, gl_FLOAT, false, 0, nil)

View file

@ -159,7 +159,9 @@ func (cv *Canvas) DrawImage(img *Image, coords ...float32) {
}
dx0, dy0 := cv.ptToGL(dx, dy)
dx1, dy1 := cv.ptToGL(dx+dw, dy+dh)
dx1, dy1 := cv.ptToGL(dx, dy+dh)
dx2, dy2 := cv.ptToGL(dx+dw, dy+dh)
dx3, dy3 := cv.ptToGL(dx+dw, dy)
sx /= float32(img.w)
sy /= float32(img.h)
sw /= float32(img.w)
@ -174,7 +176,7 @@ func (cv *Canvas) DrawImage(img *Image, coords ...float32) {
gli.Uniform1i(tr.image, 0)
gli.BindBuffer(gl_ARRAY_BUFFER, buf)
data := [16]float32{dx0, dy0, dx0, dy1, dx1, dy1, dx1, dy0,
data := [16]float32{dx0, dy0, dx1, dy1, dx2, dy2, dx3, dy3,
sx, sy, sx, sy + sh, sx + sw, sy + sh, sx + sw, sy}
gli.BufferData(gl_ARRAY_BUFFER, len(data)*4, unsafe.Pointer(&data[0]), gl_STREAM_DRAW)

14
text.go
View file

@ -87,12 +87,14 @@ func (cv *Canvas) FillText(str string, x, y float32) {
gli.Uniform1i(tr.image, 0)
gli.BindBuffer(gl_ARRAY_BUFFER, buf)
x0 := float32(bounds.Min.X) / cv.fw
y0 := float32(bounds.Min.Y) / cv.fh
x1 := float32(bounds.Max.X) / cv.fw
y1 := float32(bounds.Max.Y) / cv.fh
data := [16]float32{x0*2 - 1, -y0*2 + 1, x0*2 - 1, -y1*2 + 1, x1*2 - 1, -y1*2 + 1, x1*2 - 1, -y0*2 + 1,
0, 1, 0, 1 - (y1 - y0), x1 - x0, 1 - (y1 - y0), x1 - x0, 1}
dx0, dy0 := cv.ptToGL(float32(bounds.Min.X), float32(bounds.Min.Y))
dx1, dy1 := cv.ptToGL(float32(bounds.Min.X), float32(bounds.Max.Y))
dx2, dy2 := cv.ptToGL(float32(bounds.Max.X), float32(bounds.Max.Y))
dx3, dy3 := cv.ptToGL(float32(bounds.Max.X), float32(bounds.Min.Y))
tw := float32(bounds.Max.X-bounds.Min.X) / cv.fw
th := float32(bounds.Max.Y-bounds.Min.Y) / cv.fh
data := [16]float32{dx0, dy0, dx1, dy1, dx2, dy2, dx3, dy3,
0, 1, 0, 1 - th, tw, 1 - th, tw, 1}
gli.BufferData(gl_ARRAY_BUFFER, len(data)*4, unsafe.Pointer(&data[0]), gl_STREAM_DRAW)
gli.VertexAttribPointer(tr.vertex, 2, gl_FLOAT, false, 0, nil)