103
修平科技大學 資訊網路技術系 實務專題報告 藍芽連線五子棋 學生:BN99111 張祥森 BN99101 林士楷 BN99027 林俊豪 BN99020 黃思翰 BN99019 陳品翔 指導老師:老師 口試老師:老師 老師 老師 103 6

修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

  • Upload
    others

  • View
    0

  • Download
    0

Embed Size (px)

Citation preview

Page 1: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

修平科技大學 資訊網路技術系

實務專題報告

藍芽連線五子棋

學生:BN99111 張祥森

BN99101 林士楷

BN99027 林俊豪

BN99020 黃思翰

BN99019 陳品翔

指導老師:老師

口試老師:老師

老師

老師

中 華 民 國 1 0 3 年 6 月

Page 2: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

目錄

第一章 前言 3.

1-1動機與目的 5.

1-2 簡介 7.

1-3軟、硬體需求 9.

1-4 甘特圖 10.

第二章 文獻探討 11.

2-1 藍芽應用 13.

2-2 Android開發環境 14.

2-3 Android SDK 相關開發套件的安裝需求與流程 22.

2-4 Java Platform ( JDK ) 下載安裝教學 24.

2-5 ADT Bundle下載 31.

2-6 Android SDK 版本檔案之下載安裝 36.

第三章 系統功能 42.

3-1系統 AI策略 44.

3-2系統功能圖 45.

3-3系統架構圖 46.

3-4系統功能區塊及流程 47.

1

Page 3: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第四章 操作說明 49.

第五章結論 54.

第六章 Q&A55.

第七章參考資料 57.

第八章 附錄 101.

2

Page 4: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第一章 前言

隨著 3G 的普遍,手機顯示性能的提高,手機螢幕的擴大和較高

的分辨率,解決了傳統手機行業的很多弊端,同時 Android也採用了

鍵盤形式的按鍵,可以完成更複雜的操作。Android雖然基於 Java,

但是其虛擬機器是基於暫存器的,速度得到很大的提升,這為 Android

平台上開發遊戲提供了堅強的後盾。

隨著移動開發技術的不斷升級和終端設備成本的下降,近年來,

手機在普通消費人群中得到了極大的普及。憑藉其便於攜帶、溝通迅

速、功能多樣化、私密性強等得有優勢,手機已經成為普通民眾不可

替代的隨身工具。其益智、趣味和休閒的特點迎合了消費者的娛樂需

求,手機遊戲的開發推廣成為手機生產商和營運商重要的業務增長點,

遊戲軟體產業價值提升。手機遊戲是手機的一種高附加價值操作軟體,

遊戲編成是手機軟體編成的重要組成,同時也持續推動手機軟體技術

升級進步。

現在人們壓力日益增大,需要適當的放鬆才能獲得更高的工作效

率,工作之餘的娛樂對也是不可或缺的。五子棋這種娛樂方式簡單又

易學又具有深奧的技巧,具有趣味性和消遣性。在經過不斷發展後,

五子棋已經成為棋盤娛樂的一個重要的組成部分,它能夠增強思維能

力、開發智力,是人們休閒娛樂的不錯選擇。

3

Page 5: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

近來隨著電腦和手機的快速發展,各種各樣的遊戲層出不窮,使人們

能有更多的娛樂項目,而棋藝類遊戲能起到鍛鍊人的思維和修身養性

的作用,而且棋藝類遊戲水平頗高,大與人腦分庭抗禮之勢。現在的

五子棋遊戲軟體基本可以分為兩類:一類是網路五子棋遊戲軟體,另

一類是單機版五子棋類遊戲軟體。很少有手機板的五子棋遊戲軟體。

為了滿足手機人群的需求,設計了這款手機版的五子棋遊戲軟體,可

以提供人們閒暇的時間隨時地進行休閒娛樂,提高自子的五子棋水平,

實用性強。

主要研究在 Android 手機上開發一款由人與電腦對戰和人與人

對戰兩個遊戲模式於一身的五子棋類遊戲。遊戲介面部分 Android平

台提供的控制項和精美的布局框架設計出一個內容清楚、指示明白的

遊戲介面。

4

Page 6: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

1-1 動機與目的

隨著社會的發展,目前全球的手機用戶量已經超過了電腦PC的數量,

而且手機的數量正在快速增長,其中智慧型手機所占的比例越來越大,

特別是隨著 3G技術發展的時代到來,行動聯網裝置(Mobile Internet

Device)是一個巨大的市場,許多國際公司以及國內的公司都在搶占

智慧型手機領域的市場份額。在這段時間,出現的智慧型手機可說五

花八門總類繁多,但是真正好用受用戶喜歡的智慧型手機卻不多。

在智慧型裝置普及的環境下,APP已經成了每位使用者必備的軟體程

式,每個人的 3C 設備裡面,都是各種不同類型的 APP,所以我們決

定撰寫一個益智遊戲類的五子棋 APP。在日常生活中閒暇之餘,幾乎

都會玩起手機遊戲,手機遊戲 APP又有分很多種類型,有運動的,角

色扮演,射擊,益智………等等很多種,讓使用者有眾多的選擇,我

們之所以選益智類的,是它不僅可以讓你打發與消磨時間,又可以動

腦去思考,除了可以活化我們的腦細胞之外,也可以降低老人痴呆的

發生,增加使用者對五子棋的了解與認識,也可以與身邊的親朋好友,

利用手機藍芽連線,進行五子棋的連線對戰,也增添了不少趣味性。

Google宣布以 android系統進軍手機操作系統領域之後,三年來

Android 一路領先,快速獲得眾多用戶和廠商的認同,隨著 Android

手機中端的逐漸熱銷,Android也引起眾多手機應用程序開發商的關

5

Page 7: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

注,Android的出現帶給了智慧型手機領域更多的機遇和挑戰,由於

Android基於 Linux核心且具有開放原始碼、免費的特性,他迅速得

到廣大愛好者以及許多廠商的支持,基於 Android所開發的手機遊戲

擁有巨大潛力已成為行業共識。

1-2 簡介

手機遊戲的優點龐大的潛在用戶群現在全球超過十億部移動電話正

6

Page 8: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

在被使用,並且這個數目還在逐漸增加。在除美國之外的每個發達國

家,擁有手機的人數比擁有計算機的人數還要多。雖然這些手機只有

小部分是支持 Java 遊戲的手機,但是這個數目正在快速地提高並且

在幾年內 Java 手機將要成為行業標準。移動遊戲潛在的市場比其它

任何平台(比如 Playstation 和 GameBoy)都要大。便攜性 GameBoy

比其他任何控制台遊戲賣出的多的一個原因就是其的便攜性。與現在

的遊戲控制台或個人電腦相比,手機可能不是一個好的遊戲設備,但

是人們基本上是隨時隨地都把它們帶在身邊,在人們離開家或者想玩

的時候,可以不受任何時間地點限制地玩自己選擇的遊戲。

我們要製作的手機遊戲是能藍芽連線的五子棋大家所了解的五子棋

一定需要黑白兩色的旗子與一個大棋盤也需要兩位玩家才能進行的

遊戲,發展於日本,流行於歐美。現代五子棋日文稱之為“連珠” ,

英譯為“Renju” ,英文稱之為“Gobang” 或“FIR”(Five in a

Row 的縮寫) ,亦有“連五子”“五子連”“串珠” “五目”“五

目碰”“五格”等多種稱謂必須要五顆黑棋或五顆白棋連成五顆才

算勝利。

在現在的生活中要找到跟你下棋的人實在是少之又少,為了避免

這種情況發生,我們製做了手機板的五子棋遊戲,我們是使用了

Eclipse來製作遊戲可以讓你在無聊想找人下棋的時候玩上一把,另

7

Page 9: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

外我們製作了藍芽連線對戰的功能讓你可以跟好有進行對弈,第二章

介紹了 Eclipse軟體的說明,第三章介紹了整個遊戲的功能圖、流程

圖、程式碼。 第四章介紹遊戲的遊玩方式,最後還有結論的部分。

8

Page 10: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

1-3 軟、硬體需求

開發環境 Intel(R) Pentium(R) 4 CPU 2.40GHz,1G 內存,160G 硬

碟 Microsoft Windows XP Professional Service Pack 3 JDK 1.60

Eclipse 3.5,運行環境 Android 手機操作系統 2.2 版本。

Android 簡介

Android 是基於 Linux 內核的操作系統, Google 公司在 2007 年

11 月 5 日是公佈的手機操作系統, 早期由 Google 開發, 後由開

放手持設備聯盟(Open Handset Alliance)開發。 Android 系統具

有開放性、應用程式無界限、應用程式是在平等的條件創建的、應用

程式可以輕鬆地嵌入網路和應用程式可以並行運行等特點。 Android

的系統架構共分為 4 層,由高到低分別是應用層、應用框架層、系

統運行庫層和 Linux 內核層。從技術角度而言,Android 與 iphone

相似,採用 Webkit 瀏覽器引擎,具備觸控、高級圖形顯示和上網功

能,用戶能夠在手機上查收郵件、搜尋網址和觀看視訊節目等。

Java 是 Sun 公司在 1995 年推出的新的編程語言,它是一種簡

單的、面向對象的、分佈式的、解釋的、安全的、可移植的、性能優

異的多執行緒語言。

1-4 甘特圖

9

Page 11: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(1-4)甘特圖

第二章 文獻探討

藍芽(Bluetooth)這個名字,倒是有個有趣的起源西元十世紀時,

挪威有個維京國王 Harald(哈拉德藍芽 Blatand 為丹麥文字,相當

英文的 bluetooth) II (940-981),統一了丹麥(Denmark and

Norway),成為維京人的英雄 Ericsson 將其新的無線電介面的

Project命名為「藍牙」(Bluetooth),大概是希望藉由 Bluetooth 統

一介面規格,成為一個世界標準,而「藍牙」譯名變「藍芽」或許是

為了看起來比較文雅吧〈藍芽組織也希望能在一個標準之下整合所有

的無線電子短程通訊產品。

藍芽技術運作的原理主要是運用跳頻展頻技術(Frequency

10

Page 12: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

Hopping Spread Spectrum -- FHSS)方式,使藍芽晶片的兩端,以某

一特定形式的窄頻載波同步地在 2.4MHz 頻帶上傳送訊號。詳細來說,

此 FHSS 的傳輸技術,是將欲傳輸的信號透過一系列不同的頻率範圍

廣播出去,而由傳送裝置先傾聽頻道(Listens Channel),若偵測出

頻道處於閒置狀態時,信號便由此頻道傳送出去,若偵測出頻道為使

用中,便使用跳躍程式進行傳送。重要的是,傳送與接收必定要同步

切換頻道才可以正常接收資料。

11

Page 13: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

藍芽最多可進行 1 對 7 的傳輸,除了資料之外,也可以使用

CVSD (Continuous Variable Slope Delta-Modulation)技術來進行

語音傳輸及使用分時多工(TDMA)協定技術之通訊協定。

藍芽技術是一種小範圍的無線電頻率技術,裝置間透過晶片可互相

溝通,不必再透過纜線傳輸。

藍芽以更高的頻率(2.4GHz)取代紅外線,傳輸速率更高、應用

更廣。目前的紅外線傳輸只能傳送幾公尺,而且還不一定保密。

主要特點如下

• 操作頻段 2.4GHz 工業、科學、醫療(Industrial Scientific

Medical;ISM)頻段。

• 可及範圍十公分到一百公尺。

• 使用跳頻展頻技術(Frequency Hopping Spread

Spectrum ,FHSS)。

• 最高可支援八個連結埠。

• 無需如紅外線傳輸埠做「視線(Line-of-sight) 」的傳輸。

• 支援同步和非同步傳輸模式,易與 TCP/IP 整合成網路。

12

Page 14: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-1藍芽應用

藍芽收發話器對健康的好處,由於手機有高功率的電磁波,據報

導證實電磁波會對人體造成傷害,所以有了藍芽,你將可以把一個小

小的藍芽附件裝在你的 3C設備, 然後把收發話器戴在你的耳朵(由

於藍芽應用的是低功率,所以不會對人體有任何傷害)。準備好了以

後,你就把你的 3C 設備放在口袋裡講電話,不必把電話緊貼的臉,

甚至按下收發話器上的按鈕就可以直接聽來電。

藍芽比一般傳統式紅外線傳輸更快,且不用對準兩個傳輸埠成一直線

藍芽科技在傳輸方面的好處就是, 它能夠允許兩個裝置,在不排成

一直線的狀態下,還能夠以無線的方式傳送資料。不像紅外線傳輸最

大的缺點是,你必須對準兩個傳輸埠成一直線才有辦法傳送資料。藍

芽傳輸甚至無視於牆壁、口袋、或公事包的存在而可以順利進行。又,

藍芽的資料傳輸速度比紅外線傳輸還要快,每秒鐘高達 1MB。

13

Page 15: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-2Android開發環境

Android是一套建構在 Linux核心(Linux Kernel)之上的智慧型

手機作業系統。使用者可以透過 Android 撥打電話、傳送簡訊、收

發電子郵件、查看行事曆、上網、玩遊戲、享受影音娛樂、甚至透過

應用程式的下載,達成許多意想不到的創新功能。

由於,Android 在軟體版本授權上是採用 Apache Software

License 2.0的開放原始碼方案,因此,在這個版權協議之下,智慧

型手機製造商可免費地安裝 Android 作業系統至其生產製造的硬體

之中,有效地降低了軟體的採購成本。截至 2010 年 8 月 2 日為止,

Android 在市面上免費流通的軟體版本共有 1.5、1.6、2.1 與 2.2。

其中目前以 2.1 版本的使用量為最多。(資料來源:Android

Developers官方網頁)

對於智慧型手機製造商來說,透過免費取得作業系統而降低軟體

採購成本是一項很大的誘因,所以,截至目前為止共有 Acer(宏碁)、

Alcatel、ASUS(華碩)、CCI、Dell、Foxconn(富士康)、Garmin、Haier、

HTC(宏達電)、Huawei(華為)、Kyocera、Lenovo、LG、Motorola、NEC、

Samsung、Sharp、Sony Ericsson、Toshiba 與 ZTE 等二十家智慧型

手機製造商以及其它數十家行動通訊公司、半導體公司、軟體公司以

及商業公司陸續加入了開放手機聯盟(Open Handset Alliance)並

14

Page 16: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

投入生產、銷售或者研發 Android 作業系統的相關軟硬體產品與服

務。

Android 也因為有如此地百花齊放,因此即使 Google 的智慧型

手機 Nexus One 有點出師不利,但 Android 卻能在 2010 年第二季以

市占率 17.2%,擊敗 Apple iOS(iPhone 的作業系統,市占率 14.2%)

奪下全球智慧型手機作業系統的老三地位, 排行僅次於市場龍頭老

大 Nokia Symbian OS(市占率 41.2%)與 RIM BlackBerry OS(市占率

18.2%)。(資料來源:Gartner)

更據 Digitimes Research分析師兼專案經理林俊吉的預估,2010

年 Android全年市占率將達兩成,成為智慧型手機作業系統的第二大

平台。(資料來源:經濟日報)

Android 以新秀之姿在短短不到三年的時間就有此成績,不只對

於旗下合作的智慧型手機製造商具鼓舞作用,也會促使 Android應用

程式的開發者,投入更多時間與精力去開發兼具功能性與創新性的應

用程式。

再更進一步地說,由於 Android在應用程式開發上,採取免費、

開放的策略。開發者不僅可以免費地下載安裝 Android SDK(Android

的軟體開發工具包)進行應用程式的開發。更重要地是,人們可以使

用多數程式設計師所熟悉的 Java 程式語言進行應用程式的編寫。因

15

Page 17: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

為這兩個特點,促使為數眾多的 Java 程式設計師蜂擁至 Android 應

用程式的開發行列。

Android SDK

Android SDK 係指:開發 Android 手機應用程式所需的相關

Android APIs ( 又稱為 Framework APIs 或 Android SDK APIs ) 與

核心工具軟體。

至於,所謂的 Android APIs ( Application Programming

Interface ) 係指:Android 官方所提供的一組 Android 手機應用

程式開發者在開發 Android 手機應用程式時所會用到的程式溝通介

面,它是做為 Android 手機應用程式與 Android 作業系統底層相互

溝通之用。它裡頭主要包括了一系列的核心套件 ( packages ) 與類

別 ( classes )等程式開發元件。

簡而言之,它就是 Android 應用程式框架 ( Application

Framework ) 所提供的一系列程式開發元件,所以它又被稱為

Framework APIs 。

由於, Android 手機應用程式開發者可以使用這一系列的

Android APIs 進行 Android 手機應用程式的開發工作,因此,它讓

大部份的 Android 手機應用程式開發者省卻了理解 Android 作業

16

Page 18: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

系統底層之程式架構的時間與精力。

不同的 Android 作業系統皆有各自的 Android APIs 版本。其版

本相對應之數字識別代號,則稱為 API Level 。

Android 手機應用程式開發者可以在自己的開發環境之中,下載安裝

不同 Android 作業系統所支援的 Android APIs 。

Android Support Library

此外,當 Android 手機應用程式開發者建立 Android 手機應用程式

開發專案時,則需在這些已下載安裝的 Android APIs 當中,指定該

專案的最低 Android API Level 需求,以便告知 Android 作業系統

關於該應用程式所能相容執行的最低版本限度。

通常而言,新版本的 Android 作業系統多半能夠相容支援於舊版本

的多數 Android APIs ,但是,舊版本的 Android 作業系統則不一

定能夠相容支援於新版本的 Android APIs 。所以,Android 手機應

用程式開發者在開發過程中,儘量要避免使用到其所設定 《 最低

Android API Level 需求 》 無法相容支援的 Android APIs ,不過,

到了 2011 年 3 月初之後,Android 官方為了能讓 Android 手機應

用程式也能在舊版本的 Android 作業系統執行某些新版本 Android

APIs 之功能,因此,他們還提供了所謂的 Android 支援函式庫

17

Page 19: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

( Android Support Library ,剛推出時稱為 Android 相容性開發

套件 ( Android Compatibility package ) ) 。

當 Android 手機應用程式開發者在其所開發的 Android 手機應用

程式開發專案加入了 Android 支援函式庫 ( Android Support

Library ) 並使用其所提供之相容式 APIs 後 ,則該應用程式不再

受限於舊版本的 Android 作業系統沒有提供新式 APIs 之困擾,而

可以直接從其加入的 Android 支援函式庫 ( Android Support

Library ) 中取用既是新式但又能夠相容於舊版本 Android 作業系

統之相容式 APIs。不過,請注意! Android 手機應用程式開發者需

時常更新 Android 支援函式庫 ( Android SupportLibrary ) ,以

便能使用更新版本的相容式 APIs。另外,Android 支援函式庫

( Android Support Library ) 並非支援所有的新版本 Android 作

業系統之 APIs 。

而且它還區分成兩種:若註明為 v4 者,則最低能相容於 Android1.6

以上的作業系統版本。若註明為 v7 者, 則最低能相容於 Android

2.1 以上的作業系統版本。v4 與 v7 兩者支援之範疇並不相同。通

常而言,當您透過 ADT Bundle 或 Andorid Studio 建立 Android 手

機應用程式開發專案後,ADT Bundle 或 Android Studio 至少會自

動幫您的 Android 手機應用程式開發專案加入 v4 support library,

18

Page 20: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

以便您能夠使用其所提供之相容式 APIs。

ADT Bundle ( Android Development Tools Bundle )

如同編輯其它應用程式般,Android 手機應用程式開發者除了需要

Android APIs 外,還需要一個能夠實際提供編輯操作的程式編輯器

軟體。

Android 官方在早期並沒有特別推出獨立專屬 Android 手機應用

程式開發的程式編輯器軟體,而是以外掛開發套件的方式去提供支

援那些 Java 應用程式開發者原本就常用的程式編輯器軟體,以便

Android 手機應用程式開發者可以運用那些程式編輯器軟體進行

Android 手機應用程式之開發工作。特別是,因當時 Android 官方

的外掛開發套件似乎主力支援 Eclipse 程式編輯器軟體 ( 此外掛

開發套件稱之為 ADT Plugin for Eclipse ) 。所以,那時候不少

的 Android 手機應用程式開發者常用的開發環境就是裝有 ADT

Plugin for Eclipse 的 Eclipse 。

19

Page 21: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

然而,自 Android 4.0 之後,Android 官方已將 Android SDK 與

其客製化後的 Eclipse + ADT Plugin for Eclipse 整合壓縮封裝成

一個名為 《 ADT Bundle 》 之 Android SDK 開發工具,以減少

Android 手機應用程式開發者下載安裝 Android SDK 的步驟。

Android Studio

到了 Android 4.2 之後, Android 官方還推出了名為

《 Android Studio 》 之 Android SDK 全新開發工具。雖然,Android

Studio 與 ADT Bundle 都是 Android SDK 開發工具研發團隊支援負

責,但 Android Studio 最大差異在於它並非以 Eclipse 程式編輯

器軟體為基礎,反而是使用 IntelliJ IDEA 程式編輯器軟體為基

礎。

Android Studio 的推出似乎並不意味著它將取代 ADT Bundle ,

而且從當時 Android Studio 的推出至今,ADT Bundle 仍持續地推

出自身的更新版本 ,並未中止其更新動作。

換句話說,Android 官方可能希望除了專注發展以 Eclipse 為

基礎的 ADT Bundle 之外,也同時再多發展另一個也是開放原始碼的

程式編輯器軟體,藉以擴大 Android 手機應用程式開發的開發者族

群範圍。

20

Page 22: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

或許,我們從此處也可以看見 Android 官方持續強化 Android

手機應用程式的開發工具之廣度與深度,他們所做出的努力。

若從另一層面來看,由於 Android Studio 目前仍為 0.3.x 的早期

預覽版本,因此,Android 官方也或許能將部份尚未完全成熟的新開

發工具功能先行在 Android Studio 讓 Android 手機應用程式開發

者嘗鮮試用測試。

21

Page 23: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-3Android SDK 相關開發套件的安裝需求與流程

我們先引述 Android Developers 官網上所述, Android SDK 相關

開發套件支援的作業系統如下:

• Windows XP ( 32 位元 ) 、 Vista ( 32 或 64 位元 ) 或

Windows 7 ( 32 位元或 64 位元 )

• Mac OS X 10.5.8 或更新的版本 ( 只能在 x86 硬體上執行 )

• Linux ( Android 官方已在 Ubuntu Linux, Lucid Lynx 測試

過 )

在此要注意的是,雖然 Android SDK 相關開發套件也能在 64 位元

的作業系統上執行,不過,前提是該作業系統必需可以執行 32 位元

的應用程式。

關於需要下載安裝的相關開發套件,需包括以下兩項:

•Java開發工具包 ( Java Development Kit, JDK )

•ADT Bundle ( 附有最新版本 Android SDK )

另外由於 ADT Bundle 附的是最新版本的 Android APIs 套件,因此

您或許還會依所需而額外下載更新 Android SDK ,以便增加或更新

您所需版本的 Android APIs 套件。

其次,Android 官方提供做為 Android 手機應用程式開發者進行下

22

Page 24: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

載、更新或刪除 《 不同版本 Android APIs 套件或其它 Android SDK

工具套件 》 之管理工具軟體,稱之為 Android SDK Manager 。

ADT Bundle 本身便有包含 Android SDK Manager ,因此除了

Android SDK 外,您還需要確認您的電腦是否已預先安裝 Java

Platform ( JDK ) 。

若您的電腦無預先安裝 Java Platform ( JDK ) 或其版本低於 JDK 6

時,則您在開始執行 Android SDK 下載安裝程序工作之前,需要先

預先安裝 Java Platform ( JDK )。

至於,下載安裝上述開發套件的流程順序,如下圖所示:

圖(2-3-1) 下載安裝開發套件的流程順序

23

Page 25: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-4 Java Platform ( JDK ) 下載安裝教學

先下載 Java Platform ( JDK ) 安裝檔案圖 (2-4-1)http:

//www.oracle.com/technetwork/java/javase/downloads/index.ht

ml。

圖(2-4-1)Java Platform ( JDK ) 安裝網址

24

Page 26: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-2) 新的版本 Java SE 7u60

如圖(2-4-2)表示案裝最新的版本 Java SE 7u60,按下 Download 進

行下載的程序。

25

Page 27: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-3)電腦位元選項

如圖(2-4-3)選擇您電腦的位元後請您將這個”Java Platform ( JDK )

安裝檔案”下載儲存至您的電腦之中。

26

Page 28: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-4) JDK的安裝程序

如圖(2-4-4)表示 JDK的安裝程序,按下下一步開始安裝 JDK。

27

Page 29: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-5)安裝步驟

選擇你所要安裝的位子,選擇完畢點選下一步繼續安裝。

28

Page 30: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-6)安裝路徑

當出現”安裝 JRE ”的對話視窗時,煩請您直接按下”Next >”按

鈕。(如下圖(2-4-7))

29

Page 31: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-4-7)安裝程序

當出現”Java Platform ( JDK ) 安裝完成”對話視窗時,您可按

下”Close”按鈕,就可以完成安裝程序。

30

Page 32: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-5 ADT Bundle ( Android Development Tools Bundle ) 之下載

請 先 打 開 您 的 網 頁 瀏 覽 器 並 在 網 址 列 中 鍵 打

入 http://developer.android.com/sdk/index.html,以便連結進入

Android Developers 官網所提供的 Android SDK 下載主頁之中。當

您連結進入 Android Developers 官網所提供的 Android SDK 下載

主頁之中,您會發現在此頁面的右上側有一個大型按鈕,按鈕上面的

大字寫著 Download the SDK。

而在此大字之下又有一行小字寫著 ADT Bundle for Windows。

沒錯!此處便是 ADT Bundle 之下載處。 ( 如下圖(2-5-1)所示 )

31

Page 33: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-5-1)SDK安裝網址

按下 Download the SDK 按鈕之後,您會看到下載 ADT Bundle 之

Android SDK 使用條款與版權宣告說明,請您務必要完整詳閱此使用

條款與版權宣告說明。

32

Page 34: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-5-2) Android SDK 使用條款與版權宣告

若您已完整詳閱且同意遵守 ADT Bundle 之 Android SDK 使用條款

與版權宣告說明後,則需勾選該使用條款與版權宣告說明之下的 “I

have read and agree with the above terms and conditions”項

目。

此外還需挑選要下載的 ADT Bundle 之 32-bit 或 64-bit 版本,直

接按下“Download the SDK ADT Bundle for Windows”按鈕。

33

Page 35: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

當 ADT Bundle 壓縮檔案下載完成後,請先至您指定儲存該檔案之資

料夾之中。

接著,請點選該資料夾中那個已下載儲存的 ADT Bundle 壓縮檔案,

並按右鍵且點選”解壓縮全部”選項,以便將此 ADT Bundle

壓縮檔案進行解壓縮之動作。 ( 如下圖圈圈處所示 )

圖(2-5-3)程式資料夾

34

Page 36: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

當點擊打開”eclipse”資料夾後,您會看到所有 eclipse 資料夾當

中的程式檔案與其子資料夾。

由於,ADT Bundle 已預先壓縮了以下五個重要項目:

• Eclipse 並已預先整合了 ADT Plugin for Eclipse

• Android SDK 工具 ( Android SDK Tools )

• Andorid SDK 平台工具 ( Android Platform-tools )

• 最新版本的 Android SDK 平台 ( The latest Android

platform )

• 最新的 Android 模擬器之 Andorid 作業系統映像檔案 ( The

latest Android system image for the emulator )

使用預設之資料夾路徑並按下”OK”按鈕即可。

35

Page 37: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2-6 Android SDK 版本檔案之下載安裝

圖(2-6-1) Eclipse開啟畫面

開啟 Eclipse圖(2-6-1)為開啟的空白畫面

請在”Eclipse”主畫面之中,點選”Window”下拉式功能表當中

的”Android SDK Manager ”選項。

36

Page 38: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-6-2)安裝 SDK

按下”Android SDK Manager ”對話視窗時安裝所需要的 SDK。

37

Page 39: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-6-3)安裝選項

需要其它版本的 Android SDK 套件項目,可進行其它版本的

Android SDK 套件項目之安裝。

38

Page 40: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-6-4)選取需要的檔案

Extras 之勾選項目。

若在 Extras 之中的 Android Support Library 套件項目被標注為

未安裝 ( Not installed ) 之狀態時,建議也要勾選該項目進行安

裝。

39

Page 41: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-6-5) 下載安裝

當您勾選完成所要下載安裝之項目後,請您按下 “Install 13

packages” 按鈕。

當出現”Choose Packages to Install”對話視窗時,請您先完整詳

閱各安裝套件項目之版權宣告說明。

40

Page 42: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(2-6-6)安裝程序

若您同意遵守這些版權宣告說明,請點選”Accept License”按鈕,

並按下”Install”按鈕,當所有下載安裝程序完畢後,便可以關閉

對話視窗。

41

Page 43: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第三章 系統功能

需求分析手機螢幕尺寸分為物理尺寸和顯示分辨率兩個概念。物理尺

寸是指螢幕的實際大小。大的螢幕同時,要配備高的分辨率,也就是

在這個尺寸下可以顯示多少個畫素, 顯示的畫素越多, 可以表現的

餘地自然就越大。現在手機行業發展迅速,不同大小螢幕的手機迅速

發展,鑒於不同手機螢幕尺寸不同,在設計遊戲的時候必須滿足:軟

體的界面簡單操作容易。

軟體具有的人工智慧算法原理要簡單並且運行要快速。遊戲是需

要快速反應的,手機處理器的頻率直接要求需要使用簡單實用的智慧

演算法。在設計本遊戲時考慮到用戶需要的是一個操作簡易的遊戲軟

體,同時還提供雙人對戰、人機對戰、藍芽連線三個遊戲模式。

特別是人機部分,要考慮到此軟體是在手機上運行,手機的很多

性能都不如電腦,因此在人工智慧算法的設計上應該在盡可能的縮短

系統搜尋時間的同時還要保證要有一定的智慧水平, 不然對玩家來

說沒有一定的挑戰性,也就缺少了吸引力。此外通過軟體功能的分析,

根據五子棋愛好者的需求,得出還有如下需求信息: (1)具有重新開

始的功能; (2)提示輪到哪一方下棋的功能; (3)具有退出遊戲的功

能; (4)具有判斷勝負的功能。

42

Page 44: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

3.2 系統設計思想本次設計主要是設計一個能夠在 Android 手

機上運行的五子棋遊戲。根據一般玩手機遊戲的流程,玩家一般是先

進入一個歡迎界面,進行選擇操作後再進入遊戲的主界面開始遊戲。

本遊戲軟體也將遵循該流程,玩家打開遊戲軟體後將先進入歡迎

界面,選擇遊戲模式,然後進入遊戲的主界面開始遊戲。進入遊戲的

主界面後,系統將根據玩家所選的遊戲模式給玩家設置對手玩家。

43

Page 45: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

3-1 系統 AI策略

我們的五子棋採用的是簡易規則,所以黑子沒有不能下雙活三、雙四

或是長連的限制,我們將五子棋的棋形分類,並且把棋形都分配權值,

以做為 AI下子策略的基準點,我們以 10分為滿分,分數越高優先權

越大,反之亦然。

圖(3-1-1)系統 AI策略

棋形 權值 棋形 權值

成五 10 雙活二 4

活四、雙死四、死四活

9 死三 3

雙活三 8 活二 2

死三活三 7 死二 4

死四 6 單子 0

活三 5

44

Page 46: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

3-2系統功能圖

圖(3-2-1) 系統總體設計圖

在圖(3-2-1)設計本遊戲時考慮到用戶需要的是一個操作簡便界面簡

單的遊戲軟體。同時要提供人機對戰、雙人對戰和藍芽對戰三個遊戲

模式。手機的很多性能都不如電腦。

45

Page 47: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

3-3系統架構圖

圖(3-3-1)系統架構圖

圖(3-3-1)遊戲整體的流程大致分成三個區塊,電腦對戰、雙人對戰

與藍芽對戰三個區塊,在由雙方下棋來決定勝負,程序會計算該棋的

坐標,並且在相應位置畫出相應的棋子。以上為大致的流程圖。

46

Page 48: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

3-4系統功能區塊及流程

圖(3-4-1)系統功能區塊及流程

圖(3-4-1)表示系統主要功能區塊根據需求分析和系統設計思想, 可

以將此手機五子棋遊戲分為以下幾個功能區塊:遊戲界面初始化模塊:

裝載界面圖片,畫出棋盤,清空棋盤,清空遊戲雙方棋子等等功能。

主循環控制模塊:負責控制下棋順序,當輪到某方下棋時,負責將程

47

Page 49: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

序流程轉到相應的區塊中,主要擔當一個調度者的角色。玩家下棋子

區塊:即用戶在指定下棋區域單擊後,程序會計算該棋的坐標,並且

在相應位置畫出相應的棋子。分析盤面得出最佳下棋位置區塊: 是

本次設計的核心部分,即人工智慧區塊。電腦下棋區塊:在分析出來

的最優位置上畫出相應的棋子。勝負判斷區塊:根據預先設定的規則,

判斷遊戲勝負。要求重新開始功能區塊:通過按下重新開始遊戲即重

新遊戲,系統主要流程歡迎界面幫助界面選擇遊戲模式遊戲界面電腦

對戰遊戲模式藍芽對戰主循環控制主循環控制分析盤面得出最佳下

子位置玩家下棋玩家 1 玩家 2 手機下棋是否判斷勝負某方勝利某方

勝利否判斷勝負重新開始某方退出某方退出結束。

48

Page 50: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第四章 操作說明

圖(4-1)遊戲主畫面

圖(4-2)遊戲模式選擇畫面

49

Page 51: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(4-3)建立藍芽連線

圖(4-4)藍芽配對搜尋

50

Page 52: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(4-5)尋找藍芽配對方

圖(4-6)藍芽配對

51

Page 53: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(4-7)對弈開始

圖(4-8)勝利畫面

52

Page 54: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

圖(4-9)輸棋畫面

圖(4-10)放棄畫面

53

Page 55: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第五章 結論

這個專題我們花費了一年的時間才完成,雖然只是一個五子棋

APP,對我們來說卻是一個極具挑戰的任務,如果沒有組員們的相互

努力、以及共同解決在撰寫 APP過程中所遇到的困難,雖然在這撰寫

的過程中有些不愉快,但是這些不愉快在我們的良性溝通之下,化為

一股力量,幫助我們面對這項挑戰,也讓我們學習到了很多東西,在

短時間內要完成這項挑戰,一定有它的難度在,在我們整組努力不懈

且不輕易放棄的精神下,最後成功的撰寫出五子棋 APP遊戲。

未來我們會陸續增加其他的功能,讓使用者可以更加方便、隨心

所欲,我們計劃未來可以自定義背景圖片、自定義棋子音效、自定義

名稱和可以跟社群網站上的好友做連結,相互來較勁,為這 APP遊戲

增添許多趣味性。

54

Page 56: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第六章 Q&A

Q:發生 Host被重複連線上

A:先檢查有沒有已存 ConectThread,ConnectedThrad和

AcceptThread。如果有,一律先關掉。然後啟動 ConnectedThread,

並將 MESSAGE_DEVICE_NAME用 handler(mHandler,在

BluetoothChat.java傳了一個主 Thread的 Handler給 Service)傳訊

的方式,將 Client端的裝置資料傳回 BluetoothChat.java,讓 Server

端知道是誰在跟它做連結。

Q:原本的遊戲畫面無法加入觸控功能

A:必須將所有的圖片利用 Canvas畫布的功能包裝成一個 View,並

且利用這個 View去繼承原本 Android裡的 View,這樣才可以利用這

個繼承 View去實現手勢的監聽功能。

Q:藍芽連線後下棋要怎麼讓對方收到

A:因為藍芽連線是使用 socket方式丟字串,所以下棋後將座標轉成

字串,透過藍芽連線丟給對方。

Q:藍芽連線後啟動遊戲會讀不到圖片

A:原本做藍芽連線後子執行序會返回直接啟動遊戲,由子執行序去

55

Page 57: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

讀取圖片會導致圖片無法正常顯示,所以改成子執行序返回後設定旗

標,主執行序持續的檢查該旗標是否可以進行讀取圖片。

56

Page 58: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

第七章 參考資料

http://zh.wikipedia.org/wiki/%E4%BA%94%E5%AD%90%E6%A3%8B

五子棋維基百科

http://wenku.baidu.com/view/81cd5a13cc7931b765ce15b3.html

五子棋設計

http://wenku.baidu.com/view/ece99d4ce518964bcf847c08.html

Android設計

http://www.books.com.tw/products/0010517193

Eclipse基礎設計

http://goods.ruten.com.tw/item/show?21305298296120

程式設計

http://www.gururu.tw/

孫傳雄研究室

57

Page 59: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

附錄

主程式碼

AppDelegate.cpp

#include "AppDelegate.h"

#include "HelloWorldScene.h"

USING_NS_CC;

AppDelegate::AppDelegate() {

}

AppDelegate::~AppDelegate()

{

}

bool AppDelegate::applicationDidFinishLaunching() {

// initialize director

CCDirector* pDirector = CCDirector::sharedDirector();

CCEGLView* pEGLView = CCEGLView::sharedOpenGLView();

pDirector->setOpenGLView(pEGLView);

CCSize frameSize = pEGLView->getFrameSize();

pEGLView->setDesignResolutionSize(480,320, kResolutionShowAll);

// turn on display FPS

pDirector->setDisplayStats(false);

// set FPS. the default value is 1.0/60 if you don't call this

pDirector->setAnimationInterval(1.0 / 60);

// create a scene. it's an autorelease object

CCScene *pScene = HelloWorld::scene();

// run

pDirector->runWithScene(pScene);

return true;

}

// This function will be called when the app is inactive. When comes a phone call,it's

be invoked too

void AppDelegate::applicationDidEnterBackground() {

CCDirector::sharedDirector()->stopAnimation();

// if you use SimpleAudioEngine, it must be pause

// SimpleAudioEngine::sharedEngine()->pauseBackgroundMusic();

}

58

Page 60: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// this function will be called when the app is active again

void AppDelegate::applicationWillEnterForeground() {

CCDirector::sharedDirector()->startAnimation();

// if you use SimpleAudioEngine, it must resume here

// SimpleAudioEngine::sharedEngine()->resumeBackgroundMusic();

}

59

Page 61: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

AppDelegate.h

#ifndef _APP_DELEGATE_H_

#define _APP_DELEGATE_H_

#include "cocos2d.h"

/**

@brief The cocos2d Application.

The reason for implement as private inheritance is to hide some interface call

by CCDirector.

*/

class AppDelegate : private cocos2d::CCApplication

{

public:

AppDelegate();

virtual ~AppDelegate();

/**

@brief Implement CCDirector and CCScene init code here.

@return true Initialize success, app continue.

@return false Initialize failed, app terminate.

*/

virtual bool applicationDidFinishLaunching();

/**

@brief The function be called when the application enter background

@param the pointer of the application

*/

virtual void applicationDidEnterBackground();

/**

@brief The function be called when the application enter foreground

@param the pointer of the application

*/

virtual void applicationWillEnterForeground();

};

#endif // _APP_DELEGATE_H_

60

Page 62: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

HelloWorldScene.cpp

#ifndef __HELLOWORLD_SCENE_H__

#define __HELLOWORLD_SCENE_H__

#include "cocos2d.h"

#include <vector>

using namespacestd;

USING_NS_CC;

#include "SimpleAudioEngine.h"

using namespace CocosDenshion;

#define BLACK 0

#define WHITE 1

#define NO_CHESSMAN 1000

#define BLACK_CHESSMAN 1001

#define WHITE_CHESSMAN 1002

#define NO_GAME 10000

#define GAME_VS_COMPUTER 10001

#define GAME_VS_FRIENDS 10002

#define WAITING 10003

#define WAITINGAI 10004

#define GAME_VS_BLUE 10006

#define BT_MYTURN 10010

#define BT_WAITTURN 10011

#define BT_OK 10000000

#define BT_CANCEL 10000001

#define BT_HOST 10000002

#define BT_CONNECT 10000003

#define UPPER_BOUND 14

#define LOWER_BOUND 0

#define CHENGWU 130

#define HUOSI 90

#define CHONGSI 80

#define SISI 5

#define LIANSAN 70

#define TIAOSAN 70

#define MIANSAN 60

#define SISAN 5

#define LIANER 50

61

Page 63: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

#define TIAOER 50

#define DATIAOER 40

#define MIANER 40

#define SIER 5

#define YI 20

#define ANTI_CHENGWU 110

#define ANTI_HUOSI HUOSI-3

#define ANTI_CHONGSI 74

#define ANTI_SISI SISI-7

#define ANTI_LIANSAN LIANSAN-7

#define ANTI_TIAOSAN TIAOSAN-8

#define ANTI_TSCHENGSI TIAOSAN

#define ANTI_SISAN SISAN-7

#define ANTI_MIANSAN MIANSAN-7

#define ANTI_LIANER LIANER-7

#define ANTI_TIAOER TIAOER-8

#define ANTI_DATIAOER DATIAOER-8

#define ANTI_MIANER MIANER-7

#define ANTI_SIER SIER-7

#define ANTI_YI YI-7

#define COEFFICIENT 0.2

#define POSITIVE_DIRECTION 0

#define OPPOSITE_DIRECTION 1

#define DEPTH 1

struct position

{

int x,y,weights;

};

class HelloWorld : public cocos2d::CCLayer

{

public:

// Here's a difference. Method 'init' in cocos2d-x returns bool, instead of

returning 'id' in cocos2d-iphone

virtual boolinit();

// there's no 'id' in cpp, so we recommend returning the class instance pointer

static cocos2d::CCScene* scene();

// a selector callback

void menuCloseCallback(CCObject* pSender);

62

Page 64: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// implement the "static node()" method manually

CREATE_FUNC(HelloWorld);

void YouCanStratBT() {m_StartGameBT = true;}

void BT_MOVECHESS(std::string chessmove) {m_CanProcess = true; m_chessmove

= chessmove;}

void processbtmove();

void startgame_bt();

void tick1sec(float dt);

private:

void PlayATurn();

void PlayBTurn();

void buttonCallback(CCNode *pNode);

void buttonBlueCallback(CCNode *pNode);

void buttonBlueCallback2(CCNode *pNode);

void restartgame();

void show_chessbox();

void vs_computer(CCObject* pSender);

void vs_friends(CCObject* pSender);

void vs_blue(CCObject* pSender);

void vs_help(CCObject* pSender);

void ccTouchesEnded(cocos2d::CCSet* touches, cocos2d::CCEvent* event);

void addNewSpriteAtPosition(cocos2d::CCPoint pos);

void chess_down(int& x,int& y);

void restart();

void init_data();

void regret(CCObject* pSender);

intinline transform_x(int x);

intinline transform_y(int y);

bool win_or_not(int& x,int& y);

void AI();

vector<position> search_depth(int depth,int color=WHITE_CHESSMAN);

int solve_weights(int& x,int& y);

boolinline out_of_chessbox(int& x,int& y);

bool func_siqi(int&dir,int& x,int& y,int color);

int func_lianer(int&dir,bool is_anti,int& x,int& y,int color);

int func_tiaoer(int&dir,bool is_anti,int& x,int& y,int color);

int func_datiaoer(int&dir,bool is_anti,int& x,int& y,int color);

63

Page 65: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

int func_MIANER(int&dir,bool is_anti,int& x,int& y,int color);

int func_liansan(int&dir,bool is_anti,int& x,int& y,int color);

int func_tiaosan(int&dir,bool is_anti,int& x,int& y,int color);

int func_MIANSAN(int&dir,bool is_anti,int& x,int& y,int color);

int func_huosi(int&dir,bool is_anti,int& x,int& y,int color);

int func_chongsi(int& dir,bool is_anti,int& x,int& y,int color);

int func_chengwu(int& dir,bool is_anti,int& x,int& y,int color);

int game_status,chesses_num;

int pre_game_status;

int sub_game_status;

bool chessman_color;

int cb_status[15][15];

vector<cocos2d::CCSprite*> chesses;

CCMenuItemLabel *btn1;

CCMenuItemLabel *btn2;

CCMenuItemLabel *btn3;

bool mAmIHost;

bool m_StartGameBT;

bool m_CanProcess;

std::string m_chessmove;

CCSprite* m_pChessBox;

CCMenuItemLabel* m_item_restart;

};

#endif // __HELLOWORLD_SCENE_H__

64

Page 66: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

HelloWorldScene.h

#ifndef __HELLOWORLD_SCENE_H__

#define __HELLOWORLD_SCENE_H__

#include "cocos2d.h"

#include <vector>

using namespacestd;

USING_NS_CC;

#include "SimpleAudioEngine.h"

using namespace CocosDenshion;

#define BLACK 0

#define WHITE 1

#define NO_CHESSMAN 1000

#define BLACK_CHESSMAN 1001

#define WHITE_CHESSMAN 1002

#define NO_GAME 10000

#define GAME_VS_COMPUTER 10001

#define GAME_VS_FRIENDS 10002

#define WAITING 10003

#define WAITINGAI 10004

#define GAME_VS_BLUE 10006

#define BT_MYTURN 10010

#define BT_WAITTURN 10011

#define BT_OK 10000000

#define BT_CANCEL 10000001

#define BT_HOST 10000002

#define BT_CONNECT 10000003

#define UPPER_BOUND 14

#define LOWER_BOUND 0

#define CHENGWU 130

#define HUOSI 90

#define CHONGSI 80

#define SISI 5

#define LIANSAN 70

#define TIAOSAN 70

#define MIANSAN 60

#define SISAN 5

#define LIANER 50

65

Page 67: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

#define TIAOER 50

#define DATIAOER 40

#define MIANER 40

#define SIER 5

#define YI 20

#define ANTI_CHENGWU 110

#define ANTI_HUOSI HUOSI-3

#define ANTI_CHONGSI 74

#define ANTI_SISI SISI-7

#define ANTI_LIANSAN LIANSAN-7

#define ANTI_TIAOSAN TIAOSAN-8

#define ANTI_TSCHENGSI TIAOSAN

#define ANTI_SISAN SISAN-7

#define ANTI_MIANSAN MIANSAN-7

#define ANTI_LIANER LIANER-7

#define ANTI_TIAOER TIAOER-8

#define ANTI_DATIAOER DATIAOER-8

#define ANTI_MIANER MIANER-7

#define ANTI_SIER SIER-7

#define ANTI_YI YI-7

#define COEFFICIENT 0.2

#define POSITIVE_DIRECTION 0

#define OPPOSITE_DIRECTION 1

#define DEPTH 1

struct position

{

int x,y,weights;

};

class HelloWorld : public cocos2d::CCLayer

{

public:

// Here's a difference. Method 'init' in cocos2d-x returns bool, instead of

returning 'id' in cocos2d-iphone

virtual boolinit();

// there's no 'id' in cpp, so we recommend returning the class instance pointer

static cocos2d::CCScene* scene();

// a selector callback

void menuCloseCallback(CCObject* pSender);

66

Page 68: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// implement the "static node()" method manually

CREATE_FUNC(HelloWorld);

void YouCanStratBT() {m_StartGameBT = true;}

void BT_MOVECHESS(std::string chessmove) {m_CanProcess = true; m_chessmove

= chessmove;}

void processbtmove();

void startgame_bt();

void tick1sec(float dt);

private:

void PlayATurn();

void PlayBTurn();

void buttonCallback(CCNode *pNode);

void buttonBlueCallback(CCNode *pNode);

void buttonBlueCallback2(CCNode *pNode);

void restartgame();

void show_chessbox();

void vs_computer(CCObject* pSender);

void vs_friends(CCObject* pSender);

void vs_blue(CCObject* pSender);

void vs_help(CCObject* pSender);

void ccTouchesEnded(cocos2d::CCSet* touches, cocos2d::CCEvent* event);

void addNewSpriteAtPosition(cocos2d::CCPoint pos);

void chess_down(int& x,int& y);

void restart();

void init_data();

void regret(CCObject* pSender);

intinline transform_x(int x);

intinline transform_y(int y);

bool win_or_not(int& x,int& y);

void AI();

vector<position> search_depth(int depth,int color=WHITE_CHESSMAN);

int solve_weights(int& x,int& y);

boolinline out_of_chessbox(int& x,int& y);

bool func_siqi(int&dir,int& x,int& y,int color);

int func_lianer(int&dir,bool is_anti,int& x,int& y,int color);

int func_tiaoer(int&dir,bool is_anti,int& x,int& y,int color);

int func_datiaoer(int&dir,bool is_anti,int& x,int& y,int color);

67

Page 69: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

int func_MIANER(int&dir,bool is_anti,int& x,int& y,int color);

int func_liansan(int&dir,bool is_anti,int& x,int& y,int color);

int func_tiaosan(int&dir,bool is_anti,int& x,int& y,int color);

int func_MIANSAN(int&dir,bool is_anti,int& x,int& y,int color);

int func_huosi(int&dir,bool is_anti,int& x,int& y,int color);

int func_chongsi(int& dir,bool is_anti,int& x,int& y,int color);

int func_chengwu(int& dir,bool is_anti,int& x,int& y,int color);

int game_status,chesses_num;

int pre_game_status;

int sub_game_status;

bool chessman_color;

int cb_status[15][15];

vector<cocos2d::CCSprite*> chesses;

CCMenuItemLabel *btn1;

CCMenuItemLabel *btn2;

CCMenuItemLabel *btn3;

bool mAmIHost;

bool m_StartGameBT;

bool m_CanProcess;

std::string m_chessmove;

CCSprite* m_pChessBox;

CCMenuItemLabel* m_item_restart;

};

#endif // __HELLOWORLD_SCENE_H__

68

Page 70: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

InterfaceJNI.cpp

#include "InterfaceJNI.h"

#include "platform/android/jni/JniHelper.h"

#include <jni.h>

#include <android/log.h>

using namespace cocos2d;

void InterfaceJNI::DoBTConnect()

{

CCLog("Static DoBTConnect");

JniMethodInfo t;

if (JniHelper::getStaticMethodInfo(t

, "com/test/gobang/GoBang"

, "BT_ConnectToDevice"

, "()V"))

{

CCLog("Success In");

t.env->CallStaticVoidMethod(t.classID, t.methodID);

t.env->DeleteLocalRef(t.classID);

}

CCLog("Finish");

}

void InterfaceJNI::DoBTHost()

{

CCLog("Static DoBTHost");

JniMethodInfo t;

if (JniHelper::getStaticMethodInfo(t

, "com/test/gobang/GoBang"

, "BT_AsHost"

, "()V"))

{

CCLog("Success In");

t.env->CallStaticVoidMethod(t.classID, t.methodID);

t.env->DeleteLocalRef(t.classID);

}

CCLog("Finish");

}

void InterfaceJNI::SendMessage(const char* Message)

69

Page 71: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

{

CCLog("Static SendMessage");

JniMethodInfo t;

if (JniHelper::getStaticMethodInfo(t

, "com/test/gobang/GoBang"

, "SendChessMessage"

, "(Ljava/lang/String;)V"))

{

jstring StringArg1 = t.env->NewStringUTF(Message);

t.env->CallStaticVoidMethod(t.classID, t.methodID, StringArg1);

t.env->DeleteLocalRef(t.classID);

}

CCLog("Finish");

}

70

Page 72: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

InterfaceJNI.h

#ifndef __INTERFACE_JNI_H__

#define __INTERFACE_JNI_H__

#include "cocos2d.h"

class InterfaceJNI

{

public:

static void DoBTConnect();

static void DoBTHost();

//Webview

static void SendMessage(const char* Message);

//static void openExternalURLJNI(const char* url);

protected:

};

#endif // __INTERFACE_JNI_H__

71

Page 73: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

JNICallFromJava.cpp

#include <android/log.h>

#include <string.h>

#include <jni.h>

#include "platform/android/jni/JniHelper.h"

using namespace cocos2d;

void STARTGAMEWITHBT();

void ProcessChessMove(std::string movechess);

extern "C" {

void

Java_com_test_gobang_GoBang_NotifyConnectSuccess(JNIEnv* env, jobjectthiz,

jboolean bHost)

{

STARTGAMEWITHBT();

}

void

Java_com_test_gobang_GoBang_FriendMove(JNIEnv* env, jobjectthiz,jstringmov

estring)

{

const char * chessmessage = env->GetStringUTFChars(movestring, 0);

ProcessChessMove(chessmessage);

}

}

72

Page 74: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

PopupLayer.cpp

#include "PopupLayer.h"

PopupLayer::PopupLayer() :

m__pMenu(NULL)

, m_contentPadding(0)

, m_contentPaddingTop(0)

, m_callbackListener(NULL)

, m_callback(NULL)

, m__sfBackGround(NULL)

, m__s9BackGround(NULL)

, m__ltContentText(NULL)

, m__ltTitle(NULL)

{

}

PopupLayer::~PopupLayer()

{

CC_SAFE_RELEASE(m__pMenu);

CC_SAFE_RELEASE(m__sfBackGround);

CC_SAFE_RELEASE(m__ltContentText);

CC_SAFE_RELEASE(m__ltTitle);

CC_SAFE_RELEASE(m__s9BackGround);

}

bool PopupLayer::init()

{

bool bRef = false;

do

{

CC_BREAK_IF(!CCLayer::init());

this->setContentSize(CCSizeZero);

// 初始化需要的 Menu

CCMenu* menu = CCMenu::create();

menu->setPosition(CCPointZero);

setMenuButton(menu);

setTouchEnabled(true);

bRef = true;

} while (0);

return bRef;

73

Page 75: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

}

void PopupLayer::registerWithTouchDispatcher()

{

// 這裡的觸摸優先級設置為-128 這保證了,屏蔽下方的觸摸

CCDirector::sharedDirector()->getTouchDispatcher()->addTargetedDelegate

(this, -128, true);

}

bool PopupLayer::ccTouchBegan(cocos2d::CCTouch *pTouch, cocos2d::CCEvent

*pEvent)

{

CCLog("PopupLayer touch");

return true;

}

PopupLayer* PopupLayer::create(const char *backgroundImage)

{

PopupLayer* ml = PopupLayer::create();

ml->setSpriteBackGround(CCSprite::create(backgroundImage));

ml->setSprite9BackGround(CCScale9Sprite::create(backgroundImage));

return ml;

}

void PopupLayer::setTitle(const char*title, intfontsize)

{

CCLabelTTF* ltfTitle = CCLabelTTF::create(title, "", fontsize);

setLabelTitle(ltfTitle);

}

void PopupLayer::setContentText(const char *text, intfontsize, int padding, int

paddingTop){

CCLabelTTF* ltf = CCLabelTTF::create(text, "", fontsize);

setLabelContentText(ltf);

m_contentPadding = padding;

m_contentPaddingTop = paddingTop;

}

void PopupLayer::setCallbackFunc(cocos2d::CCObject *target,

SEL_CallFuncN callfun)

{

m_callbackListener = target;

m_callback = callfun;

}

74

Page 76: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

bool PopupLayer::addButton(const char *normalImage, const char

*selectedImage, const char *title, int tag){

CCSize winSize = CCDirector::sharedDirector()->getWinSize();

CCPoint pCenter = ccp(winSize.width / 2, winSize.height / 2);

// 創建圖片菜單按鈕

CCMenuItemImage* menuImage = CCMenuItemImage::create(normalImage,

selectedImage, this, menu_selector(PopupLayer::buttonCallback));

menuImage->setTag(tag);

menuImage->setPosition(pCenter);

// 添加文字說明並設置位置

CCSize imenu = menuImage->getContentSize();

CCLabelTTF* ttf = CCLabelTTF::create(title, "", 20);

ttf->setColor(ccc3(0, 0, 0));

ttf->setPosition(ccp(imenu.width / 2, imenu.height / 2));

menuImage->addChild(ttf);

getMenuButton()->addChild(menuImage);

return true;

}

void PopupLayer::buttonCallback(cocos2d::CCObject *pSender){

CCNode* node = dynamic_cast<CCNode*>(pSender);

CCLog("touch tag: %d", node->getTag());

if (m_callback && m_callbackListener){

(m_callbackListener->*m_callback)(node);

}

this->removeFromParentAndCleanup(true);

}

void PopupLayer::onEnter()

{

CCLayer::onEnter();

CCSize winSize = CCDirector::sharedDirector()->getWinSize();

CCPoint pCenter = ccp(winSize.width / 2, winSize.height / 2);

CCSize contentSize;

// 設定好參數,在運行時加載

if (getContentSize().equals(CCSizeZero))

{

getSpriteBackGround()->setPosition(ccp(winSize.width / 2,

winSize.height / 2));

this->addChild(getSpriteBackGround(), 0, 0);

75

Page 77: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

contentSize =

getSpriteBackGround()->getTexture()->getContentSize();

}

else

{

CCScale9Sprite *background = getSprite9BackGround();

background->setContentSize(getContentSize());

background->setPosition(ccp(winSize.width / 2, winSize.height / 2));

this->addChild(background, 0);

contentSize = getContentSize();

}

// 添加按鈕,並設置其位置

this->addChild(getMenuButton());

float btnWidth = contentSize.width / (getMenuButton()->getChildrenCount()

+ 1);

CCArray* array = getMenuButton()->getChildren();

CCObject* pObj = NULL;

int i = 0;

CCARRAY_FOREACH(array, pObj)

{

CCNode* node = dynamic_cast<CCNode*>(pObj);

node->setPosition(ccp(winSize.width / 2 - contentSize.width / 2 +

btnWidth * (i + 1), winSize.height / 2 - contentSize.height / 3));

i++;

}

// 顯示對話框標題

if (getLabelTitle())

{

getLabelTitle()->setPosition(ccpAdd(pCenter, ccp(0,

contentSize.height / 2 - 35.0f)));

this->addChild(getLabelTitle());

}

// 顯示文本內容

if (getLabelContentText())

{

CCLabelTTF* ltf = getLabelContentText();

ltf->setPosition(ccp(winSize.width / 2, winSize.height / 2));

ltf->setDimensions(CCSizeMake(contentSize.width - m_contentPadding *

76

Page 78: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

2, contentSize.height - m_contentPaddingTop));

ltf->setHorizontalAlignment(kCCTextAlignmentLeft);

this->addChild(ltf);

}

CCAction* popupLayer = CCSequence::create(CCScaleTo::create(0.0, 0.0),

CCScaleTo::create(0.06, 1.05),

CCScaleTo::create(0.08, 0.95),

CCScaleTo::create(0.08, 1.0),

NULL);

this->runAction(popupLayer);

}

void PopupLayer::onExit()

{

CCLog("popup on exit.");

CCLayer::onExit();

}

77

Page 79: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

PopupLayer.h

#pragma once

#include "cocos2d.h"

#include "cocos-ext.h"

USING_NS_CC;

USING_NS_CC_EXT;

class PopupLayer : public cocos2d::CCLayer

{

public:

PopupLayer();

~PopupLayer();

virtual boolinit();

CREATE_FUNC(PopupLayer);

// 需要重寫觸摸註冊函數,重新給定觸摸級別

virtual void registerWithTouchDispatcher(void);

// 重寫觸摸函數,永遠返回true ,屏蔽其它層,達到“模態”效果

bool ccTouchBegan(cocos2d::CCTouch *pTouch, cocos2d::CCEvent *pEvent);

// 構架,並設置對話框背景圖片

static PopupLayer* create(const char* backgroundImage);

// 它可以顯示標題,並且設定顯示文字大小

void setTitle(const char*title, intfontsize = 20);

// 文本內容,padding 為文字到對話框兩邊預留的距離,這是可控的,距上方的距離亦是

如此

void setContentText(const char *text, intfontsize = 20, int padding = 50, int

paddintTop = 100);

// 回調函數,當點擊按鈕後,我們關閉彈出層的同事,需要一個回調函數,以通知我們點

擊了哪個按鈕(如果有多個)

void setCallbackFunc(CCObject* target, SEL_CallFuncN callfun);

// 為了添加按鈕方面,封裝了一個函數,傳入些必要的參數

bool addButton(const char* normalImage, const char* selectedImage, const

char* title, int tag = 0);

// 為了在顯示層時之前的屬性生效,選擇在onEnter 裡動態展示

virtual void onEnter();

78

Page 80: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

virtual void onExit();

private:

void buttonCallback(CCObject* pSender);

// 文字內容兩邊的空白區

int m_contentPadding;

int m_contentPaddingTop;

CCObject* m_callbackListener;

SEL_CallFuncN m_callback;

CC_SYNTHESIZE_RETAIN(CCMenu*, m__pMenu, MenuButton);

CC_SYNTHESIZE_RETAIN(CCSprite*, m__sfBackGround, SpriteBackGround);

CC_SYNTHESIZE_RETAIN(CCScale9Sprite*, m__s9BackGround,

Sprite9BackGround);

CC_SYNTHESIZE_RETAIN(CCLabelTTF*, m__ltTitle, LabelTitle);

CC_SYNTHESIZE_RETAIN(CCLabelTTF*, m__ltContentText, LabelContentText);

};

79

Page 81: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

BluetoothChatService

package com.test.gobang;

import java.io.IOException;

import java.io.InputStream;

import java.io.OutputStream;

import java.util.UUID;

import android.bluetooth.BluetoothAdapter;

import android.bluetooth.BluetoothDevice;

import android.bluetooth.BluetoothServerSocket;

import android.bluetooth.BluetoothSocket;

import android.content.Context;

import android.os.Bundle;

import android.os.Handler;

import android.os.Message;

import android.util.Log;

/**

* This class does all the work for setting up and managing Bluetooth

* connections with other devices. It has a thread that listens for

* incoming connections, a thread for connecting with a device, and a

* thread for performing data transmissions when connected.

*/

public class BluetoothChatService {

// Debugging

private static final String TAG = "BluetoothChatService";

private static final boolean D = true;

// Name for the SDP record when creating server socket

private static final String NAME = "BluetoothChat";

// Unique UUID for this application

private static final UUID MY_UUID =

UUID.fromString("fa87c0d0-afac-11de-8a39-0800200c9a66");

// Member fields

private final BluetoothAdapter mAdapter;

private final Handler mHandler;

private AcceptThread mAcceptThread;

private ConnectThread mConnectThread;

private ConnectedThread mConnectedThread;

private int mState;

80

Page 82: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// Constants that indicate the current connection state

public static final int STATE_NONE = 0; // we're doing nothing

public static final int STATE_LISTEN = 1; // now listening for incoming

connections

public static final int STATE_CONNECTING = 2; // now initiating an outgoing

connection

public static final int STATE_CONNECTED = 3; // now connected to a remote

device

/**

* Constructor. Prepares a new BluetoothChat session.

* @param context The UI Activity Context

* @param handler A Handler to send messages back to the UI Activity

*/

public BluetoothChatService(Context context, Handler handler) {

mAdapter = BluetoothAdapter.getDefaultAdapter();

mState = STATE_NONE;

mHandler = handler;

}

/**

* Set the current state of the chat connection

* @param state An integer defining the current connection state

*/

private synchronized void setState(int state) {

if (D) Log.d(TAG, "setState() " + mState + " -> " + state);

mState = state;

// Give the new state to the Handler so the UI Activity can update

mHandler.obtainMessage(GoBang.MESSAGE_STATE_CHANGE, state,

-1).sendToTarget();

}

/**

* Return the current connection state. */

public synchronized int getState() {

return mState;

}

/**

* Start the chat service. Specifically start AcceptThread to begin a

81

Page 83: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

* session in listening (server) mode. Called by the Activity onResume()

*/

public synchronized void start() {

if (D) Log.d(TAG, "start");

// Cancel any thread attempting to make a connection

if (mConnectThread != null) {mConnectThread.cancel(); mConnectThread =

null;}

// Cancel any thread currently running a connection

if (mConnectedThread != null) {mConnectedThread.cancel();

mConnectedThread = null;}

// Start the thread to listen on a BluetoothServerSocket

if (mAcceptThread == null) {

mAcceptThread = new AcceptThread();

mAcceptThread.start();

}

setState(STATE_LISTEN);

}

/**

* Start the ConnectThread to initiate a connection to a remote device.

* @param device The BluetoothDevice to connect

*/

public synchronized void connect(BluetoothDevice device) {

if (D) Log.d(TAG, "connect to: " + device);

// Cancel any thread attempting to make a connection

if (mState == STATE_CONNECTING) {

if (mConnectThread != null) {mConnectThread.cancel();

mConnectThread = null;}

}

// Cancel any thread currently running a connection

if (mConnectedThread != null) {mConnectedThread.cancel();

mConnectedThread = null;}

// Start the thread to connect with the given device

mConnectThread = new ConnectThread(device);

mConnectThread.start();

setState(STATE_CONNECTING);

}

/**

* Start the ConnectedThread to begin managing a Bluetooth connection

82

Page 84: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

* @param socket The BluetoothSocket on which the connection was made

* @param device The BluetoothDevice that has been connected

*/

public synchronized void connected(BluetoothSocket socket, BluetoothDevice

device) {

if (D) Log.d(TAG, "connected");

// Cancel the thread that completed the connection

if (mConnectThread != null) {mConnectThread.cancel(); mConnectThread =

null;}

// Cancel any thread currently running a connection

if (mConnectedThread != null) {mConnectedThread.cancel();

mConnectedThread = null;}

// Cancel the accept thread because we only want to connect to one device

if (mAcceptThread != null) {mAcceptThread.cancel(); mAcceptThread =

null;}

// Start the thread to manage the connection and perform transmissions

mConnectedThread = new ConnectedThread(socket);

mConnectedThread.start();

// Send the name of the connected device back to the UI Activity

Message msg = mHandler.obtainMessage(GoBang.MESSAGE_DEVICE_NAME);

Bundle bundle = new Bundle();

bundle.putString(GoBang.DEVICE_NAME, device.getName());

msg.setData(bundle);

mHandler.sendMessage(msg);

setState(STATE_CONNECTED);

}

/**

* Stop all threads

*/

public synchronized void stop() {

if (D) Log.d(TAG, "stop");

if (mConnectThread != null) {mConnectThread.cancel(); mConnectThread =

null;}

if (mConnectedThread != null) {mConnectedThread.cancel();

mConnectedThread = null;}

if (mAcceptThread != null) {mAcceptThread.cancel(); mAcceptThread =

null;}

setState(STATE_NONE);

83

Page 85: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

}

/**

* Write to the ConnectedThread in an unsynchronized manner

* @param out The bytes to write

* @see ConnectedThread#write(byte[])

*/

public void write(byte[] out) {

// Create temporary object

ConnectedThread r;

// Synchronize a copy of the ConnectedThread

synchronized (this) {

if (mState != STATE_CONNECTED) return;

r = mConnectedThread;

}

// Perform the write unsynchronized

r.write(out);

}

/**

* Indicate that the connection attempt failed and notify the UI Activity.

*/

private void connectionFailed() {

setState(STATE_LISTEN);

// Send a failure message back to the Activity

Message msg = mHandler.obtainMessage(GoBang.MESSAGE_TOAST);

Bundle bundle = new Bundle();

bundle.putString(GoBang.TOAST, "Unable to connect device");

msg.setData(bundle);

mHandler.sendMessage(msg);

}

/**

* Indicate that the connection was lost and notify the UI Activity.

*/

private void connectionLost() {

setState(STATE_LISTEN);

// Send a failure message back to the Activity

Message msg = mHandler.obtainMessage(GoBang.MESSAGE_TOAST);

Bundle bundle = new Bundle();

bundle.putString(GoBang.TOAST, "Device connection was lost");

84

Page 86: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

msg.setData(bundle);

mHandler.sendMessage(msg);

}

/**

* This thread runs while listening for incoming connections. It behaves

* like a server-side client. It runs until a connection is accepted

* (or until cancelled).

*/

private class AcceptThread extends Thread {

// The local server socket

private final BluetoothServerSocket mmServerSocket;

public AcceptThread() {

BluetoothServerSocket tmp = null;

// Create a new listening server socket

try {

tmp = mAdapter.listenUsingRfcommWithServiceRecord(NAME,

MY_UUID);

} catch (IOException e) {

Log.e(TAG, "listen() failed", e);

}

mmServerSocket = tmp;

}

public void run() {

if (D) Log.d(TAG, "BEGIN mAcceptThread" + this);

setName("AcceptThread");

BluetoothSocket socket = null;

// Listen to the server socket if we're not connected

while (mState != STATE_CONNECTED) {

try {

// This is a blocking call and will only return on a

// successful connection or an exception

socket = mmServerSocket.accept();

} catch (IOException e) {

Log.e(TAG, "accept() failed", e);

break;

}

// If a connection was accepted

if (socket != null) {

85

Page 87: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

synchronized (BluetoothChatService.this) {

switch (mState) {

case STATE_LISTEN:

case STATE_CONNECTING:

// Situation normal. Start the connected thread.

connected(socket, socket.getRemoteDevice());

break;

case STATE_NONE:

case STATE_CONNECTED:

// Either not ready or already connected. Terminate

new socket.

try {

socket.close();

} catch (IOException e) {

Log.e(TAG, "Could not close unwanted socket", e);

}

break;

}

}

}

}

if (D) Log.i(TAG, "END mAcceptThread");

}

public void cancel() {

if (D) Log.d(TAG, "cancel " + this);

try {

mmServerSocket.close();

} catch (IOException e) {

Log.e(TAG, "close() of server failed", e);

}

}

}

/**

* This thread runs while attempting to make an outgoing connection

* with a device. It runs straight through; the connection either

* succeeds or fails.

*/

private class ConnectThread extends Thread {

86

Page 88: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

private final BluetoothSocket mmSocket;

private final BluetoothDevice mmDevice;

public ConnectThread(BluetoothDevice device) {

mmDevice = device;

BluetoothSocket tmp = null;

// Get a BluetoothSocket for a connection with the

// given BluetoothDevice

try {

tmp = device.createRfcommSocketToServiceRecord(MY_UUID);

} catch (IOException e) {

Log.e(TAG, "create() failed", e);

}

mmSocket = tmp;

}

public void run() {

Log.i(TAG, "BEGIN mConnectThread");

setName("ConnectThread");

// Always cancel discovery because it will slow down a connection

mAdapter.cancelDiscovery();

// Make a connection to the BluetoothSocket

try {

// This is a blocking call and will only return on a

// successful connection or an exception

mmSocket.connect();

} catch (IOException e) {

connectionFailed();

// Close the socket

try {

mmSocket.close();

} catch (IOException e2) {

Log.e(TAG, "unable to close() socket during connection

failure", e2);

}

// Start the service over to restart listening mode

BluetoothChatService.this.start();

return;

}

// Reset the ConnectThread because we're done

87

Page 89: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

synchronized (BluetoothChatService.this) {

mConnectThread = null;

}

// Start the connected thread

connected(mmSocket, mmDevice);

}

public void cancel() {

try {

mmSocket.close();

} catch (IOException e) {

Log.e(TAG, "close() of connect socket failed", e);

}

}

}

/**

* This thread runs during a connection with a remote device.

* It handles all incoming and outgoing transmissions.

*/

private class ConnectedThread extends Thread {

private final BluetoothSocket mmSocket;

private final InputStream mmInStream;

private final OutputStream mmOutStream;

public ConnectedThread(BluetoothSocket socket) {

Log.d(TAG, "create ConnectedThread");

mmSocket = socket;

InputStream tmpIn = null;

OutputStream tmpOut = null;

// Get the BluetoothSocket input and output streams

try {

tmpIn = socket.getInputStream();

tmpOut = socket.getOutputStream();

} catch (IOException e) {

Log.e(TAG, "temp sockets not created", e);

}

mmInStream = tmpIn;

mmOutStream = tmpOut;

}

public void run() {

88

Page 90: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

Log.i(TAG, "BEGIN mConnectedThread");

byte[] buffer = new byte[1024];

int bytes;

// Keep listening to the InputStream while connected

while (true) {

try {

// Read from the InputStream

bytes = mmInStream.read(buffer);

// Send the obtained bytes to the UI Activity

mHandler.obtainMessage(GoBang.MESSAGE_READ, bytes, -1,

buffer)

.sendToTarget();

} catch (IOException e) {

Log.e(TAG, "disconnected", e);

connectionLost();

break;

}

}

}

/**

* Write to the connected OutStream.

* @param buffer The bytes to write

*/

public void write(byte[] buffer) {

try {

mmOutStream.write(buffer);

// Share the sent message back to the UI Activity

mHandler.obtainMessage(GoBang.MESSAGE_WRITE, -1, -1, buffer)

.sendToTarget();

} catch (IOException e) {

Log.e(TAG, "Exception during write", e);

}

}

public void cancel() {

try {

mmSocket.close();

} catch (IOException e) {

Log.e(TAG, "close() of connect socket failed", e);

89

Page 91: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

}

}

}

}

DeviceListActivity.java

package com.test.gobang;

import java.util.Set;

import android.app.Activity;

import android.bluetooth.BluetoothAdapter;

import android.bluetooth.BluetoothDevice;

import android.content.BroadcastReceiver;

import android.content.Context;

import android.content.Intent;

import android.content.IntentFilter;

import android.os.Bundle;

import android.util.Log;

import android.view.View;

import android.view.Window;

import android.view.View.OnClickListener;

import android.widget.AdapterView;

import android.widget.ArrayAdapter;

import android.widget.Button;

import android.widget.ListView;

import android.widget.TextView;

import android.widget.AdapterView.OnItemClickListener;

/**

* This Activity appears as a dialog. It lists any paired devices and

* devices detected in the area after discovery. When a device is chosen

* by the user, the MAC address of the device is sent back to the parent

* Activity in the result Intent.

*/

public class DeviceListActivity extends Activity {

// Debugging

private static final String TAG = "DeviceListActivity";

private static final boolean D = true;

90

Page 92: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// Return Intent extra

public static String EXTRA_DEVICE_ADDRESS = "device_address";

// Member fields

private BluetoothAdapter mBtAdapter;

private ArrayAdapter<String> mPairedDevicesArrayAdapter;

private ArrayAdapter<String> mNewDevicesArrayAdapter;

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

// Setup the window

requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);

setContentView(R.layout.device_list);

// Set result CANCELED incase the user backs out

setResult(Activity.RESULT_CANCELED);

// Initialize the button to perform device discovery

Button scanButton = (Button) findViewById(R.id.button_scan);

scanButton.setOnClickListener(new OnClickListener() {

public void onClick(View v) {

doDiscovery();

v.setVisibility(View.GONE);

}

});

// Initialize array adapters. One for already paired devices and

// one for newly discovered devices

mPairedDevicesArrayAdapter = new ArrayAdapter<String>(this,

R.layout.device_name);

mNewDevicesArrayAdapter = new ArrayAdapter<String>(this,

R.layout.device_name);

// Find and set up the ListView for paired devices

ListView pairedListView = (ListView)

findViewById(R.id.paired_devices);

pairedListView.setAdapter(mPairedDevicesArrayAdapter);

pairedListView.setOnItemClickListener(mDeviceClickListener);

// Find and set up the ListView for newly discovered devices

ListView newDevicesListView = (ListView)

findViewById(R.id.new_devices);

newDevicesListView.setAdapter(mNewDevicesArrayAdapter);

newDevicesListView.setOnItemClickListener(mDeviceClickListener);

91

Page 93: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// Register for broadcasts when a device is discovered

IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND);

this.registerReceiver(mReceiver, filter);

// Register for broadcasts when discovery has finished

filter = new

IntentFilter(BluetoothAdapter.ACTION_DISCOVERY_FINISHED);

this.registerReceiver(mReceiver, filter);

// Get the local Bluetooth adapter

mBtAdapter = BluetoothAdapter.getDefaultAdapter();

// Get a set of currently paired devices

Set<BluetoothDevice> pairedDevices = mBtAdapter.getBondedDevices();

// If there are paired devices, add each one to the ArrayAdapter

if (pairedDevices.size() > 0) {

findViewById(R.id.title_paired_devices).setVisibility(View.VISIBLE);

for (BluetoothDevice device : pairedDevices) {

mPairedDevicesArrayAdapter.add(device.getName() + "\n" +

device.getAddress());

}

} else {

String noDevices =

getResources().getText(R.string.none_paired).toString();

mPairedDevicesArrayAdapter.add(noDevices);

}

}

@Override

protected void onDestroy() {

super.onDestroy();

// Make sure we're not doing discovery anymore

if (mBtAdapter != null) {

mBtAdapter.cancelDiscovery();

}

// Unregister broadcast listeners

this.unregisterReceiver(mReceiver);

}

/**

* Start device discover with the BluetoothAdapter

92

Page 94: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

*/

private void doDiscovery() {

if (D) Log.d(TAG, "doDiscovery()");

// Indicate scanning in the title

setProgressBarIndeterminateVisibility(true);

setTitle(R.string.scanning);

// Turn on sub-title for new devices

findViewById(R.id.title_new_devices).setVisibility(View.VISIBLE);

// If we're already discovering, stop it

if (mBtAdapter.isDiscovering()) {

mBtAdapter.cancelDiscovery();

}

// Request discover from BluetoothAdapter

mBtAdapter.startDiscovery();

}

// The on-click listener for all devices in the ListViews

private OnItemClickListener mDeviceClickListener = new

OnItemClickListener() {

public void onItemClick(AdapterView<?> av, View v, int arg2, long arg3)

{

// Cancel discovery because it's costly and we're about to connect

mBtAdapter.cancelDiscovery();

// Get the device MAC address, which is the last 17 chars in the View

String info = ((TextView) v).getText().toString();

String address = info.substring(info.length() - 17);

// Create the result Intent and include the MAC address

Intent intent = new Intent();

intent.putExtra(EXTRA_DEVICE_ADDRESS, address);

// Set result and finish this Activity

setResult(Activity.RESULT_OK, intent);

finish();

}

};

// The BroadcastReceiver that listens for discovered devices and

// changes the title when discovery is finished

private final BroadcastReceiver mReceiver = new BroadcastReceiver() {

@Override

public void onReceive(Context context, Intent intent) {

93

Page 95: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

String action = intent.getAction();

// When discovery finds a device

if (BluetoothDevice.ACTION_FOUND.equals(action)) {

// Get the BluetoothDevice object from the Intent

BluetoothDevice device =

intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);

// If it's already paired, skip it, because it's been listed

already

if (device.getBondState() != BluetoothDevice.BOND_BONDED) {

mNewDevicesArrayAdapter.add(device.getName() + "\n" +

device.getAddress());

}

// When discovery is finished, change the Activity title

} else if

(BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(action)) {

setProgressBarIndeterminateVisibility(false);

setTitle(R.string.select_device);

if (mNewDevicesArrayAdapter.getCount() == 0) {

String noDevices =

getResources().getText(R.string.none_found).toString();

mNewDevicesArrayAdapter.add(noDevices);

}

}

}

};

}

94

Page 96: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

GoBang.java

package com.test.gobang;

import org.cocos2dx.lib.Cocos2dxActivity;

import org.cocos2dx.lib.Cocos2dxGLSurfaceView;

import android.os.Bundle;

import android.os.Handler;

import android.os.Message;

import android.app.Activity;

import android.bluetooth.BluetoothAdapter;

import android.bluetooth.BluetoothDevice;

import android.content.Intent;

import android.util.Log;

import android.widget.ArrayAdapter;

import android.widget.Toast;

public class GoBang extends Cocos2dxActivity{

private static Activity me = null;

// Debugging

private static final String TAG = "BluetoothChat";

private static final boolean D = true;

// Message types sent from the BluetoothChatService Handler

public static final int MESSAGE_STATE_CHANGE = 1;

public static final int MESSAGE_READ = 2;

public static final int MESSAGE_WRITE = 3;

public static final int MESSAGE_DEVICE_NAME = 4;

public static final int MESSAGE_TOAST = 5;

// Key names received from the BluetoothChatService Handler

public static final String DEVICE_NAME = "device_name";

public static final String TOAST = "toast";

// Intent request codes

private static final int REQUEST_CONNECT_DEVICE = 1;

private static final int REQUEST_ENABLE_BT = 2;

// Name of the connected device

private String mConnectedDeviceName = null;

// Array adapter for the conversation thread

//private ArrayAdapter<String> mConversationArrayAdapter;

// String buffer for outgoing messages

private StringBuffer mOutStringBuffer;

95

Page 97: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

// Local Bluetooth adapter

private BluetoothAdapter mBluetoothAdapter = null;

// Member object for the chat services

private BluetoothChatService mChatService = null;

private static native void NotifyConnectSuccess(Boolean bHost);

private static native void FriendMove(String movestring);

protected void onCreate(Bundle savedInstanceState){

super.onCreate(savedInstanceState);

me = this;

// Get local Bluetooth adapter

mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();

// If the adapter is null, then Bluetooth is not supported

if (mBluetoothAdapter == null) {

Toast.makeText(this, "Bluetooth is not available",

Toast.LENGTH_LONG).show();

finish();

return;

}

}

@Override

public void onStart() {

super.onStart();

if(D) Log.e(TAG, "++ ON START ++");

// If BT is not on, request that it be enabled.

// setupChat() will then be called during onActivityResult

if (!mBluetoothAdapter.isEnabled()) {

Intent enableIntent = new

Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);

startActivityForResult(enableIntent, REQUEST_ENABLE_BT);

// Otherwise, setup the chat session

} else {

if (mChatService == null) setupChat();

}

}

@Override

public synchronized void onResume() {

96

Page 98: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

super.onResume();

if(D) Log.e(TAG, "+ ON RESUME +");

// Performing this check in onResume() covers the case in which BT was

// not enabled during onStart(), so we were paused to enable it...

// onResume() will be called when ACTION_REQUEST_ENABLE activity

returns.

if (mChatService != null) {

// Only if the state is STATE_NONE, do we know that we haven't started

already

if (mChatService.getState() == BluetoothChatService.STATE_NONE) {

// Start the Bluetooth chat services

mChatService.start();

}

}

}

@Override

public synchronized void onPause() {

super.onPause();

if(D) Log.e(TAG, "- ON PAUSE -");

}

@Override

public void onStop() {

super.onStop();

if(D) Log.e(TAG, "-- ON STOP --");

}

@Override

public void onDestroy() {

super.onDestroy();

// Stop the Bluetooth chat services

if (mChatService != null) mChatService.stop();

if(D) Log.e(TAG, "--- ON DESTROY ---");

}

private void setupChat() {

// Initialize the BluetoothChatService to perform bluetooth connections

mChatService = new BluetoothChatService(this, mHandler);

// Initialize the buffer for outgoing messages

mOutStringBuffer = new StringBuffer("");

97

Page 99: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

}

public void ensureDiscoverable() {

if(D) Log.d(TAG, "ensure discoverable");

if (mBluetoothAdapter.getScanMode() !=

BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) {

Intent discoverableIntent = new

Intent(BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE);

discoverableIntent.putExtra(BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION,

300);

startActivity(discoverableIntent);

}

}

/**

* Sends a message.

* @param message A string of text to send.

*/

private void sendMessage(String message) {

// Check that we're actually connected before trying anything

if (mChatService.getState() != BluetoothChatService.STATE_CONNECTED) {

Toast.makeText(this, R.string.not_connected,

Toast.LENGTH_SHORT).show();

return;

}

// Check that there's actually something to send

if (message.length() > 0) {

// Get the message bytes and tell the BluetoothChatService to write

byte[] send = message.getBytes();

mChatService.write(send);

// Reset out string buffer to zero and clear the edit text field

mOutStringBuffer.setLength(0);

//mOutEditText.setText(mOutStringBuffer);

}

}

// The Handler that gets information back from the BluetoothChatService

private final Handler mHandler = new Handler() {

@Override

98

Page 100: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

public void handleMessage(Message msg) {

switch (msg.what) {

case MESSAGE_STATE_CHANGE:

if(D) Log.i(TAG, "MESSAGE_STATE_CHANGE: " + msg.arg1);

switch (msg.arg1) {

case BluetoothChatService.STATE_CONNECTED:

//mTitle.setText(R.string.title_connected_to);

//mTitle.append(mConnectedDeviceName);

//mConversationArrayAdapter.clear();

NotifyConnectSuccess(true);

if(D) Log.i(TAG, "IN:MESSAGE_STATE_CHANGE");

break;

case BluetoothChatService.STATE_CONNECTING:

//mTitle.setText(R.string.title_connecting);

break;

case BluetoothChatService.STATE_LISTEN:

case BluetoothChatService.STATE_NONE:

//mTitle.setText(R.string.title_not_connected);

break;

}

break;

case MESSAGE_WRITE:

byte[] writeBuf = (byte[]) msg.obj;

// construct a string from the buffer

String writeMessage = new String(writeBuf);

if(D) Log.i(TAG, "MESSAGE_WRITE"+writeMessage);

//mConversationArrayAdapter.add("Me: " + writeMessage);

break;

case MESSAGE_READ:

byte[] readBuf = (byte[]) msg.obj;

// construct a string from the valid bytes in the buffer

String readMessage = new String(readBuf, 0, msg.arg1);

FriendMove(readMessage);

if(D) Log.i(TAG, "MESSAGE_READ"+readMessage);

//mConversationArrayAdapter.add(mConnectedDeviceName+": " +

readMessage);

99

Page 101: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

break;

case MESSAGE_DEVICE_NAME:

// save the connected device's name

mConnectedDeviceName = msg.getData().getString(DEVICE_NAME);

Toast.makeText(getApplicationContext(), "Connected to "

+ mConnectedDeviceName,

Toast.LENGTH_SHORT).show();

break;

case MESSAGE_TOAST:

Toast.makeText(getApplicationContext(),

msg.getData().getString(TOAST),

Toast.LENGTH_SHORT).show();

break;

}

}

};

public void onActivityResult(int requestCode, int resultCode, Intent data)

{

super.onActivityResult(requestCode, resultCode, data);

if(D) Log.d(TAG, "onActivityResult " + resultCode);

switch (requestCode) {

case REQUEST_CONNECT_DEVICE:

// When DeviceListActivity returns with a device to connect

if (resultCode == Activity.RESULT_OK) {

// Get the device MAC address

String address = data.getExtras()

.getString(DeviceListActivity.EXTRA_DEVIC

E_ADDRESS);

// Get the BLuetoothDevice object

BluetoothDevice device =

mBluetoothAdapter.getRemoteDevice(address);

// Attempt to connect to the device

mChatService.connect(device);

}

break;

case REQUEST_ENABLE_BT:

// When the request to enable Bluetooth returns

100

Page 102: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

if (resultCode == Activity.RESULT_OK) {

// Bluetooth is now enabled, so set up a chat session

setupChat();

} else {

// User did not enable Bluetooth or an error occured

Log.d(TAG, "BT not enabled");

Toast.makeText(this, R.string.bt_not_enabled_leaving,

Toast.LENGTH_SHORT).show();

finish();

}

}

}

//call from c++

private static void BT_ConnectToDevice()

{

Intent serverIntent = new Intent(me, DeviceListActivity.class);

me.startActivityForResult(serverIntent, REQUEST_CONNECT_DEVICE);

}

private static void BT_AsHost()

{

((GoBang) me).ensureDiscoverable();

}

private static void SendChessMessage(final String chessmessage)

{

((GoBang) me).sendMessage(chessmessage);

}

public Cocos2dxGLSurfaceView onCreateView() {

Cocos2dxGLSurfaceView glSurfaceView = new Cocos2dxGLSurfaceView(this);

// GoBang should create stencil buffer

glSurfaceView.setEGLConfigChooser(5, 6, 5, 0, 16, 8);

return glSurfaceView;

}

static {

System.loadLibrary("cocos2dcpp");

}

}

101

Page 103: 修平科技大學 - ir.hust.edu.twir.hust.edu.tw/bitstream/310993100/4334/1/藍芽連線五子棋.pdf · 第二章 文獻探討11. 2-1 藍芽應用13. 2-2 Android開發環境14

102