added documentation; added input event functions
This commit is contained in:
parent
95e59ccb5f
commit
1703c1a8fd
2 changed files with 221 additions and 24 deletions
140
sdlcanvas/keynames.go
Normal file
140
sdlcanvas/keynames.go
Normal file
|
@ -0,0 +1,140 @@
|
|||
package sdlcanvas
|
||||
|
||||
import "github.com/veandco/go-sdl2/sdl"
|
||||
|
||||
var keyMap [262]string
|
||||
|
||||
func init() {
|
||||
keyMap[sdl.SCANCODE_ESCAPE] = "Escape"
|
||||
keyMap[sdl.SCANCODE_0] = "Digit0"
|
||||
keyMap[sdl.SCANCODE_1] = "Digit1"
|
||||
keyMap[sdl.SCANCODE_2] = "Digit2"
|
||||
keyMap[sdl.SCANCODE_3] = "Digit3"
|
||||
keyMap[sdl.SCANCODE_4] = "Digit4"
|
||||
keyMap[sdl.SCANCODE_5] = "Digit5"
|
||||
keyMap[sdl.SCANCODE_6] = "Digit6"
|
||||
keyMap[sdl.SCANCODE_7] = "Digit7"
|
||||
keyMap[sdl.SCANCODE_8] = "Digit8"
|
||||
keyMap[sdl.SCANCODE_9] = "Digit9"
|
||||
keyMap[sdl.SCANCODE_MINUS] = "Minus"
|
||||
keyMap[sdl.SCANCODE_EQUALS] = "Equal"
|
||||
keyMap[sdl.SCANCODE_BACKSPACE] = "Backspace"
|
||||
keyMap[sdl.SCANCODE_TAB] = "Tab"
|
||||
keyMap[sdl.SCANCODE_Q] = "KeyQ"
|
||||
keyMap[sdl.SCANCODE_W] = "KeyW"
|
||||
keyMap[sdl.SCANCODE_E] = "KeyE"
|
||||
keyMap[sdl.SCANCODE_R] = "KeyR"
|
||||
keyMap[sdl.SCANCODE_T] = "KeyT"
|
||||
keyMap[sdl.SCANCODE_Y] = "KeyY"
|
||||
keyMap[sdl.SCANCODE_U] = "KeyU"
|
||||
keyMap[sdl.SCANCODE_I] = "KeyI"
|
||||
keyMap[sdl.SCANCODE_O] = "KeyO"
|
||||
keyMap[sdl.SCANCODE_P] = "KeyP"
|
||||
keyMap[sdl.SCANCODE_LEFTBRACKET] = "BracketLeft"
|
||||
keyMap[sdl.SCANCODE_RIGHTBRACKET] = "BracketRight"
|
||||
keyMap[sdl.SCANCODE_RETURN] = "Enter"
|
||||
keyMap[sdl.SCANCODE_LCTRL] = "ControlLeft"
|
||||
keyMap[sdl.SCANCODE_A] = "KeyA"
|
||||
keyMap[sdl.SCANCODE_S] = "KeyS"
|
||||
keyMap[sdl.SCANCODE_D] = "KeyD"
|
||||
keyMap[sdl.SCANCODE_F] = "KeyF"
|
||||
keyMap[sdl.SCANCODE_G] = "KeyG"
|
||||
keyMap[sdl.SCANCODE_H] = "KeyH"
|
||||
keyMap[sdl.SCANCODE_J] = "KeyJ"
|
||||
keyMap[sdl.SCANCODE_K] = "KeyK"
|
||||
keyMap[sdl.SCANCODE_L] = "KeyL"
|
||||
keyMap[sdl.SCANCODE_SEMICOLON] = "Semicolon"
|
||||
keyMap[sdl.SCANCODE_APOSTROPHE] = "Quote"
|
||||
keyMap[sdl.SCANCODE_GRAVE] = "Backquote"
|
||||
keyMap[sdl.SCANCODE_LSHIFT] = "ShiftLeft"
|
||||
keyMap[sdl.SCANCODE_BACKSLASH] = "Backslash"
|
||||
keyMap[sdl.SCANCODE_Z] = "KeyZ"
|
||||
keyMap[sdl.SCANCODE_X] = "KeyX"
|
||||
keyMap[sdl.SCANCODE_C] = "KeyC"
|
||||
keyMap[sdl.SCANCODE_V] = "KeyV"
|
||||
keyMap[sdl.SCANCODE_B] = "KeyB"
|
||||
keyMap[sdl.SCANCODE_N] = "KeyN"
|
||||
keyMap[sdl.SCANCODE_M] = "KeyM"
|
||||
keyMap[sdl.SCANCODE_COMMA] = "Comma"
|
||||
keyMap[sdl.SCANCODE_PERIOD] = "Period"
|
||||
keyMap[sdl.SCANCODE_SLASH] = "Slash"
|
||||
keyMap[sdl.SCANCODE_RSHIFT] = "RightShift"
|
||||
keyMap[sdl.SCANCODE_KP_MULTIPLY] = "NumpadMultiply"
|
||||
keyMap[sdl.SCANCODE_LALT] = "AltLeft"
|
||||
keyMap[sdl.SCANCODE_SPACE] = "Space"
|
||||
keyMap[sdl.SCANCODE_CAPSLOCK] = "CapsLock"
|
||||
keyMap[sdl.SCANCODE_F1] = "F1"
|
||||
keyMap[sdl.SCANCODE_F2] = "F2"
|
||||
keyMap[sdl.SCANCODE_F3] = "F3"
|
||||
keyMap[sdl.SCANCODE_F4] = "F4"
|
||||
keyMap[sdl.SCANCODE_F5] = "F5"
|
||||
keyMap[sdl.SCANCODE_F6] = "F6"
|
||||
keyMap[sdl.SCANCODE_F7] = "F7"
|
||||
keyMap[sdl.SCANCODE_F8] = "F8"
|
||||
keyMap[sdl.SCANCODE_F9] = "F9"
|
||||
keyMap[sdl.SCANCODE_F10] = "F10"
|
||||
keyMap[sdl.SCANCODE_PAUSE] = "Pause"
|
||||
keyMap[sdl.SCANCODE_SCROLLLOCK] = "ScrollLock"
|
||||
keyMap[sdl.SCANCODE_KP_7] = "Numpad7"
|
||||
keyMap[sdl.SCANCODE_KP_8] = "Numpad8"
|
||||
keyMap[sdl.SCANCODE_KP_9] = "Numpad9"
|
||||
keyMap[sdl.SCANCODE_KP_MINUS] = "NumpadSubtract"
|
||||
keyMap[sdl.SCANCODE_KP_4] = "Numpad4"
|
||||
keyMap[sdl.SCANCODE_KP_5] = "Numpad5"
|
||||
keyMap[sdl.SCANCODE_KP_6] = "Numpad6"
|
||||
keyMap[sdl.SCANCODE_KP_PLUS] = "NumpadAdd"
|
||||
keyMap[sdl.SCANCODE_KP_1] = "Numpad1"
|
||||
keyMap[sdl.SCANCODE_KP_2] = "Numpad2"
|
||||
keyMap[sdl.SCANCODE_KP_3] = "Numpad3"
|
||||
keyMap[sdl.SCANCODE_KP_0] = "Numpad0"
|
||||
keyMap[sdl.SCANCODE_KP_DECIMAL] = "NumpadDecimal"
|
||||
keyMap[sdl.SCANCODE_PRINTSCREEN] = "PrintScreen"
|
||||
keyMap[sdl.SCANCODE_NONUSBACKSLASH] = "IntlBackslash"
|
||||
keyMap[sdl.SCANCODE_F11] = "F11"
|
||||
keyMap[sdl.SCANCODE_F12] = "F12"
|
||||
keyMap[sdl.SCANCODE_KP_EQUALS] = "NumpadEqual"
|
||||
keyMap[sdl.SCANCODE_F13] = "F13"
|
||||
keyMap[sdl.SCANCODE_F14] = "F14"
|
||||
keyMap[sdl.SCANCODE_F15] = "F15"
|
||||
keyMap[sdl.SCANCODE_F16] = "F16"
|
||||
keyMap[sdl.SCANCODE_F17] = "F17"
|
||||
keyMap[sdl.SCANCODE_F18] = "F18"
|
||||
keyMap[sdl.SCANCODE_F19] = "F19"
|
||||
keyMap[sdl.SCANCODE_UNDO] = "Undo"
|
||||
keyMap[sdl.SCANCODE_PASTE] = "Paste"
|
||||
keyMap[sdl.SCANCODE_AUDIOPREV] = "MediaTrackPrevious"
|
||||
keyMap[sdl.SCANCODE_CUT] = "Cut"
|
||||
keyMap[sdl.SCANCODE_COPY] = "Copy"
|
||||
keyMap[sdl.SCANCODE_AUDIONEXT] = "MediaTrackNext"
|
||||
keyMap[sdl.SCANCODE_KP_ENTER] = "NumpadEnter"
|
||||
keyMap[sdl.SCANCODE_RCTRL] = "ControlRight"
|
||||
keyMap[sdl.SCANCODE_MUTE] = "AudioVolumeMute"
|
||||
keyMap[sdl.SCANCODE_AUDIOPLAY] = "MediaPlayPause"
|
||||
keyMap[sdl.SCANCODE_AUDIOSTOP] = "MediaStop"
|
||||
keyMap[sdl.SCANCODE_VOLUMEDOWN] = "AudioVolumeDown"
|
||||
keyMap[sdl.SCANCODE_VOLUMEUP] = "AudioVolumeUp"
|
||||
keyMap[sdl.SCANCODE_KP_DIVIDE] = "NumpadDivide"
|
||||
keyMap[sdl.SCANCODE_RALT] = "AltRight"
|
||||
keyMap[sdl.SCANCODE_HELP] = "Help"
|
||||
keyMap[sdl.SCANCODE_HOME] = "Home"
|
||||
keyMap[sdl.SCANCODE_UP] = "ArrowUp"
|
||||
keyMap[sdl.SCANCODE_PAGEUP] = "PageUp"
|
||||
keyMap[sdl.SCANCODE_LEFT] = "ArrowLeft"
|
||||
keyMap[sdl.SCANCODE_RIGHT] = "ArrowRight"
|
||||
keyMap[sdl.SCANCODE_END] = "End"
|
||||
keyMap[sdl.SCANCODE_DOWN] = "ArrowDown"
|
||||
keyMap[sdl.SCANCODE_INSERT] = "Insert"
|
||||
keyMap[sdl.SCANCODE_DELETE] = "Delete"
|
||||
keyMap[sdl.SCANCODE_APPLICATION] = "ContextMenu"
|
||||
}
|
||||
|
||||
func keyName(s sdl.Scancode) string {
|
||||
if int(s) >= len(keyMap) {
|
||||
return "Unidentified"
|
||||
}
|
||||
name := keyMap[s]
|
||||
if name == "" {
|
||||
return "Unidentified"
|
||||
}
|
||||
return name
|
||||
}
|
|
@ -14,6 +14,8 @@ import (
|
|||
"github.com/veandco/go-sdl2/sdl"
|
||||
)
|
||||
|
||||
// Window represents the opened window with GL context. The Mouse* and Key*
|
||||
// functions can be set for callbacks
|
||||
type Window struct {
|
||||
Window *sdl.Window
|
||||
GLContext sdl.GLContext
|
||||
|
@ -22,9 +24,17 @@ type Window struct {
|
|||
frameCount int
|
||||
fps float32
|
||||
close bool
|
||||
events []sdl.Event
|
||||
Event func(event sdl.Event)
|
||||
MouseDown func(button, x, y int)
|
||||
MouseMove func(x, y int)
|
||||
MouseUp func(button, x, y int)
|
||||
KeyDown func(scancode int, rune rune, name string)
|
||||
KeyUp func(scancode int, rune rune, name string)
|
||||
}
|
||||
|
||||
func CreateCanvasWindow(w, h int, title string) (*Window, *canvas.Canvas, error) {
|
||||
// CreateWindow creates a window using SDL and initializes the OpenGL context
|
||||
func CreateWindow(w, h int, title string) (*Window, *canvas.Canvas, error) {
|
||||
runtime.LockOSThread()
|
||||
|
||||
// init SDL
|
||||
|
@ -73,54 +83,87 @@ func CreateCanvasWindow(w, h int, title string) (*Window, *canvas.Canvas, error)
|
|||
wnd := &Window{
|
||||
Window: window,
|
||||
GLContext: glContext,
|
||||
events: make([]sdl.Event, 0, 100),
|
||||
}
|
||||
|
||||
return wnd, cv, nil
|
||||
}
|
||||
|
||||
// Destroy destroys the GL context and the window
|
||||
func (wnd *Window) Destroy() {
|
||||
sdl.GL_DeleteContext(wnd.GLContext)
|
||||
wnd.Window.Destroy()
|
||||
}
|
||||
|
||||
// FPS returns the frames per second (averaged over 10 frames)
|
||||
func (wnd *Window) FPS() float32 {
|
||||
return wnd.fps
|
||||
}
|
||||
|
||||
// Close can be used to end a call to MainLoop
|
||||
func (wnd *Window) Close() {
|
||||
wnd.close = true
|
||||
}
|
||||
|
||||
func (wnd *Window) IsClosed() bool {
|
||||
return wnd.close
|
||||
}
|
||||
|
||||
// StartFrame handles events and gets the window ready for rendering
|
||||
func (wnd *Window) StartFrame() error {
|
||||
for {
|
||||
ei := sdl.PollEvent()
|
||||
if ei == nil {
|
||||
break
|
||||
}
|
||||
switch e := ei.(type) {
|
||||
case *sdl.WindowEvent:
|
||||
if e.Event == sdl.WINDOWEVENT_CLOSE {
|
||||
wnd.close = true
|
||||
}
|
||||
case *sdl.KeyDownEvent:
|
||||
if e.Keysym.Scancode == sdl.SCANCODE_ESCAPE {
|
||||
wnd.close = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
err := sdl.GL_MakeCurrent(wnd.Window, wnd.GLContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
wnd.events = wnd.events[:0]
|
||||
for {
|
||||
event := sdl.PollEvent()
|
||||
if event == nil {
|
||||
break
|
||||
}
|
||||
|
||||
handled := false
|
||||
switch e := event.(type) {
|
||||
case *sdl.MouseButtonEvent:
|
||||
if e.Type == sdl.MOUSEBUTTONDOWN {
|
||||
if wnd.MouseDown != nil {
|
||||
wnd.MouseDown(int(e.Button), int(e.X), int(e.Y))
|
||||
handled = true
|
||||
}
|
||||
} else if e.Type == sdl.MOUSEBUTTONUP {
|
||||
if wnd.MouseUp != nil {
|
||||
wnd.MouseUp(int(e.Button), int(e.X), int(e.Y))
|
||||
handled = true
|
||||
}
|
||||
}
|
||||
case *sdl.MouseMotionEvent:
|
||||
if wnd.MouseMove != nil {
|
||||
wnd.MouseMove(int(e.X), int(e.Y))
|
||||
handled = true
|
||||
}
|
||||
case *sdl.KeyDownEvent:
|
||||
if wnd.KeyDown != nil {
|
||||
wnd.KeyDown(int(e.Keysym.Scancode), rune(e.Keysym.Unicode), keyName(e.Keysym.Scancode))
|
||||
handled = true
|
||||
}
|
||||
case *sdl.KeyUpEvent:
|
||||
if wnd.KeyUp != nil {
|
||||
wnd.KeyUp(int(e.Keysym.Scancode), rune(e.Keysym.Unicode), keyName(e.Keysym.Scancode))
|
||||
handled = true
|
||||
}
|
||||
}
|
||||
|
||||
if !handled && wnd.Event != nil {
|
||||
wnd.Event(event)
|
||||
handled = true
|
||||
}
|
||||
|
||||
if !handled {
|
||||
wnd.events = append(wnd.events, event)
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// FinishFrame updates the FPS count and displays the frame
|
||||
func (wnd *Window) FinishFrame() {
|
||||
now := time.Now()
|
||||
wnd.frameTimes[wnd.frameIndex] = now
|
||||
|
@ -136,7 +179,8 @@ func (wnd *Window) FinishFrame() {
|
|||
sdl.GL_SwapWindow(wnd.Window)
|
||||
}
|
||||
|
||||
func (wnd *Window) MainLoop(drawFunc func()) {
|
||||
// MainLoop runs a main loop and calls run on every frame
|
||||
func (wnd *Window) MainLoop(run func()) {
|
||||
// main loop
|
||||
for !wnd.close {
|
||||
err := wnd.StartFrame()
|
||||
|
@ -145,7 +189,20 @@ func (wnd *Window) MainLoop(drawFunc func()) {
|
|||
continue
|
||||
}
|
||||
|
||||
drawFunc()
|
||||
for _, event := range wnd.events {
|
||||
switch e := event.(type) {
|
||||
case *sdl.WindowEvent:
|
||||
if e.Event == sdl.WINDOWEVENT_CLOSE {
|
||||
wnd.close = true
|
||||
}
|
||||
case *sdl.KeyDownEvent:
|
||||
if e.Keysym.Scancode == sdl.SCANCODE_ESCAPE {
|
||||
wnd.close = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
run()
|
||||
|
||||
wnd.FinishFrame()
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue