Scratch,做爲世界流行的青少年編程語言,其對青少年智力的開發及計算思惟的培養根本毋庸置疑。既然定位在青少年,那就不能複雜,可是,又要遵循「低門檻,高上限」兩個基本特徵。讓青少年儘快入門的同時,又可讓部分可以深刻鑽研的同窗深入體會到編程的創造性、複雜性及內在樂趣。然後者,在全國青少年編程競賽與等級考試中確定要體現出來——天然也是體現參加者做品創意與難度的所在。程序員
Scratch開發者恰當地把握了上述要求與特徵:最基礎最重要的計算機編程語言特徵必須具有,同時又儘量巧妙地「屏蔽」程序設計算法及內在原理的複雜性,在界面設計上追求「極簡且穩定第一」的風格——就像小朋友手中的真實積木,任意摔打而毫無問題。算法
咱們知道,Scratch程序運行原理上是基於事件驅動的,這一點學起來並不複雜。但另外一方面,多線程編程及其同步技術這種「高上限」又沒法迴避——這是開發複雜應用程序最實用但又最複雜的技術之一。編程
仍是那句話,Scratch毫不是玩具式語言!下面經過實例來講明問題。小程序
在本文中,咱們想使用Scratch開發一個如圖所示的小程序。數組
在三消遊戲、卡牌遊戲中常常出現本程序中的需求,即按指定矩陣排列規律在屏幕特定區域佈局精靈。爲了簡化問題,我使用了大寫的26個英文字母來作試驗,如圖所示。
爲了朋友們看起來方便,有些基礎性的準備工做我簡單介紹一下。多線程
手段多樣。我使用的辦法是結合Scratch的導出功能與Photoshop聯手搞定。編程語言
有興趣的朋友高度推薦自學一下Photoshop,這個軟件相似於平常辦公中的Office軟件,在平常圖形圖像處理中功能極其強大!一經學會,終生受益!編輯器
整體步驟以下:ide
【第一步】Scratch中內置的角色庫的」字母「類型中已經提供26個字母的造型,如圖所示:
佈局
【第二步】添加一個空白角色,切換到造型編輯器(或者稱圖形編輯器)狀態下,從內置角色庫中把上述字母造型逐個按序加入到本角色中,參考下圖:
【第三步】仔細觀察,這些字母的造型大小並不一致(我上圖中給出的是通過我加工的,因此大小同樣),並且大小差距很多。若是根據咱們上面程序要求,很是有必要把它們調整得同樣大小。怎麼辦?
考慮到系統內置造型編輯器的有限功能,想到:把它們導出,而後用Photoshop統一處理。請參考接下來的步驟。
【第四步】先在造型編輯器中把上述造型逐個轉換成位圖類型。注:默認添加的字母造型是矢量的,只能導出爲.SVG格式。在轉換成位圖類型後便可把它們導出成.PNG格式,而後使用Photoshop處理。有興趣的朋友,能夠分析一下直接使用矢量編輯軟件如CoreDraw或者Illustrator等直接處理.SVG文件。由於個人Photoshop是CS6,默認不能直接處理.SVG,因此我先轉換成位圖類型。
【第五步】在獲得位於同一文件夾下的26個.PNG文件後,能夠很輕鬆地使用Photoshop把它們批量修改爲同一尺寸(有興趣的朋友能夠參考我本文稍後整理的短博文,在此省略介紹)。考慮到Scratch的創做屏幕爲480X360像素,因此,我把每個字母的大小修改爲30X34像素大小。
爲了度量方便性,這裏還有一個小技巧是:我把背景圖替換成了Scratch系統內置的背景圖,名字爲Xy-grid-30px。
針對上面如圖所示的字母排列,很多中學信息學教材中介紹逐個角色方式建立,並逐個排列到屏幕上。這種方法是最原始、最簡單、最直接的,但每每也是最有問題的方法。不妨設想:在擁有幾十甚至上百個關卡的卡牌或者消除類遊戲中,若是使用這種排列方法,麻煩大了!
顯然,最好的辦法是利用Scratch中的克隆技術:建立一個角色,並讓這個角色擁有上面26個英文字母的26種造型。那麼問題來了:
【問題1】如何利用克隆技術?
【問題2】如何有效管理這些造型並適時地動態調整?
克隆對應的英文單詞是「Clone」,意思是徹底複製。在Scratch編程中,克隆不只複製母體的全部靜態屬性,還複製包括執行代碼在內的一切。在遊戲軟件開發中,經常要求相同的角色的大量不一樣的副本,並且要求這些副本表現出與母體徹底相同的行爲;例如,大量的殭屍與小魚、無數的雨點與雪花……
所以,巧妙地使用克隆技術,可以生成大量類似或相同表現的角色,並極大地簡化程序、特別是遊戲軟件的開發過程。
【注】在本文中,咱們把做爲克隆種子的角色統一稱爲「母體」,把每個克隆生成的角色簡稱爲「克隆體」,理解與搞清「母體」與「克隆體」之間的關係是克隆技術編程的關鍵。
例一:生整天空中的雨點
下面的兩段代碼針對故事中的「雨點」角色編程:
第一段
第二段
【技術總結】此處代碼的特色是:母體角色(只有一個)只負責生成克隆體角色,各類屬性的設置統一由克隆體自身處理。這屬於克隆技術編程的最簡單的情形。這種情形下,第二段代碼能夠盡情使用程序中定義的全局變量,但要注意各克隆體之間使用上不該出現衝突。
【問題】這兩段代碼屬於兩個線程,這兩個線程的執行看起來沒有什麼共享數據或者同步要求,因此,這種情形下的克隆編程是比較簡單的。
多線程、多進程編程是幾乎每個中級程序員必須面對和要克服的難題,Scratch後臺系統的特徵與實際程序開發的需求要求它不得不引入多線程技術,儘管Scratch竭力巧妙地掩蓋這種技術,但這些技術自己具備的複雜性在使用Scratch編寫比較複雜的程序時必然(並且已經)彰顯出來且須要克服。值得慶幸的是,Scratch開發者早已預料到這一點,並已經給出了圓滿的解決方案。
例二:生成三隻有規律排列的小貓
先看下圖:
【問題一】哪個是母體?答案見下圖:
即最右邊一個是母體!
截止到目的,咱們對克隆技術使用要求是生成滿天的雨滴或者是三隻貓,並無要求區別母體與克隆體!可是,有些,甚至是更多,應用狀況下要求區別對待母體與克隆體(甚至是各克隆體之間也要區別)。
【問題二】要想使左邊第一隻貓成爲母體,怎麼辦?
先看下面的圖示:
結合上圖,得出目前結論是:克隆體老是由母體生成的!
所以,要解決上面【問題二】要求在克隆體內修改座標,而不能在母體代碼中修改座標(母體代碼中修改老是修改母體角色的屬性值)。天然,要實現「在克隆體內修改」這種目標,因而積木命令登場!
那麼,看接下來的這段代碼及結果圖示:
這段代碼也好理解不是?【問題二】的答案初步有眉目了!可是,新的問題又出現了:
【問題三】第三隻(最右邊)小貓(克隆體)如何生成?
若是至關然修改,可能會有如圖結果:
有關克隆體代碼(積木【看成爲克隆體啓動時】所屬代碼)中繼續克隆本身的問題暫時不討論(涉及到克隆遞歸及最大遞歸深度的問題)。
繼續修改,嘗試以下代碼(與結果圖):
細心的朋友容易觀察出,克隆母體兩次,這兩個克隆體都調用了積木【看成爲克隆體啓動時】所屬代碼,因此結果是:這兩個克隆體小貓的位置是重合的。
再想辦法(結果仍是不行!):
再也不糾纏下去了,其實,解決上面的【問題二】的辦法是把兩次克隆體代碼區別開來,即區別哪是第一次克隆哪是第二次克隆,問題就好辦了。因而,咱們想到下面的解決辦法:
運行結果以下:
注意到,這種方案具備表明性,即若是生成N個位置的X只小貓的話,只要區別這X次克隆問題就迎刃而解了。
上面提供的辦法運用到了在克隆體執行代碼中使用全局變量的功能,其實,你們順着這個路子還會想出更復雜的與克隆有關的問題來。
有興致的朋友能夠考慮:解決上面【問題二】是否是還有其餘更好的辦法?
3、26個字母排列問題
其實,在前面的舉例中,都涉及到了多線程編程的問題。此時,一旦涉及到數據的共享訪問(或者稱數據同步),則必須設法解決其中同步的問題。如今,讓咱們回到本文開始第一張圖所展現的問題上。
篇幅所限,咱們僅考慮如圖所示的這一種情形,其餘情形相似,有興趣的朋友能夠參考本文程序在51CTO上的源碼(忽然發現要聯繫博客主管才能上傳,爭取明天解決這個問題)。下面直接給出代碼並輔助必定的解釋。
含義一目瞭然。
(1)第一段
這是消息接收到後的初始化工做,注意全局變量「gv克隆體計數器」是用來區別各個克隆體使用的(固然,本例子僅是一個入門,並無深刻區別對待每個克隆體的操做)。
(2)第二段
注意:本例子中爲了數據管理的方便,引入了兩個分別記錄屏幕上按規律排列的每個角色橫縱座標的兩個列表,如圖所示:
其中,「const橫座標列表」用來存儲垂直方向平均切割成16份(30X16=480)每個角色的中心點的橫座標,「const縱座標列表」用來存儲水平方向平均切割成10份(10X34+20=360)每個角色的中心點的縱座標。
上面代碼開始時,母體定位,並初始化幾個輔助變量,例如row和column分別用來記錄屏幕上角色所在的行與列(正好也與下面的二重條件循環次數大體相對應——並不是嚴格對應)。
接下來,變量「____克隆結束2」的做用是很是重大的。咱們引入這個變量的目的是讓程序嚴格地接次序生成屏幕上的克隆體角色(如第1個、第2個、第3個......)。
接下來,兩個循環的循環次數含義不用解釋了,分別對應行數與列數。當生成了第26個角色(Z字母)後,循環結束。這裏循環結束前的「隱藏」積木調用的做用是,用於隱藏母體!!!請各位根據前面克隆體與母體的舉例仔細體會。
row和column在循環體內的修改用於控制屏幕上行數與列數。
接下來,看克隆體執行部分的代碼。
(3)第三段
語句的做用是,等待上一個角色操做結束(多是很長時間,本例中時間是很是短暫的)。
接下來的語句做用是,按字母順序生成屏幕上的角色。
接下來,根據兩個數組對應座標值來修改當前角色的座標值。
最後,克隆體計數加1,並設置克隆操做結束的標記。
整體來看,在本實例中,協調主程序與克隆體運行代碼(其實這是典型的兩個線程)的變量「____克隆結束2」的做用功不可沒。
在本文中,咱們還只是初步探討了Scratch多線程編程通信技術與克隆體技術編程的部份內容,並未涉及到所有。可是,相信朋友們已經覺察出Scratch並不是市面上談論得那麼「簡單」。也正因如此,Scratch(及其各類「克隆體」)才成爲風靡世界的青少年編程語言。在之後的文章中,我還會給出更多的有關使用Scratch開發創新性應用與遊戲的實例,並進一步探討Scratch編程的奧祕,敬請期待。不足之處,歡迎廣大同仁與青少年朋友批評指正。