Добавление поддержки новых игр.
Для того, чтобы добавить поддержку новой игры, нужно подготовить минимум .ini файл с описанием, картинку в формате png размером 450x150 и, если игра требует дополнительных телодвижений для запуска, то и shell-скрипт, который будет запускаться в конце установки и делать грязную работу.
Теперь, подробнее, по шагам.
Допустим, у вас есть .ipk файл с игрой mygame, и называется он наверняка com.vendor.app.mygame_1.0.0_all.ipk - это стандартный формат имени для .ipk файлов.
1) Копируем .ipk файл на телефон в папку /home/user/MyDocs/Downloads/
2) Создаем картинку иллюстрирующую игру, размером 450х150 в формате png, называем mygame.png и сохраняем на телефоне в /usr/share/wgames/gamesinfo/images/
3) В папке /usr/share/wgames/gamesinfo/ini создаем файл mygame.ini (или копируем из любого другого в этом каталоге).
Тут я остановлюсь подробнее. Содержимое нашего файла будет примерно таким:
===================================
Title=MyGame
Description="Long game description in English"
Description_ru_RU="Длинное описание игры на русском"
Genre=Action
PreviewImage=mygame.png
IPK_Name=com.vendor.app.mygame*_all.ipk
Space_Required=218
ID=com.gameloft.app.mygame
URL=http://www.vendor.com/mygame
Notes="Postinstall notes"
Notes_ru_RU="Заметки по игре, которые будут показываться после утсановки"
Preload="PowerVR:BIN_DIR"
Postinstall=mygame.sh
SaveFiles="savesettings,savegame"
Env="LD_LIBRARY_PATH=\".;$LD_LIBRARY_PATH\""
===================================
То, что выделено - это обязательные поля.
Title - название игры, как она будет отображаться в списке игр Менеджера.
Description и Description_ru_RU - описание игры на английском и русском. Добавление поддержки любого другого языка(например китайского) заключается в создании дополнительного поля вида Description_zn_CN, где zn_CN - стандартизированное название китайской локали. Чем полнее и интересней описание, тем лучше.
Genre - жанр игры, показывается в списке сразу под название игры.
PreviewImage - имя файла картинки, которую мы создали на шаге 2. Показывается в правой части Менеджера.
IPK_Name - маска файлов .ipk для данной игры. Хотя формат имени и достаточно строг, но мы должны узнавать все версии и возможные модификации игры, поэтому там где могут символы отличаться, ставим звездочку (*)
Space_Required - сколько требует места в Мегабайтах. Можно узнать, распаковав игру на компьютере командой:
ar x com.vendor.app.mygame_1.0.0_all.ipk data.tar.gz | tar xz -C .
и посмотрев сколько занимает места появившаяся папка. А можно написать любое близкое к размеру .ipk файла значение, и потом на телефоне проверить и исправить.
ID - уникальный идентификатор игры. Как правило совпадает с названием в имени файла. Но, бывает так (как, например, с игрой Monopoly), что разные игры содержат разные IDы - отличаются концовкой, к примеру. Поэтому это поле на самом деле обычный RegExp - чтобы подставить все возможные варианты с разной концовкой, дописывает в конце ".*". Вобщем, регексп он и в Африке регексп.
URL - собственно официальный адрес игры в интернете. Надеюсь, когда-нибудь тут будут ссылки на странички, на которых можно официально приобрести файл с игрой.
Дальше идут необязательные поля:
Notes и Notes_ru_RU - заметки, которые показываются после установки игры. Могут содержать предупреждение, советы по использовнию и всякое такое. По аналогии с полем Description, можно использовать локализованные тексты, добавляя _имя_локали к названию поля.
SaveFiles - файлы сейвов. Если указаны, то в окне управления сейвами появится возможность сохранять/восстанавливать сейвы. Формат - относительные пути файлов касательно каталога с бинарными данными(обычно /home/user/Games/MyGame/, можно несколько, через запятую. Например, если у нас в каталоге с игрой есть папка MyGameData и в ней два файла game.save и game.settings, то поле Saves должно иметь вид "MyGameData/game.save,MyGameData/game.settings".
Теперь интересные поля.
Postinstall - имя скрипта, который будет выполняться в конце инсталляции. Скрипты лежат в каталоге /usr/share/wgames/gamesinfo/hacks/. Для основы своего скрипта нужно взять скрипт /usr/share/wgames/gamesinfo/hacks/example.sh - там весь необходимый минимум есть. Первый параметр скрипта - install или uninstall, второй и третий - путь к каталогу с бинарными данными и путь к каталогу с данными игры.
Env - если игре нужно передать какие-то дополнительные переменные окружения, вписываем в это поле.
Preload - параметры LD_PRELOAD хака. Суть его в том, что если игра обращается по какому-то пути, которого нет или мы не имеем туда доступа (и не хотим иметь), мы можем ее обмануть и редиректить эти обращения на лету. Это делается путем перехвата вызова fopen(). Формат поля такой:
Preload="FROM_DIR:TO_DIR" - например "/media/internal/:BIN_DIR" - все обращения к файлам в каталоге /media/internal будут на самом деле обращениями к файлам с теми же именами в каталоге /home/user/Games/MyGame (BIN_DIR автоматически заменится на наш бинарный каталог, обычно это /home/user/Games/MyGame, а DATA_DIR заменится на каталог с данными - /home/user/MyDocs/Games/MyGame)
Есть еще специальный вариант этого хака для файлов в /etc/powervr.d/:
Preload="FROM_DIR:TO_DIR;PowerVR:BIN_DIR". - здесь PowerVR заменяет путь /etc/powervr.d/. Можно эти два пути комбинировать через точку с запятой, но пока только два. Если появится игра, где нужно больше путей заменять на лету - я допишу.
Собственно вот так.
4) Заходим в Менеджер (или выбираем "Обновить список" в меню) и пробуем установить игру. Если все ок - проверяем что она работает. Если не ок или не работает - идем в консоль, запускаем preenv, вооружаемся ldd, strace'ом, gdb и всем таким, находим проблему, и пишем все необходимые хаки в Postinstall и Preenv поля. Пробуем снова пока не получится.
5) Если все удачно и вы уверены, что можно этот .ini/.sh/.png использовать - выкладывайте тут на форуме, я проверю и добавлю к следующему обновлению.
Теперь несколько нюансов по тому, как прописывать хаки для игр. Рассмотрим разные случаи:
1) Игре нужен файл вида /etc/powervr.d/MyGame.ini с текстом
"[Default]
ForceExternalZBuffer=0"
Что делаем в таком случае:
В поле Preload добавляем значение "PowerVR:BIN_DIR", а в наш mygame.sh скрипт, в секцию install добавляем команду вроде
"echo -e "[default]\nForceExternalZBuffer=0\n" > ${BIN_DIR}/MyGame.ini"
2) Игра пытается открыть файл в несуществующем каталоге вроде /media/cryptofs или /media/internal или еще где-то.
В поле Preload добавляем значение "/media/internal/:BIN_DIR". Тут важно понимать, что часть пути, которая содержала /media/internal будет просто заменяться на BIN_DIR=/home/user/Games/MyGame/ - остальная часть пути будет оставаться такой же. Поддиректории по этому каталогу не создаются автоматически, если что.
3) Игре нужна дополнительная конфигурация через gconf.
Опять же, засовываем все такие команды (gconftool-2 --set .... /apps/preenv/MyGame ....) в наш mygame.sh в секцию install. Смотрите примеры в /usr/share/wgames/gamesinfo/hacks/
4) Всякие разные случаи. Например, как с Avatar'ом - он слинкован с библиотекой libavcodec.so, и не использует ни одной функции оттуда, но при этом падает если использовать родной maemo-вский libavcodec. Решение - слинковать его с пустой библиотекой с таким же именем - libavcodec.so.52. У preenv есть такая библиотека-пустышка - libstub.so, лежит в /opt/preenv/lib, но чтобы там создавать симлинк, нам тоже нужны права root, а их у нас нет. Поэтому выход следующий:
в mygame.sh создаем симлинк на libstub.so в каталоге BIN_DIR, а в поле Env прописываем путь "." в список путей поиска библиотеки: LD_LIBRARY_PATH=".;$LD_LIBRARY_PATH"
Теперь avatar ищет эту библиотеку в каталоге с бинарником, а там симлинк на libstub и все работает.
Если с другими играми возникнут какие-то проблемы, требующие решений, с которыми вышеописанные средства не справляются - пишите, будем придумывать.
Вот как-то так.
---
Быть мрачным и непонятным очень просто. Охрененно трудно быть добрым и ясным. (с) Стивен Содеберг.