[原創]使用命令行工具提高cocos2d-x開發效率(一)之TexturePacker篇

TexturePacker是一個經常使用的製做sprite sheet的工具,它提供了不少實用的功能。html

通常咱們製做sprite sheet都是使用他的gui版本,純手工操做,就像下面這張圖示的同樣。ios

剛開始咱們的項目也是使用這種方式,但後來發現這種方式在開發中有很大的問題。隨着圖片的增多,sprite sheet會愈來愈多,爲了生成這些sprite sheet須要作不少重複的手工勞動,再考慮到給Android平臺打包的sprite sheet配置和iOS的不一樣,還有包括圖片變動,配置優化等狀況,算下來光打包sprite sheet就須要巨大的工做量,這還不考慮因爲手工誤操做形成的各類問題。web

因而我就考慮,如何儘量地減小打包sprite sheet的工做量,提升開發的效率。後來經過搜索,看到raywenderlich上一篇關於使用TexturePacker的文章,裏面比較詳細地介紹了TexturePacker的用法,特別還提到了它的命令行工具的使用以及這個工具和xcode的集成,這給了我想要的答案。xcode

接下來說一下我在項目中如何使用這個TexturePacker的命令行工具以及實用它的一些經驗。bash

---------------------------------------正式開始的分割線-----------------------------------------app

具體下載和安裝TexturePacker以及它命令行工具的方法就不說了,上面提到的那篇文章裏有較詳細的說明。一些準備就緒後,咱們能夠在命令行裏執行texturepacker命令,正常狀況下你將會看到texturepacker的各類參數以及使用方法的說明,以下圖:ide

接下來爲了方便說明,咱們新建一個測試工程foo,這裏以quick-cocos2d-x-2.2.1-rc引擎建立的工程爲例,建立好後目錄結構以下圖:工具

咱們須要一個目錄去保存全部原始的(未打到sprite sheet裏的)圖片,這裏咱們新建個目錄叫originalImages,而後找些圖片,丟進這個目錄,並將他們分類到不一樣的文件夾,接着咱們再建立一個目錄,用來存放咱們打包sprite sheet的腳本工具,咱們起名叫tools,而後,咱們再建立一個目錄spriteSheets,用於存放打好的圖片,最後,通常咱們會將工程用到的圖片存放到res/images目錄裏面,因此爲了清楚,再建立一個這個文件夾,最終目錄結構以下圖所示:測試

接下來我說一下思路,咱們的腳本工具存放在tools文件夾中,運行以後會去遍歷originalImages這個目錄下的全部文件夾,而後將每一個文件夾中的圖片打包爲一個sprite sheet,這個sprite sheet名字與該文件夾的名字相同,接着將打包後的sprite sheet文件複製兩份,一份存入spriteSheets目錄中,另外一份拷貝到咱們程序使用圖片的目錄。優化

舉例來講,當我運行腳本,會生成三份sprite sheet,分別是button.png,button.plist,checkBox.png,checkBox.plist,common.png,common.plist,他們分別會存放入spriteSheets目錄和res目錄下的images目錄中(通常res目錄下的images目錄用來存放程序中用到的圖片)。

---------------------------------------漸入佳境的分割線------------------------------------------

好的,一切準備就緒,咱們開始說說這個腳本究竟要如何編寫。

首先咱們須要大概瞭解一下texturepacker的一些經常使用參數。

--format

指定sprite sheet的格式,默認是cocos2d,作cocos2d-x項目的話,就選cocos2d就行。可選的選項以下:

--texture-format

很是重要的一個屬性,指定texture的格式。若是咱們作iOS上的遊戲,通常都會使用PVR,由於這個format的texture是專門爲蘋果iPhone和iPad的圖形處理器優化的,而Android由於設備硬件多種多樣,因此咱們通常可能會選用png格式的,感興趣的朋友能夠本身搜索一下相關內容。這個參數若是不指定值的話texturepacker會嘗試去根據sprite sheet的命名來自動選擇一個合適的format。具體的選項以下:

--data

指定data文件的名字,也就是plist文件的名字

--sheet

sprite sheet文件的名字

--enable-rotation

是否開啓旋轉。通常咱們會開啓,爲了更有效率的將散圖打在一塊兒。

--scale

在建立sprite sheet以前爲全部散圖作一個調整scale的操做,好比,若是是0.5,那麼就把原始圖都壓縮通常大小,再存入sprite sheet中

--shape-padding

設置每一個圖片在sprite sheet中的間隔,默認是2

--max-size

sprite sheet的最大尺寸,你不可能將全部圖片都打入到一張sprite sheet裏,由於沒有設備能支持這樣的sprite sheet,因而須要限定大小:)。

--opt

這個是很重要的一個屬性,決定了sprite sheet的像素格式,這個屬性能夠很大程序改變sprite sheet所佔的內存。經常使用的選項以下:

--trim

爲了能在一張sprite sheet加入更多的圖片,裁減掉原始圖片的空白像素,可是使用的時候仍是按照圖片的原始尺寸來使用。

--smart-update

智能更新,爲了不重複生成相同內容的sprite sheet,texturepacker會檢查現存的sprite sheet和將要生成的sprite sheet內容是否相同,若是不一樣再生成新的,若是相同則不生成。

---------------------------------------激動人心的分割線------------------------------------------

好了,最後激動人心的時刻到了,咱們上腳本!(腳本寫的通常,多包涵)

 1 #! /bin/bash
 2 
 3 CURRENT_DIR=`dirname $0`
 4 
 5 # input paths
 6 IMAGE_DIR=$CURRENT_DIR/../originalImages
 7 
 8 # path that game proj use
 9 GAME_IMAGE_PATH=$CURRENT_DIR/../res/images
10 
11 # temporary path to place the sprite sheets
12 OUTPUT_PATH=$CURRENT_DIR/../spriteSheets
13 OUTPUT_PATH_PVR=$OUTPUT_PATH/packagedPVR
14 OUTPUT_PATH_PNG=$OUTPUT_PATH/packagedPNG
15 
16 # path of the texture packer command line tool
17 TP=/usr/local/bin/TexturePacker
18 
19 # $1: Source Directory where the assets are located
20 # $2: Output File Name without extension
21 # $3: RGB Quality factor
22 # $4: Scale factor
23 # $5: Max-Size factor
24 # $6: Texture Type (PNG, PVR.CCZ)
25 # $7: Texture format
26 pack_textures() {
27 
28     ${TP} --smart-update \
29         --texture-format $7 \
30         --format cocos2d \
31         --data "$2".plist \
32         --sheet "$2".$6 \
33         --maxrects-heuristics best \
34         --enable-rotation \
35         --scale $4 \
36         --shape-padding 1 \
37         --max-size $5 \
38         --opt "$3" \
39         --trim \
40         $1/*.png 
41 
42 }
43 
44 # check the output path
45 
46 if [ -d $OUTPUT_PATH ];then
47     :
48 else
49     mkdir $OUTPUT_PATH
50 fi
51 
52 if [ -d $OUTPUT_PATH_PVR ]
53 then
54     :
55 else
56     mkdir $OUTPUT_PATH_PVR
57 fi
58 
59 if [ -d $OUTPUT_PATH_PNG ]
60 then
61     :
62 else
63     mkdir $OUTPUT_PATH_PNG
64 fi
65 
66 # do the job
67 for i in $IMAGE_DIR/*
68 do
69     if [ -d $i ] 
70     then
71         spriteSheetName=`basename $i`
72         pack_textures $i $OUTPUT_PATH_PNG/$spriteSheetName 'RGBA8888' 1 2048 'png' "png"
73         pack_textures $i $OUTPUT_PATH_PVR/$spriteSheetName 'RGBA8888' 1 2048 'pvr.ccz' "pvr2ccz"
74     fi
75 done
76 
77 # cp them to the game proj image path
78 
79 cp -f $OUTPUT_PATH_PVR/* $GAME_IMAGE_PATH

將腳本的內容保存到一個文件中,命名後把後綴改成command,好比我是這個樣子的:

而後記得在命令行裏改一下腳本的權限,最後雙擊一下腳本,新鮮的sprite sheets就打包出來了,若是有什麼圖片的改動,只須要修改originalImages這個目錄下的圖片,而後雙擊一下腳本,新的sprite sheet就生成好了,再也沒有了無聊煩人的手工勞動,向TP的GUI說再見吧!是否是很爽?:)

----------------------------------------最後的分割線-----------------------------------------

最後簡單說一下在腳本里咱們作的事情:

在腳本中咱們針對originalImages裏面每個文件夾中的圖,生成了兩份sprite sheet,這兩份惟一的區別是一份是pvr2ccz格式的,一份是png格式的,其餘的屬性都相同:像素格式RGBA8888,scale爲1,最大尺寸爲2048*2048。在生成完成後,將全部的sprite sheet拷貝到了spriteSheets這個文件夾,並把其中pvr格式的sprite sheet拷貝到了咱們工程使用的圖片目錄裏。

OK,大概就是這樣子,那個腳本能夠根據項目具體需求去改,我寫的很簡單,也沒加什麼log,這個其實徹底能夠寫得更智能話寫,這就留給各位去發揮了。

 

 ----------------------------------一些更新和補充----------------------------------------

最近有園子裏的朋友和我交流了幾個問題,我以爲其中有2個挺不錯的,具體交流的內容在本文的留言裏面有,不過爲了方便你們查閱,我把它們整理(其實主要是截圖,我是有多懶=。=)了一下,整合到這個篇文章中:

問題1:來自園友 tanyongdahaoren

 

答案:

這個問題回答的比較明確,我就不過多解釋了:)

(這裏忍不住吐槽一下博客園的插入代碼功能,在回覆裏面沒有bash的選項不說,在文章中bash的代碼明顯沒有按照bash的腳本着色,「/*」居然按照註釋理解了,真心汗一個)

問題2:來自園友sousou123

 

這個園友主要的想法是考慮如何用TexturePacker把單張的png圖片轉換成pvr格式的圖片。我一開始建議它用蘋果官方的工具texturetool,但後來我意識到,這個texturetool相對TexturePacker有不少不方便的地方,好比它對原始圖片的格式有硬性要求,必須至少知足:

  • Height and width must be at least 8.
  • Height and width must be a power of 2.
  • Must be square (height==width)

而TexturePacker雖然能夠作png到pvr轉換的事情,可是畢竟設計目的是打包sprite sheet用的。

不過通過和他的討論,最終我給出了TexturePacker的解決方案:

這段腳本所作的事情是遍歷images這個文件夾下的全部png圖片,而後對每一張小圖片都作一次打包操做,打包後的圖片格式爲pvr,這就至關於對每一張圖片作了一次格式的轉換:從png到pvr。這個作法雖然不一樣於TexturePacker的設計初衷,但畢竟是可行的,並且很方便。

這裏要注意一點,咱們相對於以前打包的腳本多增長了一個參數:--size-constraints

這個參數很是關鍵,它決定了最終生成的sprite sheet的尺寸是否會受POT(Power Of Two)格式的限制。通常狀況下咱們生成sprite sheet的尺寸都是寬高相等,而且都是2的N次方。而對咱們如今這個轉換圖片格式的需求,這個限制就多餘了,由於咱們確定但願原始圖片多大尺寸,最終轉換獲得的圖片就是多大尺寸,因此這裏咱們設置這個參數的值爲AnySize。

--size-constraints AnySize

不得不說TexturePacker這個工具的功能真的很強大,做者考慮問題很是得全面~

這個參數在GUI裏面在這裏:

還有一點小問題是,對於每個sprite sheet,都會須要生成一個data文件,這裏咱們不須要這個data文件,因此在參數裏面咱們就隨便叫了一個dummy.plist:)其餘的參數大家能夠按需修改。

好了,更新部分就是這麼多,最後感謝一下園友sousou123和tanyongdahaoren,經過解決他們的問題也讓我學到了新的東西:)

 

 

 

 

 

感謝你們的收看~ 若是有問題能夠留言或者私信我,我會盡可能回覆你們。

最近剛開始專門寫博客,若是表達的很差,或者有其餘方面問題,也請你們多提寶貴意見:)

 

最最後,原創文章,轉載請註明出處,謝謝:)

相關文章
相關標籤/搜索