プログラミング工房
TOP
Flex基本
開発環境 JavaScript連携 PHP連携1 PHP連携2(AMFPHP) ウィンドウ ボタンスキン 矩形スキン ローカルファイル(テキスト) F5等の対策 ローカルファイル(イメージ) ダウンロード、アップロード 1枚の画像のカラーを変更 時間のかかる計算処理 外部SWFの読込み
Flexで3D
Flexだけで3D Papervision3Dを使ってみる 3Dオブジェクト カメラ、前後判定の工夫しました 自由な形状を作成
Flexでクラス
Class1(白黒ゲームの盤) Class2(白黒ゲームのプレイヤー) Class3(プレイヤーを外部SWF)
PHP
共通関数1
Flexの作品
お問合せの説明 サンプルのソース表示の説明 分子構造の表示(PDBファイル) マンデルブロ集合の画像作成 swf参加型白黒ゲーム(Reversi) ストップウォッチ WEB素材
AIR
AIRを使ってみる ソースファイルのHTML変換を作る
etc.
マンデルブロ集合のギャラリー ジュリア集合のギャラリー wonderflを使ってみました お問合せ

Flexでクラス-Class2(白黒ゲームのプレイヤー)

■2011.04.20:作成
サンプル サンプルのソース

Flexでクラス-Class2(白黒ゲームのプレイヤー)

Flexでクラス-Class1(白黒ゲームの盤) で白黒ゲームが一応動くようになったので、今度はプレイヤーのクラスを作ってみます。
作成クラスはプレイヤーの基底クラス、人間が操作するプレイヤーと自動で打つプレイヤーです。

自動で打つプレイヤーは、難しいロジックは組めないので 「左上からすべての升目をチェック」して最初に見つけた位置に打つことにします。

プレイヤーの基底クラス clsPlayer.as

プレイヤーの基底クラスは、盤クラスと同じ基底クラス「Sprite」を持ちます。

clsPlayer() //コンストラクター
setColor(ip:int・・) //プレイヤーの初期化
 プレイヤーの色(黒(=1),白(=2))を指定する
 盤(駒)の状態を取得する関数群(chkIti、masuJyoutai、getRireki、Kekka)
fncRun(fRet:Function) //打つ番が来たときにコールされる関数
 引数は駒を打つ時にコールする関数。(fRet)
 戻り値:盤のクリックイベントの登録関数(プレイヤーが人間の時使用、それ以外は不要(null))
fncEnd() //ゲーム終了
//プレイヤーの基底クラス
package cls {
    import flash.display.Sprite;

    public class clsPlayer extends Sprite {
        //コンストラクター================================================
        public function clsPlayer():void {
        }
        //プレイヤーの初期化===========================================
        // ip:プレイヤーのno(黒=1or白=2)
        // chkIti:指定升目に打てるかチェック(clsBoardの関数) 
        //        chkIti(itiNam:String, ip:int):int
        // masuJyoutai:指定位置の枡の状態(clsBoardの関数) 
        //        masuJyoutai(itiNam:String):int
        // getRireki:履歴の取得(clsBoardの関数)
        //        getRireki(no:int):Object
        // Kekka:駒数(clsBoardの関数)
        //        Kekka(ip:int):int
        public function setColor(ip:int, chkIti:Function,
                masuJyoutai:Function,
                getRireki:Function,Kekka:Function):void {
        }
        //打つ番が来たときにコールされる関数==============================
        // fRet:打つ升目が決まったとき呼ぶ関数 fncOnxy(iti:String):void
        // 戻り値:盤をクリックした時にコールされる関数
        //       (プレイヤーが人間のとき使用,不要の時null)
        //       fucClic(itiNam:String):void
        public function fncRun(fRet:Function):Function {
            return null;
        }
        //ゲーム終了===========================================
        public function fncEnd():void {
        }
    }
}

人間が操作するプレイヤー clsPlMan.as

「clsPlayer」を基底クラスにもちます。これにより「Sprite」の表示機能が使えます。
コンストラクター、初期化関数で初期表示を行います。
setColor()で自分の色の表示と、盤クラスの関数を保持します。
fncRun()で盤がクリックイベントに「fucClic」を登録します。
 「fucClic」がコールされたときに「fncRet」でクラス利用側にクリック升目を返します。
fncEnd()では勝敗を自分の表示エリアに書きます。
package cls {
    import flash.display.Sprite;
    import flash.text.TextField;
    import flash.text.TextFieldAutoSize;
    import flash.events.Event;
    import flash.events.MouseEvent;
    import spark.components.mediaClasses.VolumeBar;

    public class clsPlMan extends clsPlayer {
        private var textColNam:TextField;
        private var textMessg:TextField;
        private var fncRet:Function;
        private var ipNo:int;
        private var fncChkIti:Function;
        private var fncMasuJyoutai:Function;
        private var fncGetRireki:Function;
        private var fncKekka:Function;
        //コンストラクター================================================
        public function clsPlMan():void {
            if (stage) init();
            else addEventListener(Event.ADDED_TO_STAGE, init);
        }
        //初期化
        private function init(e:Event = null):void {
            removeEventListener(Event.ADDED_TO_STAGE, init);
            textColNam = new TextField();
            textColNam.autoSize = TextFieldAutoSize.LEFT;
            textColNam.width = 250;
            textColNam.wordWrap = true;
            textColNam.x = 5;
            textColNam.y = 5;
            textColNam.text = "人間です。";
            addChild(textColNam);
            textMessg = new TextField();
            textMessg.autoSize = TextFieldAutoSize.LEFT;
            textMessg.width = 250;
            textMessg.wordWrap = true;
            textMessg.x = 5;
            textMessg.y = 25;
            textMessg.text = "準備中";
            addChild(textMessg);
            // 四角形を描く (中を塗りつぶす)
            graphics.lineStyle(1, 0x0000ff);
            graphics.beginFill(0xcccccc);
            graphics.drawRect(0, 0, 300, 50);
            graphics.endFill();
        }
        //プレイヤーの初期化===========================================
        // ip:プレイヤーのno(黒=1or白=2)
        // chkIti:指定升目に打てるかチェック(clsBoardの関数) 
        //        chkIti(itiNam:String, ip:int):int
        // masuJyoutai:指定位置の枡の状態(clsBoardの関数) 
        //        masuJyoutai(itiNam:String):int
        // getRireki:履歴の取得(clsBoardの関数)
        //        getRireki(no:int):Object
        // Kekka:駒数(clsBoardの関数)
        //        Kekka(ip:int):int
        override public function setColor(ip:int, chkIti:Function,
                masuJyoutai:Function,
                getRireki:Function,Kekka:Function):void {
            ipNo=ip;
            fncChkIti=chkIti;
            fncMasuJyoutai=masuJyoutai;
            fncGetRireki=getRireki;
            fncKekka = Kekka;
            textColNam.text = clsRevCom.getPlColNam(ipNo)+"-人間です。";
            textMessg.text = "まってます。";
        }
        //打つ番が来たときにコールされる関数==============================
        // fRet:打つ升目が決まったとき呼ぶ関数 fncOnxy(iti:String):void
        // 戻り値:盤をクリックした時にコールされる関数
        //       (プレイヤーが人間のとき使用,不要の時null)
        //       fucClic(itiNam:String):void
        override public function fncRun(fRet:Function):Function {
            fncRet = fRet;
            textMessg.text = "クリックして下さい。";
            return fucClic; //盤がクリックしたときの関数
        }
        //盤がクリックしたときの関数
        private function fucClic(itiNam:String):void {
            textMessg.text = "まってます。";
            fncRet(itiNam);
        }
        //ゲーム終了===========================================
        override public function fncEnd():void {
            var ip1n:int = fncKekka(ipNo);
            var ip2n:int = fncKekka(clsRevCom.getOtherPlayer(ipNo));
            if (ip1n > ip2n) {textMessg.text = "私の勝ちです。"; }
            else if (ip1n < ip2n) {textMessg.text = "私の負けです。"; }
            else {textMessg.text = "引き分け";}
        }
    }
}

自動で打つプレイヤー(自動で左上から探します) clsPlCon1.as

fncRun()関数以外は「clsPlMan」とほぼ同じです。

すべての升目を左上から探し最初の「打てる升目」を「打つ升目」にします。
動きがわかりやすくするために1秒後に「打つ升目」を返します。

盤をクリックイベントに登録する関数は不要なので「null」を指定。
package cls {
    import flash.display.Sprite;
               :
    public class clsPlCon1 extends clsPlayer {
               :
        //コンストラクター================================================
        public function clsPlCon1():void {
            if (stage) init();
            else addEventListener(Event.ADDED_TO_STAGE, init);
        }
                        :
        //打つ番が来たときにコールされる関数==============================
        // fRet:打つ升目が決まったとき呼ぶ関数 fncOnxy(iti:String):void
        // 戻り値:盤をクリックした時にコールされる関数
        //       (プレイヤーが人間のとき使用,不要の時null)
        //       fucClic(itiNam:String):void
        override public function fncRun(fRet:Function):Function {

            fncRet = fRet;
            textMessg.text = "すこし考えています。";
            okIti = "";
            //左上から順番に探して最初の打てる場所に打つ
            for (var i:int = 0; i < 8; i++) {
                for (var j:int = 0; j < 8; j++) {
                    var strNam:String = clsRevCom.getYokoNam(j)+
                                            clsRevCom.getTateNam(i);
                    if (fncChkIti(strNam,ipNo) >0) {
                        okIti = strNam;
                        break;
                    }
                }
                if (okIti != "") { break;}
            }
            var setIDName:Number = setTimeout(fncRunOK, 1000);  //1秒後に実行
            return null;        //盤がクリックしたときの関数(何もしない)
        }
        //fncRunで見つけた升目を返す
        private function fncRunOK():void {
            textMessg.text = "まってます。";
            fncRet(okIti);
        }
                   :

クラスを使う側


先攻(黒)、後攻(白)に「clsPlMan」または「clsPlCon1」を指定できるようにしたので
プレイヤー指定ボタンで各プレイヤーを「new」、「addChild」(表示)、
「setColor」(プレイヤーの初期化)し、配列arrPlにセットします。

先攻(黒ip=1)で「ゲーム開始」します。
打つプレイヤーの指定は「arrPl[ip-1].fncRun(fncOnxy)」で行ないます。

ゲーム終了時は各プレイヤーの「fncEnd()」を実行
//プレイヤー読み込み
private function onPl1(swfNam:String):void {
    while (pl1.numChildren) pl1.removeChildAt(0);
    if (swfNam == "clsPlMan") {
        objPl1 = new clsPlMan();
    }else {
        objPl1 = new clsPlCon1();
    }
    pl1.addChild(objPl1);
    arrPl[0] = objPl1;
    arrPl[0].setColor(clsRevCom.getFirstPlayer(), 
        objBoard.chkIti, objBoard.masuJyoutai,
        objBoard.getRireki,objBoard.Kekka);
    if(arrPl[1] != null) {btnStart.enabled =true;}
}
         :
//ゲーム開始
public function onStart():void {
    fncMess2Clear();
    fncMess2Set("盤の初期化");
    objBoard.initDataSet();
    ip = clsRevCom.getFirstPlayer();
    PlayerSel.enabled = false;
    objBoard.fncSetFnc(arrPl[ip-1].fncRun(fncOnxy));
}

//駒を打つ升目が決まったときにコールする関数
// iti:クリックした升目("a1"~"h8")
public function fncOnxy(itiNam:String):void {
    var n:int = objBoard.okuIti(itiNam, ip);
    if (n > 0) {    //升目がOKか,駒を置く
        fncMess2Set(clsRevCom.getPlColNam(ip) + ":" + itiNam + ":" +
                              (n-1) + "個変更");
        ip = clsRevCom.getOtherPlayer(ip);  //次に打つプレイヤー
    } else {
        objBoard.fncSetFnc(arrPl[ip - 1].fncRun(fncOnxy));
        return;
    }
    //次に打つプレイヤーが打てる場所があるか?
    if ( objBoard.chkPlayer(ip) >0) {
        objBoard.fncSetFnc(arrPl[ip-1].fncRun(fncOnxy));
        return;
    }
    //次の次のプレイヤーが打てる場所があるか?
    ip = clsRevCom.getOtherPlayer(ip);  //次に打つプレイヤー
    if ( objBoard.chkPlayer(ip) >0) {
        objBoard.fncSetFnc(arrPl[ip - 1].fncRun(fncOnxy));
        return;
    }
    //二人とも打てる場所なし->終了
    var ip1:int = clsRevCom.getFirstPlayer();
    var ip2:int = clsRevCom.getOtherPlayer(ip1);
    var ip1n:int = objBoard.Kekka(ip1);
    var ip2n:int = objBoard.Kekka(ip2);
    var strWin:String = "引き分けです。";
    if (ip1n > ip2n) { strWin = clsRevCom.getPlColNam(ip1) + "の勝ちです。"; }
    if (ip1n < ip2n) { strWin = clsRevCom.getPlColNam(ip2) + "の勝ちです。"; }
    arrPl[0].fncEnd();
    arrPl[1].fncEnd();
    
    Alert.show("終了しました。" +strWin+"\n"+ clsRevCom.getPlColNam(ip1) + ":" +
                    ip1n +
                    "/" + clsRevCom.getPlColNam(ip2) + ":" + ip2n,
                    "Reversi2",mx.controls.Alert.OK,this,fncNect);

    objBoard.fncSetFnc(null);
}

プログラミング工房