前言
GNU/Linux 不是 Objective-C 的官方平台,無法使用 Cocoa,只能使用其仿作品 GNUstep。但不同 GNU/Linux 發行版對 GNUstep 支援程度相異,本文把實際建置 Objective-C 開發環境的過程記下來,供有需要的讀者參考。
使用系統套件管理軟體安裝 GNUstep
使用系統套件管理軟體安裝 GNUstep 是最快的方式,只是其版本號可能會略為滯後。如果不在意 GNUstep 的最新特性的話,使用預編好的 GNUstep 即可。
Ubuntu
使用以下指令即可安裝:
$ sudo apt install gnustep gnustep-devel
openSUSE
使用以下指令即可安裝:
$ sudo zypper install gnustep-base gnustep-base-devel
目前 openSUSE Leap 15.2 只提供 GNUstep Base 物件庫相關的套件,能寫的程式形態較受限。其他 GNUstep 相關套件則放在實驗性質的套件庫,需自行加入套件庫後再安裝。
CentOS
CentOS 在第 8 版後移除掉 GNUstep 了,無法透過官方套件庫取得。
支援 Objective-C 的編輯器
由於 GNU/Linux 不是開發 Objective-C 的主要平台,沒有什麼 IDE 可用。Atom 和 VSCode 對 Objective-C 提供基本的支援,讀者可擇一使用。
自行編譯 GNUstep 原始碼
如果想要使用最新版本的 GNUstep,可以試著自行編譯 GNUstep。但不是每個 GNU/Linux 發行版都能順利編譯。目前實際編譯的結果是 Ubuntu 可完整編譯;openSUSE 僅能編譯 GNUstep Base 物件庫;CentOS 過於困難故放棄。細節請看下文。
有些讀者可能看過本文先前的版本,但無法順利編譯 GNUstep。由於筆者已經重新編譯過 GNUstep 並修改文章了,讀者可重讀本文,試著編譯 GNUstep 看看。
前置作業
在前置作業中會用到 git(1)
和 wget(1)
,請自行安裝。以 Ubuntu 為例:
$ sudo apt install wget git
以 openSUSE 為例:
$ sudo zypper install wget git
下載編譯 GNUstep 的 shell 命令稿:
$ wget -c https://raw.githubusercontent.com/gnustep/tools-scripts/master/compile-all
若讀者使用 Ubuntu,需額外下載安裝相依套件的 shell 命令稿:
$ wget -c https://raw.githubusercontent.com/gnustep/tools-scripts/master/install-dependencies-linux
若讀者使用 openSUSE,可參考筆者寫的 shell 命令稿。這個命令稿仿造前述命令稿,在 openSUSE 上自動安裝 GNUstep 的相依套件。
筆者未為 CentOS 撰寫自動安裝相依性的命令稿,有興趣的讀者可自嘗試手動安裝。
若使用 Clang 來編譯 GNUstep 的話,還要額外下載此專案:
$ git clone https://github.com/gnustep/tools-scripts.git
因為在安裝過程中會用到一個 shell 命令稿。
到各個專案去下載最近穩定版的專案原始碼:
$ wget -c https://github.com/gnustep/tools-make/releases/download/make-2_8_0/gnustep-make-2.8.0.tar.gz
$ wget -c https://github.com/gnustep/libs-base/releases/download/base-1_27_0/gnustep-base-1.27.0.tar.gz
$ wget -c https://github.com/gnustep/libs-gui/releases/download/gui-0_28_0/gnustep-gui-0.28.0.tar.gz
$ wget -c https://github.com/gnustep/libs-back/releases/download/back-0_28_0/gnustep-back-0.28.0.tar.gz
其實也可以從各個專案直接拷貝 master 分支的原始碼來用,但 master 分支的原始碼沒那麼穩定,有興趣嘗鮮的讀者可自行嘗試。
此外,也要拷貝此專案:
$ git clone https://github.com/gnustep/plugins-session.git
這個專案其實只是一些簡單的設定而已。
把各個專案的目錄名稱整理一下:
$ tar xf gnustep-make-2.8.0.tar.gz
$ mv gnustep-make-2.8.0 tools-make
$ tar xf gnustep-base-1.27.0.tar.gz
$ mv gnustep-base-1.27.0 libs-base
$ tar xf gnustep-gui-0.28.0.tar.gz
$ mv gnustep-gui-0.28.0 libs-gui
$ tar xf gnustep-back-0.28.0.tar.gz
$ mv gnustep-back-0.28.0 libs-back
這是為了配合 compile-all 命令稿所指定的目錄,不要死背這些目錄的名稱。
在 Ubuntu 安裝相依性
執行以下 shell 命令稿即可:
$ chmod +x install-dependencies-linux
$ ./install-dependencies-linux
在 openSUSE 安裝相依性
參考筆者自行撰寫的 shell 命令稿 即可。
在 CentOS 安裝相依性
筆者後來放棄在 CentOS 上建置 Objective-C 開發環境,因為 CentOS 8 連 Objective-C 編譯器的套件都移除了。想到要從編譯編譯器本身開始,從頭打造整個開發環境的過程,就懶了。此外,編譯器是系統的重要軟體,儘量用系統內建的版本,對系統穩定性會比較好。
編譯 GNUstep
使用以下指令,會以 GCC 來編譯 GNUstep:
$ chmod +x compile-all
$ ./compile-all
在非蘋果平台上撰寫 GNUstep 程式多是使用 GCC。如果讀者想用一些 Clang 所帶來的新語法特性,可以改用以下指令:
$ ./compile-all /usr/GNUstep clang clang++
筆者在 openSUSE 上編譯 GNUstep 時,只能順利編譯 GNUstep Base 物件庫。GNUstep GUI 會因 ImageMagick 相關的議題無法編譯,連帶 GNUstep Backend 也無法順利編譯。
自動載入 GNUstep 開發環境
手動將以下指令加入 shell 的個人設定檔即可:
. /usr/GNUstep/System/Library/Makefiles/GNUstep.sh
編譯第一個 Objective-C 程式
若讀者順利地建置 GNUstep 開發環境,可以寫個小程式來測試一下該環境是否可用。
用編輯器建立 hello.m 文字檔案,加入以下內容:
#import <Foundation/Foundation.h>
#define PRINT(FORMAT, ...) \
fprintf(stdout, "%s\n", \
[[NSString stringWithFormat:FORMAT, ##__VA_ARGS__] UTF8String]);
int main(void)
{
NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
if (!pool)
return 1;
PRINT(@"Hello World");
[pool release];
return 0;
}
現階段的重點在於熟悉開發環境,暫時不了解程式碼的意義無妨。
使用以下指令來編譯上述程式:
$ gcc -o hello hello.m -lobjc -lgnustep-base -I /usr/GNUstep/System/Library/Headers -L /usr/GNUstep/System/Library/Libraries -fconstant-string-class=NSConstantString
由於 GNUstep 未位於編譯器的標準位置上,要額外設置 LD_LIBRARY_PATH
環境變數才能順利連結 GNUstep 物件庫的二進位檔。參考以下指令:
$ LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/GNUstep/System/Library/Libraries ./hello
Hello World