6.オクトラのリセマラを自動化する(2/2)
このページの目的
- サイラスを求めてオクトラのリセマラを自動化する記事の後半です。
- →前半の記事はこちら
- モンスターとの戦闘画面以降の処理を自動化します。
自動化する手順
- 手順①:戦闘シーン
- 手順②:戦闘後〜旅団入力前まで
- 手順③:旅団名入力〜チュートリアル終了
- 手順④:手紙等を回収〜ガチャを選択
コードの画像
コードの内容
#手順① click(Pattern("1616237575845.png").targetOffset(259,-53)) wait("1616237622001.png",30) click(Pattern("1616237575845.png").targetOffset(311,-223)) click(Pattern("1616237672556.png").similar(0.81)) wait("1616240877531.png",30) click(Pattern("1616237575845.png").targetOffset(311,-223)) click(Pattern("1616237575845.png").targetOffset(311,-223)) click(Pattern("1616237672556.png").similar(0.83)) sleep(2) click(Pattern("1616237575845.png").targetOffset(281,-344)) dragDrop(Pattern("1616236244111.png").targetOffset(77,-314),Pattern("1616236244111.png").targetOffset(233,-318)) click(Pattern("1616237575845.png").targetOffset(267,-61)) wait("1616237900862.png",10) click(Pattern("1616237575845.png").targetOffset(311,-223)) click(Pattern("1616237575845.png").targetOffset(311,-223)) click(Pattern("1616237672556.png").similar(0.83)) click(Pattern("1616237575845.png").targetOffset(267,-61)) try: for i3 in range(20): wait("1616237958258.png",30) click(Pattern("1616237575845.png").targetOffset(267,-61)) except: click(Pattern("1616236244111.png").targetOffset(-3,-123)) #手順② for i6 in range(50): for i5 in range(10): click(Pattern("1616236244111.png").targetOffset(-3,-123)) click(Pattern("1616236244111.png").targetOffset(315,-403)) click(Pattern("1616236244111.png").targetOffset(78,-152)) if exists("1616238609597.png"): break sleep(1) #手順③ click("1616238609597.png") click("1616238634432.png") click("1616238651178.png") click("1616238665487.png") click("1616238676885.png") for i6 in range(50): for i5 in range(10): click(Pattern("1616236244111.png").targetOffset(-3,-123)) click(Pattern("1616236244111.png").targetOffset(315,-403)) click(Pattern("1616236244111.png").targetOffset(78,-152)) if exists("1616250673676.png"): break sleep(1) #手順④ click("1616250692289.png") click("1616250704896.png") sleep(2) click(Pattern("1616250751619.png").targetOffset(201,-6)) try: for i7 in range(10): click("1616250777171.png") except: click(Pattern("1616250795130.png").similar(0.84)) click("1616250816390.png") click("1616250830547.png") click("1616250999541.png") click("1616250860668.png") click(Pattern("1616250795130.png").similar(0.84)) sleep(2) click("1616250888746.png") try: for i7 in range(10): click("1616250777171.png") except: click(Pattern("1616250795130.png").similar(0.84)) click("1616250943191.png") sleep(3) click("1616250954534.png") sleep(2) click("1616250972284.png") click("1616250999541.png") click(Pattern("1616250795130.png").similar(0.84)) sleep(2) click("1616250888746.png") click("1616251047230.png") click("1616251062495.png") click("1616252286759.png") click("1616250999541.png") sleep(2) click(Pattern("1616250795130.png").similar(0.84)) sleep(2) click("1616250888746.png") click("1616289001842.png") wait("1616289021182.png",10) click("1616289032414.png")
コードのポイント解説
- 手順①:戦闘シーン。鬱陶しい解説画面を閉じつつ、攻撃を続ける。ブーストはdragDropで動作しました。攻撃の繰り返し処理はfor文で実行
- 手順②:戦闘後はひたすら3点タップを繰り返し(前半記事参照)。シナリオ選ぶ場面がありますが、私のタップ位置だと権力が選ばれます(嫌ならタップ位置を工夫するなどの考慮要)。「はい」「いいえ」の選択箇所があるので、「はい」が表示される場所をタップ箇所に含めておくことが必要。
- 手順③:旅団名を決める必要があるので、キーボードから「あ」を選択してしているだけ。特に複雑な点はないです。その後は3点タップを繰り返し。
- 手順④:手紙からもらえるルビーが298で10連ガチャに微妙に足りないので、オススメ装備で功績から5ルビーをもらいつつ、サイラスガチャを選択する。特に工夫の点はなく、一個ずつボタンを押していくだけです。この辺から作りが適当になりますがどうせ1日しか使わないので、動けばいいかと……
動作する様子
最後に
無事サイラスをゲットしました。15回目ぐらいだったかな……。最後はなぜか☆4☆5のサイラス二枚抜きでした。
5.オクトラのリセマラを自動化する(1/2)
このページの目的
- オクトバストラベラーのスマホゲーにサイラスが登場。前作でダントツの強さを見せた魔法使いさながら、まさかの三属性を使いこなす強キャラでの実装と聞くと、引かざるをえず、リセマラしてオクトラをやり直すことを決意。梅原裕一郎ボイスと一緒ならこのゲームやり直せるよ……
- リセマラは課金を避けて意図したキャラを入手可能なほとんど唯一の手段でありながら、人々の膨大な時間を奪ってく悪しき文化。本記事ではリセマラの自動化の実例を示して、日本人の生産性を高めたい。オクトラに限らず、他のゲームでも同様の手段をとることはできるはず。
- しかし、現時点で移動だけは自動化できておらず、完全自動化には至っていません。移動だけは手動でやるとして、今回は移動する前までの内容を記載。
- また、スマホゲームを外部ツールで操作するのは通常規約で禁止されています。あくまでも自己責任でということを理解しつつご参照ください(本サイトの別記事参照)
必要な環境
- オクトラはPCのスペックが高いとBlueStacksで動くという書き込みを見つけられるのですが、私の環境では動かないので、「Android端末をパソコンからリモートコントロール」+「パソコン上の操作をSikulixで自動化」することでリセマラ操作を自動化します。事前準備は以下。
- 環境構築の詳細については以下のページ参照
自動化する手順
今回は前半部分
- 手順①:ストレージへのアクセスを許可。ダウンロード終わるまで待って利用規約等に合意
- 手順②:ひたすら三点タップを繰り返す
- 手順③:歩く
コードの画像
コードの内容
#手順① click("1616290393849.png") click("1616290425223.png") wait("1616235972492.png",300) doubleClick(Pattern("1616235972492.png").targetOffset(207,-48)) click("1616236064871.png") click("1616236085877.png") click("1616236099285.png") sleep(2) click("1616236085877.png") click("1616236119292.png") wait("1616236141344.png",30) click("1616236141344.png") wait("1616236185327.png",60) click("1616236185327.png") #手順② for i in range(50): for i5 in range(10): click(Pattern("1616236244111.png").targetOffset(-3,-123)) click(Pattern("1616236244111.png").targetOffset(315,-403)) click(Pattern("1616236244111.png").targetOffset(78,-152)) if exists("1616236543907.png"): break sleep(1) #手順③ for i2 in range(10): dragDrop(Pattern("1616236244111.png").targetOffset(-104,-120),Pattern("1616236244111.png").targetOffset(319,-109))
コードのポイント解説
- 手順①:表示されるボタンをタップしていくのみ。表示まで時間がかかるものはwait()を使って表示されるまで待つか、sleep()で待機秒数を指定。
- 手順②:ゲーム開始後は画面のどこかをひたすらタップすると進む。ここではfor文を使って画面上の3点を繰り返しタップする動作を指定。画面上固定で表示されるVysorのフッタからの相対位置で画面の場所を指定。3点のうち2点は画面上たまに表示されるメニューの閉じるボタン位置と、OKボタン位置を指定することで可用性を高めています。繰り返し最中にif exists()で繰り返し処理を停止するトリガとなる画面(ここでは歩く処理が要求される場面)が表示されていないかを確認し、繰り返し処理続行を判断
- 手順③:歩く処理をdragDropで指定。走るのも同じdragDropで出来そうですが、なぜか出来ない。誰かできた人は教えていただきたいです……(マップが表示されれば、マップ上で移動先を指定できるのですが……)
動作する様子
4.クエスト周回を自動化する
このページの目的
- ひたすら同一クエストを周回するというソシャゲでよくある作業を自動化します。
前提
今回自動化する作業
プリコネの同一のイベントクエストで周回する作業で、実施手順は以下の通り。
- 手順①:クエスト画面で挑戦するをクリック
- 手順②:もしスタミナがないときには回復
- 手順③:「バトル開始」ボタンをクリック
- 手順④:戦闘が終わるまで待機し、戦闘終了後の画面で「次へ」ボタンをクリック
- 手順⑤:アイテム一覧画面で「次へ」をクリック
- 手順⑥:限定ショップ出現が表示されたときには「キャンセル」ボタンをクリック
- 手順⑦:「再戦する」ボタンをクリック
- 手順⑧:「OKボタン」をクリック
- 以降、戦闘が再開するため④〜⑧をループ
具体的なコード
コードの内容
#手順① doubleClick("挑戦するボタン") #手順② if exists("スタミナが不足しています。回復しますか?"): click("OKボタン") click("OKボタン") click("OKボタン") #手順③ click("バトル開始ボタン") sleep(5) #手順④ for i in range(3): wait("次へボタン",240) #手順⑤ click("次へボタン") #手順⑥ if exists("限定ショップ出現"): click("キャンセル") sleep(2) #手順⑦ click("再戦する") sleep(2) #手順⑧ click("OKボタン") sleep(10)
コードのポイント解説
- 手順② 手順⑥
- if exists(画像)は、指定の画像が表示された場合のみ以下の動作を実行するというコマンド。
- スマホゲームで、毎回同じ表示になるのではなくて、○○が出た場合には○○するという場合に使う。
- 上記の条件下で実行するコマンドについては、行頭にタブもしくはスペース4字を入れて記載する
- 手順④〜⑧を繰り返す
- for i in range(数字): は、指定された回数、以下の動作を繰り返すというコマンド
- 上記の条件下で実行するコマンドについては、行頭にタブもしくはスペース4字を入れて記載する
動作する様子
3.デイリーミッションを自動化する
このページの目的
- ゲーム内で毎日やるような定形作業について、Sikulixを使ってどのように自動化をするのか、初歩的な例で説明します。
- 日毎に繰り返す作業は、手順の少ないものでも自動化しておくとメリットが大きいです。ここでは1つの作業だけを例に記載していますが、日毎に操作が必要な複数の作業をまとめて一つのプログラムにしておくことで、面倒な日常の作業をワンクリックで終わらせることができるようになります。
- 一時期ハマってたプリンセスコネクトを例に記載
前提
今回自動化する作業
プリコネのデイリーガチャを引く一連の作業で、実施手順は以下の通り。
- 手順①:マイページ画面から「ガチャボタン」をクリック
- 手順②:ガチャ画面に遷移後、「ノーマル」タブをクリック
- 手順③:「10回引く」ボタンをクリック
- 手順④:「OKボタン」を押す
- 手順⑤:ガチャの結果が表示された後の「OKボタン」を押す
- 手順⑥:「マイページ」に戻る
具体的なコード
コードの内容
code:gacha doubleClick("ガチャアイコン") #手順① wait("ノーマル",20) click("ノーマル") #手順② click("10回引く") #手順③ click("青いOKボタン") #手順④ wait("白いOKボタン",10) click("白いOKボタン") #手順⑤ sleep(2) click("マイページアイコン") #手順⑥
コードのポイント解説
- 手順①
- 手順②
- 手順①の後、ガチャの画面遷移までに時間がかかるため、「ノーマルタブ」が表示されるまで、待機する設定を記載
- サーバとの通信に時間がかかる処理については、いちいち"wait"を入れたほうがいい
- sleepでもいいが、必ず一定時間待つのは時間の無駄であり、また、サーバとの通信は環境に依存して予想以上に時間がかかることがあるため以前大丈夫だった待機時間でもタイムアウトするという場合が発生するためwaitがいい
- 手順③・手順④
- 単なるクリック。ここは画面遷移にタイムラグがないのでwait不要
- 手順⑤
- ガチャのアニメーションの時間を待機し、白いOKボタンが押されるまで待った上でクリック
- 手順⑥
- 手順⑤の後、若干の画面読み込みがあり、マイページアイコンを即クリックすると失敗することがあるため、"sleep"で2秒の休止時間を入れる
- 上記のような実際にクリックできるようになるまでのタイムラグはスマホゲーでしばしば存在するため、実際に何度か操作させてみて、適宜sleepやwaitを入れるような調整が必要
動作する様子
2.ゲームの起動を自動化する
このページの目的
sikulixによるゲーム自動化の手始めとして、ゲームを起動するプログラムを作ります。
- sikulixで操作するために毎回エミュレータからゲームを起動する……、という動作は結構面倒なので、自動化するメリットは大きいです。
- 一時期ハマってたプリンセスコネクトを例に作成。Macを例に作成していますがWIndowsも同様です。
前提
今回自動化する作業
MacからBlueStacksを起動しアプリを立ち上げる。手順は以下の通り。
- 手順①:デスクトップで虫眼鏡マークをクリックしてSpotlightを立ち上げる
- 手順②:Bluestacksを検索、起動
- 手順③:Bluestacksが起動するのを待ってゲームアイコンをクリック
- 手順④:ゲームが起動するのを待って、クリックボタンをクリック
- 手順⑤:データダウンロード画面が表示されれば、OKボタンをクリック
- 手順⑥:お知らせ画面が表示されれば、閉じるをクリック
コードの画像
コードの内容
#手順① click("虫めがねボタン") #虫めがねボタンクリック #手順② type("bluesta") type(Key.ENTER) #手順③ wait("ゲームのアイコン",60) sleep(2) doubleClick("ゲームのアイコン") #手順④ wait("データ連携ボタン",100) click(Pattern("CRIWAREのアイコン").targetOffset(525,-7)) #手順⑤ wait(10) if exists("データダウンロード表示"): click("OKボタン") #手順⑥ sleep(30) if exists("閉じるボタン"): click("閉じるボタン") #手順⑥
コードの作成方法と解説
- 手順①
- click()は指定した画像をデスクトップ上で検索してクリックします。
- 画像のスクショはsikulixの「スクリーンショットを撮る」ボタンから可能
- Spotlightを呼び出したいだけなので、contral+spaceを押す形でもいい。その場合は、type(Key.SPACE, Key.CTRL)
- 画像だとデスクトップの環境に依存するためキーボード操作のほうがスマートかも
- sleep()は数字で指定した秒数待機する。 これを入れないと手順②の入力に失敗することがあったので挿入
- 手順②
- type("")は指定したキーをタイプします
- type(Key.ENTER)はエンターキーを押します
- 手順③・手順④
- wait(画像,秒数)は指定した画像が表示されるまで指定した秒数待機します。
- ここではAndroidのホーム画面で指定したゲームのアイコンが表示されるのを60秒待っています。
- 2秒のsleepを挿入しているのは、アイコンが表示されて直ちにクリックするとうまく起動できなくなる場合があったため
- ゲームアイコンのdoubleClickはclickでも問題ないはずですが、たまにclickで失敗することがあるのでdoubleClickに置き換えています。
- 手順⑤
- if exists():は指定した画像が表示された場合のみ特定のコードを実行します。
- 指定するコードはタブで字下げ(スペースで4文字分字下げ)して記載しています。
- ここではアプリのデータダウンロードがあった場合のみ、OKボタンをクリックしています。
- 手順⑥
- 手順⑤と同じく、if exists():を使ってログイン後にポップアップで画面が表示された場合のみ、OKボタンで閉じるというのを実現しています
動作する様子
1.事前準備(環境構築)
このページの目的
- Sikulixによるスマホゲーム自動化を実現するための環境整備方法を記載します。
- Sikuliによるゲーム自動化には以下の2つのやり方があり、それぞれメリット・デメリットがあります。
- このサイトの本論ではないので、主として私が参照したページの紹介にとどめます
①Sikulix(バージョン2以降)のインストール
- Windowsの場合
- Windows向けについては複数の解説サイトがあるので、サイトを参考にすると割と簡単にいけるはず。
- Sikulixのバージョン1と2以降で手順が異なるので、必ずバージョン2以降に対応したサイトを参照ください
【2020年最新版】Sikulixインストール・セットアップ方法!入門者向けに図説
- Macの場合
- Mac向けは解説サイトが少なく、ハマるポイントが多かった。
- 基本の手順は以下のサイト参照
SikuliX 2.0.4のインストール方法と基本的な使い方 - 上記内容だけでは、私のMacの場合(OSはCatalinaでバージョンは10.15.7)、sikulixideは立ち上がるが動かなかった。セキュリティとプライバシー設定で、javaからの実行について、以下の項目の許可して現在は動いている状況。
- フルディスクアクセス
- ファイルとフォルダ
- 画面収録
- しかし、上記の設定が方法が曲者で、設定項目に対して自分でアプリを自由に追加・設定できなかったりする……
- またBig Surにしたときに、果たして動くのかわからない。日本語のサイトの解説も見つからず、このあたりは非常に不安。
②NoxおよびBluestacksのインストール
- WindowsでもMacでも普通にインストールすればまず使えると思います。解説は割愛
- NoxおよびBluestacksへのゲームのインストールについて説明は割愛
- このやり方の一番のネックは、やりたいゲームがNoxやBluestasksで動くかどうか
③Android端末およびPCへのVysorのインストール
0.サイトの概要とコンテンツ一覧
このサイトの目的
- スマホゲームにおいて機械的になりがちなルーティン作業をフリーのRPAツールSikuliXで自動化・効率化し、日常の生産性を高めつつ、ゲームの美味しいところだけ楽しむことを目指します
- Pythonのプログラミングの学び・実践の場として、新たな側面からスマホゲームを楽しみます
使用するツール
リスク
以下を認識した上で自己責任で利用するようにしてください (とても重要。大手を振ってやることではありません)
- 外部ツールを使ったゲームの操作はスマホゲームにおいては基本的に規約違反となっています。SikuliXも外部ツールとみなされる可能性があり、運営にアカウントを停止されるリスクがあります
- 規約違反とされる行為で効率的な攻略を行う行為が、他のプレイヤーから反感を持たれる可能性もあります(自分は地道な作業をこんなにがんばっているのにずるい!)
- プログラムの内容によっては、サーバに大きな負荷を与え、サービス運営のコストを増加させる可能性があります。愛するゲームの運営者の迷惑とならないよう良識の範囲内で利用ください
SikuliXの長所
- 無料で利用可能です。
- プログラミング言語+画像認識によって、状況に応じて柔軟な対処ができるプログラムを作ることができます。同じタップ作業を何回繰り返す、というだけではなく、○が表示さればA、△が表示されればBというように、状況に応じた操作を実現可能です
- Bluestacks等のAndroidエミュレータで動くゲームを自動化できるだけではなく、Androidエミュレータで動かないゲームについては、Android端末をPCからリモート操作するツールと組み合わせることで、Androidで動くゲームであればどんなゲームでも自動化することができます
- OSの機能と組み合わせて毎日決まった時間にプログラムを起動して、特定の時間にしかできない作業を自動化することができます
SikuliXの短所
- 基本的にキャプチャした画像との一致により操作を行うするため、自分のPC環境の変更(アプリのウィンドウサイズや画面の解像度等)、ゲーム側の環境変更(アイコン等のデザイン変更など)があると動作しなくなります