// Copyright 2017 The Ebiten Authors // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. //go:build example // +build example package main import ( "log" "strings" "github.com/hajimehoshi/ebiten/v2" "github.com/hajimehoshi/ebiten/v2/ebitenutil" "github.com/hajimehoshi/ebiten/v2/inpututil" ) const ( screenWidth = 640 screenHeight = 480 ) // repeatingKeyPressed return true when key is pressed considering the repeat state. func repeatingKeyPressed(key ebiten.Key) bool { const ( delay = 30 interval = 3 ) d := inpututil.KeyPressDuration(key) if d == 1 { return true } if d >= delay && (d-delay)%interval == 0 { return true } return false } type Game struct { runes []rune text string counter int } func (g *Game) Update() error { // Add runes that are input by the user by AppendInputChars. // Note that AppendInputChars result changes every frame, so you need to call this // every frame. g.runes = ebiten.AppendInputChars(g.runes[:0]) g.text += string(g.runes) // Adjust the string to be at most 10 lines. ss := strings.Split(g.text, "\n") if len(ss) > 10 { g.text = strings.Join(ss[len(ss)-10:], "\n") } // If the enter key is pressed, add a line break. if repeatingKeyPressed(ebiten.KeyEnter) || repeatingKeyPressed(ebiten.KeyNumpadEnter) { g.text += "\n" } // If the backspace key is pressed, remove one character. if repeatingKeyPressed(ebiten.KeyBackspace) { if len(g.text) >= 1 { g.text = g.text[:len(g.text)-1] } } g.counter++ return nil } func (g *Game) Draw(screen *ebiten.Image) { // Blink the cursor. t := g.text if g.counter%60 < 30 { t += "_" } ebitenutil.DebugPrint(screen, t) } func (g *Game) Layout(outsideWidth, outsideHeight int) (int, int) { return screenWidth, screenHeight } func main() { g := &Game{ text: "Type on the keyboard:\n", counter: 0, } ebiten.SetWindowSize(screenWidth, screenHeight) ebiten.SetWindowTitle("TypeWriter (Ebiten Demo)") if err := ebiten.RunGame(g); err != nil { log.Fatal(err) } }