Human Factors of XR: Using Human Factors to Design XR Systems
Mobile Apps by Pure Go with Reverse Binding
1. Mobile Apps
by Pure Go
with Reverse Binding
GopherCon India
22nd Feb. 2017
The Go gopher was designed by Renee French.
The gopher stickers was made by Takuya Ueda.
Licensed under the Creative Commons 3.0
Attributions license.
Slide URL: https://goo.gl/OG55gT
2. Slide URL: https://goo.gl/OG55gT
Who am I?
Mercari, Inc./Souzoh, Inc.
Takuya Ueda
twitter: @tenntenn
■ Communities
Google Cloud Platform User Group (GCPUG) Tokyo
Go Beginners in Tokyo, Japan
golang.tokyo
Go Conference in Tokyo, Japan
■ Works
Developing Mercari Atte in GAE/Go
2
3. Slide URL: https://goo.gl/OG55gT
What is this talk about?
● The Basics of Go Mobile
○ Cross-compile / cgo for Android
○ What is Go Mobile?
○ SDK Apps and Native Apps
● Developing Android Apps in pure Go
○ gomobile bind
○ What is Reverse Bindings?
○ Use Platform APIs from Go
3
5. Slide URL: https://goo.gl/OG55gT
Cross-compile
● GOOS and GOARCH
○ Go can cross-compile
○ GOOS indicates target OS
○ GOARCH indicates target architecture
5
# Build for 32bit Windows
$ GOOS=windows GOARCH=386 go build
# Build for arm Linux
$ GOOS=linux GOARCH=arm go build
A linux/arm binary also works on android devices.
7. Slide URL: https://goo.gl/OG55gT
cgo
● C codes into Go codes
7
import "unsafe"
/*
#include <stdio.h>
#include <stdlib.h>
void hello(char *s) { printf("Hello, %sn", s); }
*/
import "C"
func main() {
str := C.CString("GopherCon India")
C.hello(str)
C.free(unsafe.Pointer(str))
}
Comments before import "C"
would be built as C codes
Call C’s function from Go code
8. Slide URL: https://goo.gl/OG55gT
cgo for Android
● cgo codes also can be cross-compiled
8
$ CGO_ENABLED=1
CC=arm-linux-androideabi-gcc
GOOS=android
GOARCH=arm
GOARM=7
go build -buildmode=pie hellocgo.go
$ adb push hellocgo /data/local/tmp
$ chmod 755 /data/local/tmp/hellocgo
$ /data/local/tmp/hellocgo
Hello, GopherCon India
GOOS should be android
when CGO_ENABLED is 1.
Enable cgo at cross-compiling
adb shell
PC
9. Slide URL: https://goo.gl/OG55gT
buildmode
● Change output formats
○ archive, c-archive
■ build into C archive (.a file)
○ shared, c-shared
■ build into shared library (.so file)
○ plugin
■ bulid into Go Plugin (<= Go 1.8)
○ exe
■ build into executable file
○ pie
■ build into PIE style executable file
9
archive and
shared ignore
main package
Go can build to .so files for Android
10. Slide URL: https://goo.gl/OG55gT
Go Mobile
● What is Go Mobile?
○ Go Mobile is a toolkit for Mobile Platform
(Android and iOS) in Go.
● How Go Mobile works?
○ Go Mobile provides bindings of Android
and iOS through cgo.
10
Go C
Java
Obj-C
JNIcgo
Android
iOS
12. Slide URL: https://goo.gl/OG55gT
Installation
● Install gomobile comand
● Initialize the build tool chain
○ gomobile init initializes the build tool
chain for mobile apps.
12
$ gomobile init -v
$ ls $GOPATH/pkg/gomobile
android_ndk_root pkg_android_amd64
pkg_android_arm64 pkg_darwin_arm version
pkg_android_386 pkg_android_arm
pkg_darwin_amd64 pkg_darwin_arm64
$ go get -u golang.org/x/mobile/cmd/gomobile
13. Slide URL: https://goo.gl/OG55gT
gomobile command
gomobile command provides sub-commands.
● Sub-commands
13
bind build a library for Android and iOS
build compile Android APK and iOS app
clean remove object files and cached gomobile files
init install android compiler toolchain
install compile android APK and install on device
version print version
14. Slide URL: https://goo.gl/OG55gT
SDK Apps and Native Apps
Go Mobile provides two ways to develop mobile
apps.
■ SDK Apps
● Write common funcations in Go as a
library
■ Native Apps
● Write UI and all codes in Go
14
15. Slide URL: https://goo.gl/OG55gT
SDK Apps and Native Apps
● SDK Apps for Android
● Native Apps for Android
15
Go
aar file
Binding Classes (Java)
Shared library (.so)
Java
UI, IAB, ...
As a library
gomobile bind
apk file
Go
GoNativeActivity
Shared library (.so)UI, audio, ...
gomobile build
16. Slide URL: https://goo.gl/OG55gT
An Example of SDK Apps: Ivy
● Ivy big number calculator (source code)
○ Interpriter for APL-like language
○ Android App and iOS App use a same engine
○ The engine is written in Go by Rob Pike
16
Google Play App Store
17. Slide URL: https://goo.gl/OG55gT
An Example of Native Apps
● Flappy Gopher
○ A mobile game written in Go Mobile
○ Developed by Andrew Gerrand
for Go Conference 2015 Winter
○ Source Code
17
19. Slide URL: https://goo.gl/OG55gT
gomobile bind
● Generate an Android Archive (.aar)
○ a shared library (.so) written in Go
○ a JAR file which is bult Java bindings
● Develop with Android Studio Plugin
○ Runs gomobile bind
○ Links to a generated .aar file
19
$ gomobile bind [-target ios|android] mypkg
21. Slide URL: https://goo.gl/OG55gT
Calling Go code from Java code
21
Bindings
Java codes
Application Codes
(Java)
C codes
Go/cgo codes
JNI Generated by
gomobile bind
SDK Codes
(Go)
cgo
22. Slide URL: https://goo.gl/OG55gT
An Example of Bindings
22
package sample
func Hello() string { return "Hello" }
type MyStruct struct { Str string }
func (s MyStruct) MyMethod() string { return s.Str }
public abstract class Sample {
// ...
private Sample() {} // uninstantiable
public static final class MyStruct extends Seq.Proxy {
public final native String getStr();
public final native void setStr(String v);
public native String MyMethod();
// ...
}
public static native String Hello();
}
Java
Go
Struct
Field
Method
Package Function
23. Slide URL: https://goo.gl/OG55gT
Type restrictions
● Signed integer and floating point type
● String and boolean type
● Byte slice type
● Any functions
○ parameter and result types must be supported types
○ results are 0, 1 or 2 (2nd result must be an error
type)
● Any struct type
○ all fields and methods must be supported types
● Any interface
○ all methods must be supported types
23
24. Slide URL: https://goo.gl/OG55gT
Calling Platform API from Go
● In-app Billing
○ Purchase a items in the game
● SNS connection
○ Facebook, Twitter, ...
● Advertisements
● Analytics
○ Google Analytics, Firebase, Facebook
Analytics,...
24
These APIs are provided
as Java SDK for Android
25. Slide URL: https://goo.gl/OG55gT
Traditional gomobile bind
● Bindings to Go from Java/Obj-C
● Platform APIs can be accessed BUT...
○ Indirect way
○ Needs wrappers
○ Not convenient
25
A way to access directly
Platform APIs from Go is needed!
26. Slide URL: https://goo.gl/OG55gT
Reverse Bindings
● Access Platform APIs from Go
● Generate bindings automatically
○ Reverse direction of traditional one
○ use gomobile bind
● Prposed by #16876 and #17102
(Android) (iOS)
26
28. Slide URL: https://goo.gl/OG55gT
An Example of Reverse Bindings
28
package pkg
import "Java/java/lang"
import "Java/pkg"
type Obj struct {
lang.Object
}
func (h *Obj) ToString(this *pkg.Obj) string {
return "hoge"
}
● Parse import statements
○ Java/* or ObjC/*
● Generate bindings automatically
corresponds java.lang
package in Java
inherit java.lang.Object
Hold a Java instance
29. Slide URL: https://goo.gl/OG55gT
How Generate Reverse Bindings?
● Parse import statements
○ Begin with Java/
● Extract class infomation by javap
○ Exported fields and methods
○ Dependent classes
○ Implementing interfaces
● Generate bindings of all dependented
classes and interfaces
29
$ javap java.lang.String
Compiled from "String.java"
public final class java.lang.String implements java.io.Serializable,
java.lang.Comparable<java.lang.String>, java.lang.CharSequence {
public static final java.util.Comparator<java.lang.String>
CASE_INSENSITIVE_ORDER;
public java.lang.String();
....
30. Slide URL: https://goo.gl/OG55gT
Using Platform APIs from Go
● Example of Reverse Binding in x/mobile
30
$ cd $GOPATH/src/golang.org/x/mobile
$ cd example/reverse/android
$ gradle wrapper
$ ./gradlew build
$ cd build/outputs/apk
$ adb install -r android-debug.apk
Android Studio
also can build
31. Slide URL: https://goo.gl/OG55gT
Use Platform APIs from Go
● Use Activity and write in life cycle of
Android
31
type MainActivity struct {
app.AppCompatActivity
binding databinding.ActivityMainBinding
}
func (a *MainActivity) OnCreate(
this gopkg.MainActivity, b os.Bundle) {
...
}
func (a *MainActivity) OnDestroy(
this gopkg.MainActivity) {
...
}
reverse.go
32. Slide URL: https://goo.gl/OG55gT
Use Platform APIs from Go
● Use data binding of Android
32
func (a *MainActivity) OnCreate(
this gopkg.MainActivity, b os.Bundle) {
this.Super().OnCreate(b)
db := DataBindingUtil.SetContentView(
this, rlayout.Activity_main)
a.binding = ActivityMainBinding.Cast(db)
a.binding.SetAct(this)
}
func (a *MainActivity) GetLabel() string {
return "Hello, GopherCon India!"
}
reverse.go
33. Slide URL: https://goo.gl/OG55gT
Use Platform APIs from Go
● Use data binding of Android
33
...
<data>
<variable name="act"
type="reverse.MainActivity"/>
</data>
<RelativeLayout ...
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{act.label}"/>
</RelativeLayout>
</layout>
activity_main.xml
34. Slide URL: https://goo.gl/OG55gT
Summaries
● The Basics of Go Mobile
○ Cross-compile / cgo for Android
○ What is Go Mobile?
○ SDK Apps and Native Apps
● Developing Android Apps in pure Go
○ gomobile bind
○ What is Reverse Bindings?
○ Use Platform APIs from Go
34
36. Slide URL: https://goo.gl/OG55gT
Binding between Go and Java
36
Package Abstruct Class
Struct Inner Class
Struct Field
Getter/Setter
(Native)
Method Method
(Native)
Package Function Static Method
Go Java
● gomobile bind generates bindings