适配 Korok 游戏到 MAC

适配 Korok 游戏到 MAC

前几天我们 Android 版本的 2048 小游戏上线了 GooglePlay,接下来就开始了 MAC 版本的适配,MAC 平台相对 Android 来说,更为简单,我们之前提供的文件、语言相关的方法都是跨平台的,所以 MAC 版本基本上没有多余的操作,直接打包构建二进制文件了。

回顾一下,做 Android 时候提供的平台相关的方法:

var lang = hid.Language()
var file = hid.FileDir()

在 MAC 上提供这些方法使用的是 Go 调用 Objec-C 实现的,中间使用 Cgo 作为中介。以语言为例,调用 Object-C 的代码大概如下:

/*
#cgo CFLAGS: -x objective-c
#cgo LDFLAGS: -framework Cocoa
#import <Cocoa/Cocoa.h>

#include <stdlib.h>
#include <string.h>

char* kk_getLanguage() {
	// get the current language and country config
	NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    NSArray *languages = [defaults objectForKey:@"AppleLanguages"];
    NSString *currentLanguage = [languages objectAtIndex:0];

    // get the current language code.(such as English is "en", Chinese is "zh" and so on)
    NSDictionary* temp = [NSLocale componentsFromLocaleIdentifier:currentLanguage];
    NSString * languageCode = [temp objectForKey:NSLocaleLanguageCode];

    //get uft8 string and copy it
	const char* str = [languageCode UTF8String];
	char * retString = strdup(str);
	return retString;
}

*/
import "C"
import (
	"unsafe"
)

func Language() string {
	return deviceAttr.Lang(func() string {
		var ret string
		cstring := C.kk_getLanguage()
		ret = C.GoString(cstring)
		C.free(unsafe.Pointer(cstring))
		return ret
	})
}

这样,我们的同一套代码也得到了复用。适配 MAC 的大部分工作集中到了打包环节。

如何构建一个 MAC 系统的可执行程序?

如果是 Go 语言的工程,使用 go build 既可以编译出一个可执行的二进制文件,比如我们的2048游戏,工程目录大概如下:

tree .
.
├── assets
│   ├── icon.png
│   └── simp.ttf
├── board.go
├── color.go
├── file.go
├── file_darwin.go
├── input.go
├── main.go
├── popup.go
├── text_font.go
└── tile.go

需要注意的是这样会编译出来的工程可能会存在一些兼容性的为,手动执行Build出来的二进制文件是没有问题的,但是到打包环节MAC会检测打包的二进制的兼容性,这需要在编译的时候指定MAC的最低兼容API版本既mmacosx-version-min=10.8,需要这么写:

$ CGO_CFLAGS=-mmacosx-version-min=10.8 \
  CGO_LDFLAGS=-mmacosx-version-min=10.8 \
  go build -ldflags -v *.go

这是 go 的一些原因导致的见 github.com/golang/go/is 有详细解释。

这个二进制文件还依赖 assets 目录,所以需要打包成 MAC 的可执行文件格式才方便分发。MAC 的可执行文件其实是一个以 .app 作为后缀名的文件夹,大概结构如下:

➜  cd The\ 2048\ Game.app 
➜  The 2048 Game.app tree Contents 
Contents
├── Info.plist
├── MacOS
│   └── 2048
├── Resources
│   ├── assets
│   │   ├── icon.png
│   │   └── simp.ttf
│   └── icon.icns
└── _CodeSignature
    └── CodeResources

其中,分为4个部分:

  1. Info.plist 配置文件,包含可执行文件名,ICON 等信息
  2. MacOS 存放可执行的二进制文件的地方
  3. Resources 资源目录
  4. _CodeSignature 签名信息,发布到 MAC STORE 才需要签名(可以不签)

这样,我们把用 go build 打包出来的二进制可执行文件复制到 MacOS 目录,把依赖的资源复制到 Resources 目录,基本上算是完成了。接下来需要给应用添加图标和配置文件,典型的 Info.plist 可以从一个MAC应用工程里面复制出来,然后做一些修改即可。比较关键的字段有:

  1. CFBundleExecutable 可执行二进制文件名字
  2. CFBundleIdentifier 包名,应用的唯一ID
  3. CFBundleIconFile Icon 文件的名字

其它的信息可以参考:

➜  Contents cat Info.plist 
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
	<key>CFBundleGetInfoString</key>
	<string>The 2048 Game</string>
	<key>CFBundleExecutable</key>
	<string>2048</string>
	<key>CFBundleIdentifier</key>
	<string>io.korok.2048</string>
	<key>CFBundleName</key>
	<string>The 2048 Game</string>
	<key>CFBundleIconFile</key>
	<string>icon.icns</string>
	<key>CFBundleShortVersionString</key>
	<string>1.0</string>
	<key>CFBundleVersion</key>
	<string>1.2</string>
	<key>CFBundleInfoDictionaryVersion</key>
	<string>6.0</string>
	<key>CFBundlePackageType</key>
	<string>APPL</string>
	<key>IFMajorVersion</key>
	<integer>0</integer>
	<key>IFMinorVersion</key>
	<integer>1</integer>
	<key>NSHighResolutionCapable</key>
	<true/>
	<key>NSSupportsAutomaticGraphicsSwitching</key>
	<true/>
	<key>LSApplicationCategoryType</key>
	<string>public.app-category.games</string>
	<key>NSHumanReadableCopyright</key>
	<string>Copyright © 2018 Korok.io. All rights reserved.</string>
	<key>LSMinimumSystemVersion</key>
	<string>10.9</string>
	<key>CFBundleDevelopmentRegion</key>
	<string>en</string>
</dict>
</plist>

然后就是应用图片,MAC 应用的图片文件是 icns 文件,其实是一个文件包含了多种分辨率的图标集合。MAC 提供了工具来自动生成 icns 文件,我用的是网上找到的一段脚本,提供了一个1024*1024的图标文件作为模板便可以生成 icns

如果这些信息都准备好了,复制到 .app 文件中,会发现文件夹的样子变成了:

这和MAC上的其它应用已经没有区别了。甚至直接 zip 之后就可以分发。但是如果需要上传到 Mac Store,那么还要做签名、打包 pkg 文件,这些工作属于 MAC 开发人员的日常,在此不表。


最后,欢迎大家下载体验我们MAC版本的2048小游戏,相比 Android 版本,重新设计了UI,添加了不同模式的选择:

可以选择 4X4/5X5/6X6 等不同的模式。

传送门:ntop.itch.io/the-2048-g


PS: 因为是2048题材,在上传MacStore的时候被拒绝了很多次,事实上我的硬盘里还有好几份修改版,2048中文版本/2048天干地支版/2048最简版.. 总之都被拒绝了,做这款游戏主要还是为了演示所以还是需要上传到一个地方,最后发现了 itch.io , 一个非常适合放原型游戏的地方。关于 MacStore/AppStore 欢迎有经验的同学再下面评论交流,因为我发现上面有很多山寨的游戏或者是直接从手机适配来的游戏但是确能审核通过,这是一件奇妙的事情。

编辑于 2018-08-23

文章被以下专栏收录