2014-07-31 08:23:38 -04:00
|
|
|
// Copyright 2014 The Go Authors. All rights reserved.
|
|
|
|
// Use of this source code is governed by a BSD-style
|
|
|
|
// license that can be found in the LICENSE file.
|
|
|
|
|
2015-07-08 13:25:36 -06:00
|
|
|
package mobileinit
|
2014-07-31 08:23:38 -04:00
|
|
|
|
app: use one thread for both GL and other UI C code.
This change will break Darwin. I have only built and tested this on
desktop linux and Android linux. A follow-up CL will fix Darwin.
Currently, OpenGL gets its own thread, and UI C code (e.g. the Android
event loop, or the X11 event loop) gets its own thread. This relies on
multiple system-provided UI-related C libraries working nicely together,
even when running on different threads. Keeping all the C code on the
one thread seems more sound.
As side-effects:
- In package app/debug, DrawFPS now takes an explicit Config.
- In package app, some callbacks now take an explicit Config.
- In package exp/sprite, Render now takes an explicit Config.
- In package event, there are new events (Config, Draw, Lifecycle),
and an event filter mechanism to replace multiple app Callbacks.
- In package geom, the deprecated Width, Height and PixelsPerPt global
variables were removed in favor of an event.Config that is
explicitly passed around (and does not require mutex-locking).
Converting a geom.Pt to pixels now requires passing a pixelsPerPt.
- In package gl, the Do, Start and Stop functions are removed, as well
as the need to call Start in its own goroutine. There is no longer a
separate GL thread. Instead, package app explicitly performs any GL
work (gl.DoWork) when some is available (gl.WorkAvailable).
- In package gl/glutil, Image.Draw now takes an explicit Config.
Callbacks are no longer executed on 'the UI thread'.
Changing the app programming model from callbacks to events (since a
channel of events works with select) will be a follow-up change.
Change-Id: Id9865cd9ee1c45a98c613e9021a63c17226a64b1
Reviewed-on: https://go-review.googlesource.com/11351
Reviewed-by: David Crawshaw <crawshaw@golang.org>
2015-06-23 16:41:48 +10:00
|
|
|
/*
|
|
|
|
To view the log output run:
|
|
|
|
adb logcat GoLog:I *:S
|
|
|
|
*/
|
|
|
|
|
2014-07-31 08:23:38 -04:00
|
|
|
// Android redirects stdout and stderr to /dev/null.
|
|
|
|
// As these are common debugging utilities in Go,
|
|
|
|
// we redirect them to logcat.
|
|
|
|
//
|
|
|
|
// Unfortunately, logcat is line oriented, so we must buffer.
|
|
|
|
|
|
|
|
/*
|
2015-07-08 13:25:36 -06:00
|
|
|
#cgo LDFLAGS: -landroid -llog
|
|
|
|
|
2014-07-31 08:23:38 -04:00
|
|
|
#include <android/log.h>
|
|
|
|
#include <string.h>
|
|
|
|
*/
|
|
|
|
import "C"
|
|
|
|
|
|
|
|
import (
|
|
|
|
"bufio"
|
2014-08-21 16:06:11 -04:00
|
|
|
"log"
|
2014-07-31 08:23:38 -04:00
|
|
|
"os"
|
|
|
|
"unsafe"
|
|
|
|
)
|
|
|
|
|
2014-08-21 16:06:11 -04:00
|
|
|
var (
|
2015-07-09 12:12:06 +02:00
|
|
|
ctag = C.CString("GoLog")
|
2014-08-21 16:06:11 -04:00
|
|
|
)
|
|
|
|
|
|
|
|
type infoWriter struct{}
|
|
|
|
|
|
|
|
func (infoWriter) Write(p []byte) (n int, err error) {
|
|
|
|
cstr := C.CString(string(p))
|
2015-07-08 13:25:36 -06:00
|
|
|
C.__android_log_write(C.ANDROID_LOG_INFO, ctag, cstr)
|
2014-08-21 16:06:11 -04:00
|
|
|
C.free(unsafe.Pointer(cstr))
|
|
|
|
return len(p), nil
|
|
|
|
}
|
2014-07-31 08:23:38 -04:00
|
|
|
|
|
|
|
func lineLog(f *os.File, priority C.int) {
|
|
|
|
const logSize = 1024 // matches android/log.h.
|
|
|
|
r := bufio.NewReaderSize(f, logSize)
|
|
|
|
for {
|
|
|
|
line, _, err := r.ReadLine()
|
|
|
|
str := string(line)
|
|
|
|
if err != nil {
|
|
|
|
str += " " + err.Error()
|
|
|
|
}
|
|
|
|
cstr := C.CString(str)
|
|
|
|
C.__android_log_write(priority, ctag, cstr)
|
|
|
|
C.free(unsafe.Pointer(cstr))
|
|
|
|
if err != nil {
|
|
|
|
break
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func init() {
|
2014-08-21 16:06:11 -04:00
|
|
|
log.SetOutput(infoWriter{})
|
2014-10-23 09:55:09 -04:00
|
|
|
// android logcat includes all of log.LstdFlags
|
|
|
|
log.SetFlags(log.Flags() &^ log.LstdFlags)
|
2014-08-21 16:06:11 -04:00
|
|
|
|
2014-07-31 08:23:38 -04:00
|
|
|
r, w, err := os.Pipe()
|
|
|
|
if err != nil {
|
|
|
|
panic(err)
|
|
|
|
}
|
|
|
|
os.Stderr = w
|
|
|
|
go lineLog(r, C.ANDROID_LOG_ERROR)
|
|
|
|
|
|
|
|
r, w, err = os.Pipe()
|
|
|
|
if err != nil {
|
|
|
|
panic(err)
|
|
|
|
}
|
|
|
|
os.Stdout = w
|
|
|
|
go lineLog(r, C.ANDROID_LOG_INFO)
|
|
|
|
}
|