diff --git a/common/font.go b/common/font.go index 834ff9e8..d9cf7502 100644 --- a/common/font.go +++ b/common/font.go @@ -178,6 +178,9 @@ func (f *Font) generateFontAtlas(c int) FontAtlas { YLocation: make([]float32, c), Width: make([]float32, c), Height: make([]float32, c), + OffsetX: make([]float32, c), + RightSide: make([]float32, c), + OffsetY: make([]float32, c), } currentX := float32(0) @@ -200,32 +203,55 @@ func (f *Font) generateFontAtlas(c int) FontAtlas { }) lineHeight := d.Face.Metrics().Height - lineBuffer := float32(lineHeight.Ceil()) / 2 - xBuffer := float32(10) + ascent := d.Face.Metrics().Ascent + prev := 0 for i := 0; i < c; i++ { - _, adv, ok := d.Face.GlyphBounds(rune(i)) + bounds, adv, ok := d.Face.GlyphBounds(rune(i)) if !ok { continue } - currentX += xBuffer + advance := float32(adv.Ceil()) - atlas.Width[i] = float32(adv.Ceil()) - atlas.Height[i] = float32(lineHeight.Ceil()) + lineBuffer - atlas.XLocation[i] = currentX - atlas.YLocation[i] = currentY + atlas.Width[i] = float32((bounds.Max.X - bounds.Min.X).Ceil()) + atlas.Height[i] = float32((bounds.Max.Y - bounds.Min.Y).Ceil()) + atlas.OffsetX[i] = float32(bounds.Min.X.Ceil()) + atlas.OffsetY[i] = float32((ascent + bounds.Min.Y).Ceil()) + atlas.RightSide[i] = advance - float32(bounds.Max.X.Ceil()) + + if prev > 0 { + currentX += float32(f.face.Kern(rune(prev), rune(i)).Ceil()) + } - currentX += float32(adv.Ceil()) + xBuffer + //overlapping characters + if atlas.Width[i] > advance { + if atlas.OffsetX[i] < 0 { + advance -= atlas.OffsetX[i] + } else if advance < float32(bounds.Max.X.Ceil()) { + advance = float32(bounds.Max.X.Ceil()) + } + } - if currentX > atlas.TotalWidth { - atlas.TotalWidth = currentX + // position correction of overlapped characters + if atlas.OffsetX[i] < 0 { + currentX -= atlas.OffsetX[i] } - if currentX > 1024 || i >= c-1 { + if currentX+advance > 1024 { currentX = 0 - currentY += float32(lineHeight.Ceil()) + lineBuffer - atlas.TotalHeight += float32(lineHeight.Ceil()) + lineBuffer + currentY += float32(lineHeight.Ceil()) + atlas.TotalHeight += float32(lineHeight.Ceil()) + prev = 0 } + + if currentX+advance > atlas.TotalWidth { + atlas.TotalWidth = currentX + advance + } + + atlas.XLocation[i] = currentX + atlas.YLocation[i] = currentY + currentX += advance + prev = i } // Create texture @@ -238,8 +264,11 @@ func (f *Font) generateFontAtlas(c int) FontAtlas { if !ok { continue } - d.Dot = fixed.P(int(atlas.XLocation[i]), int(atlas.YLocation[i]+float32(lineHeight.Ceil()))) + d.Dot = fixed.P(int(atlas.XLocation[i]), int(atlas.YLocation[i]+float32(ascent.Ceil()))) d.DrawBytes([]byte{byte(i)}) + // position correction + atlas.XLocation[i] += atlas.OffsetX[i] + atlas.YLocation[i] += atlas.OffsetY[i] } imObj := NewImageObject(actual) @@ -265,6 +294,12 @@ type FontAtlas struct { Width []float32 // Height contains the height in pixels of all the characters Height []float32 + // OffsetX is the offset of the glyph and the x-coordinate + OffsetX []float32 + // RightSide is the space left to the right of the glyph + RightSide []float32 + // OffsetY is the offset of the glyph and the y-coordinate + OffsetY []float32 // TotalWidth is the total amount of pixels the `FontAtlas` is wide; useful for determining the `Viewport`, // which is relative to this value. TotalWidth float32 diff --git a/common/render_shaders_text.go b/common/render_shaders_text.go index 19b5f09b..edf941a7 100644 --- a/common/render_shaders_text.go +++ b/common/render_shaders_text.go @@ -214,36 +214,38 @@ func (l *textShader) generateBufferContent(ren *RenderComponent, space *SpaceCom } offset := 20 * index + xoff := atlas.OffsetX[char] + yoff := atlas.OffsetY[char] // These five are at 0, 0: - setBufferValue(buffer, 0+offset, currentX, &changed) - setBufferValue(buffer, 1+offset, currentY, &changed) + setBufferValue(buffer, 0+offset, currentX+xoff, &changed) + setBufferValue(buffer, 1+offset, currentY+yoff, &changed) setBufferValue(buffer, 2+offset, atlas.XLocation[char]/atlas.TotalWidth, &changed) setBufferValue(buffer, 3+offset, atlas.YLocation[char]/atlas.TotalHeight, &changed) setBufferValue(buffer, 4+offset, tint, &changed) // These five are at 1, 0: - setBufferValue(buffer, 5+offset, currentX+atlas.Width[char]+letterSpace, &changed) - setBufferValue(buffer, 6+offset, currentY, &changed) + setBufferValue(buffer, 5+offset, currentX+xoff+atlas.Width[char]+letterSpace, &changed) + setBufferValue(buffer, 6+offset, currentY+yoff, &changed) setBufferValue(buffer, 7+offset, (atlas.XLocation[char]+atlas.Width[char])/atlas.TotalWidth, &changed) setBufferValue(buffer, 8+offset, atlas.YLocation[char]/atlas.TotalHeight, &changed) setBufferValue(buffer, 9+offset, tint, &changed) // These five are at 1, 1: - setBufferValue(buffer, 10+offset, currentX+atlas.Width[char]+letterSpace, &changed) - setBufferValue(buffer, 11+offset, currentY+atlas.Height[char]+lineSpace, &changed) + setBufferValue(buffer, 10+offset, currentX+xoff+atlas.Width[char]+letterSpace, &changed) + setBufferValue(buffer, 11+offset, currentY+yoff+atlas.Height[char]+lineSpace, &changed) setBufferValue(buffer, 12+offset, (atlas.XLocation[char]+atlas.Width[char])/atlas.TotalWidth, &changed) setBufferValue(buffer, 13+offset, (atlas.YLocation[char]+atlas.Height[char])/atlas.TotalHeight, &changed) setBufferValue(buffer, 14+offset, tint, &changed) // These five are at 0, 1: - setBufferValue(buffer, 15+offset, currentX, &changed) - setBufferValue(buffer, 16+offset, currentY+atlas.Height[char]+lineSpace, &changed) + setBufferValue(buffer, 15+offset, currentX+xoff, &changed) + setBufferValue(buffer, 16+offset, currentY+yoff+atlas.Height[char]+lineSpace, &changed) setBufferValue(buffer, 17+offset, atlas.XLocation[char]/atlas.TotalWidth, &changed) setBufferValue(buffer, 18+offset, (atlas.YLocation[char]+atlas.Height[char])/atlas.TotalHeight, &changed) setBufferValue(buffer, 19+offset, tint, &changed) - currentX += modifier * (atlas.Width[char] + letterSpace) + currentX += modifier * (atlas.Width[char] + letterSpace + xoff + atlas.RightSide[char]) } return changed diff --git a/script/toolchain.sh b/script/toolchain.sh index 5b82b777..d0b1961e 100755 --- a/script/toolchain.sh +++ b/script/toolchain.sh @@ -151,8 +151,6 @@ browserEnvironmentSetup() { # for build wasm info "install tools for build wasm" installNodeJsLTS - GO111MODULE=off go get github.com/gopherjs/gopherjs - GO111MODULE=off go get github.com/gopherjs/gopherwasm/js } developerEnvironmentSetup() {