LoginSignup
5

More than 3 years have passed since last update.

【ポケモン剣盾】化石の復活を自動化したよって話

Last updated at Posted at 2020-01-30

0. はじめに

まずは大事な大事な宣伝から。
ここで自動化までの流れを説明しています。
私の方法で自動化したい場合は「ATmega32U4」が乗ってる?マイコンじゃないとダメです。
※まだ知識が足りていないので間違っている可能性あり
ケーブルを買うことを考えるとこれが安くてよさそう。

後、ここでワットの自動回収のソースを解説しています。
ぜひ見てください。

1. ソース

#include <SwitchControlLibrary.h>
int MAX = 0; // 最大受け取り数※0の場合無限ループ
int poke = 3;
// 1:パッチラゴン
// 2:パッチルドン
// 3:ウオノラゴン
// 4:ウオチルドン
int kaseki1;
// 1:トリ
// 2:サカナ
int kaseki2;
// 1:リュウ
// 2:クビナガ
int cnt = 0;

// 初期処理 マイコン接続後1番に動きます
void setup(){
  // LRボタン押下でコントローラーとして認識させる
  SwitchControlLibrary().PressButtonR();
  delay(50);
  SwitchControlLibrary().ReleaseButtonR();
  delay(500);
  SwitchControlLibrary().PressButtonL();
  delay(50);
  SwitchControlLibrary().ReleaseButtonL();
  delay(500);
  SwitchControlLibrary().PressButtonR();
  delay(50);
  SwitchControlLibrary().ReleaseButtonR();
  delay(500);
  SwitchControlLibrary().PressButtonR();
  delay(50);
  SwitchControlLibrary().ReleaseButtonR();
  delay(2000);
  switch(poke){ // 選ぶ化石決める
    case 1:
    kaseki1 = 1;
    kaseki2 = 1;
    break;
    case 2:
    kaseki1 = 1;
    kaseki2 = 2;
    break;
    case 3:
    kaseki1 = 2;
    kaseki2 = 1;
    break;
    case 4:
    kaseki1 = 2;
    kaseki2 = 2;
    break;
    default:
    kaseki1 = 1;
    kaseki2 = 1;
  }
}

// 繰り返し処理 マイコンの接続をやめるまで{}内を繰り返します
void loop() {
  // 開始
  if(cnt < MAX || 0 == MAX){
    cnt++;
    ButtonA();
    delay(1000);
    ButtonA();
    delay(1000);
    // 1回目の化石選択
    if(kaseki1 == 2){
      MoveHatDown();
      delay(500);
    }
    ButtonA();
    delay(1000);
    // 2回目の化石選択
    if(kaseki2 == 2){
      MoveHatDown();
      delay(500);
    }
    ButtonA();
    delay(1000);

    ButtonA();
    delay(1000);
    ButtonA();
    delay(4000);
    ButtonA();
    delay(1000);
    ButtonA();
    delay(1000);
    ButtonA();
    delay(1000);
    ButtonA();
    delay(5000);
    ButtonA();
    delay(3000);
    ButtonA();
    delay(2000);
  }else{
    SwitchSleep();
  }
}

//Aボタンを押下して離すまで
void ButtonA(){
  SwitchControlLibrary().PressButtonA();
  delay(50);
  SwitchControlLibrary().ReleaseButtonA();
}

//ホームボタンを押下して離すまで
void ButtonHome(){
  SwitchControlLibrary().PressButtonHome();
  delay(50);
  SwitchControlLibrary().ReleaseButtonHome();
}

//下を入力して離すまで
void MoveHatDown(){
  SwitchControlLibrary().MoveHat(4); // down
  delay(50);
  SwitchControlLibrary().MoveHat(8); // center
}

//Switchをスリープにする
void SwitchSleep(){
  SwitchControlLibrary().PressButtonHome();
  delay(4000);
  SwitchControlLibrary().ReleaseButtonHome();
  ButtonA();
}

2. 解説

解説するほど大したコードは書いていませんが、解説したいので解説します。
なお、前回解説した内容はほとんど省きます。

まず、使い方から。

#include <SwitchControlLibrary.h>
int MAX = 0; // 最大受け取り数※0の場合無限ループ
int poke = 3;
// 1:パッチラゴン
// 2:パッチルドン
// 3:ウオノラゴン
// 4:ウオチルドン
int kaseki1;
// 1:トリ
// 2:サカナ
int kaseki2;
// 1:リュウ
// 2:クビナガ

一番上にある、MAX変数で復活させる数を指定してください。
0を場合は、マイコンの接続を切るまで受け取り続けます。
そして、poke変数に復活させたいポケモンの番号を指定します。
コメントにあるように、ポケモンは以下の番号に対応しています。

番号 ポケモン
パッチラゴン
パッチルドン
ウオノラゴン
ウオチルドン

このMAXとpokeを指定した後、マイコンにプログラムを書き込んでマイコンをSwitchにつなげてください。

ポイント解説。

  switch(poke){ // 選ぶ化石決める
    case 1:
    kaseki1 = 1;
    kaseki2 = 1;
    break;
    case 2:
    kaseki1 = 1;
    kaseki2 = 2;
    break;
    case 3:
    kaseki1 = 2;
    kaseki2 = 1;
    break;
    case 4:
    kaseki1 = 2;
    kaseki2 = 2;
    break;
    default:
    kaseki1 = 1;
    kaseki2 = 1;
  }

初登場、switch文。
見て察しが付くように、単なる分岐です。
基本的にはifとelseで全く同じことができます。
じゃあ、どうして2種類あるのか?というと、「分かりやすい」や「書きやすい」これに尽きると思います。
※詳しくは知らないので、ご立派な理由が他にあるかもしれません。
今回の様に、一つの変数の値によって多分岐する場合、if elseで書くとわかりにくいんです。
試しにif文で書いてみましょう。

  if(poke == 1){
    kaseki1 = 1;
    kaseki2 = 1;
  }else if(poke == 2){
      kaseki1 = 1;
      kaseki2 = 2;
    }else if(poke == 3){
      kaseki1 = 2;
      kaseki2 = 1;
    }else if(poke == 4){
      kaseki1 = 2;
      kaseki2 = 2;
    }
  }

分かりにくさはいまいち伝わっていない気がしますが、書きにくさは伝わりませんかね?
実際にソースを打ち込んだ自分はかなり書きづらかったです。

それで、どんなことをやっているかというと・・・って思いましたが、if文で書いたのでもう内容は理解できましたかね?
poke変数で指定しているポケモンをswicth文で判定し、kaseki1、kaseki2の変数に適切な値を入れていっています。

  // 開始
  if(cnt < MAX || 0 == MAX){

ここのif文でMAXの回数分、もしくは無限ループを行う判定を行っています。
※cntはループした回数です。

    // 1回目の化石選択
    if(kaseki1 == 2){
      MoveHatDown();
      delay(500);
    }
    ButtonA();
    delay(1000);
    // 2回目の化石選択
    if(kaseki2 == 2){
      MoveHatDown();
      delay(500);
    }
    ButtonA();
    delay(1000);

で、ここで化石の選択を行っています。
1つ目の選択肢はすでに選ばれている状態で表示されるので、2つ目の選択肢を選ばなければならない、「サカナ」と「クビナガ」の化石の場合のみ↓の入力を行うようになっています。

  }else{
    SwitchSleep();
  }
//Switchをスリープにする
void SwitchSleep(){
  SwitchControlLibrary().PressButtonHome();
  delay(4000);
  SwitchControlLibrary().ReleaseButtonHome();
  ButtonA();
}

最後。
SwitchSleep()関数です。
SleepSwitchのほうが正しい命名なような気もしますが、趣味でプログラミングをかじった程度の実力+英語力皆無なので命名センスは無いです。
ただ、誰にでもやりたいことははっきりと伝わると思います。
Switchをスリープにするんです。※ポケモンのスリープじゃないですよ。
ホームボタンを長押しして、Aボタンを押すという簡単な処理ですね。
で、いつスリープさせるのかというと、MAXにしていした数だけループしたときです。
そうすることで、マイコンを刺したままでも処理を終わらせることができます。

3. さいごに

マジカル交換の自動化とかも完成しています。
次やりたい自動化は、羽集めです。
ここまで来たら対戦以外はやらなくて済むくらいに自動化しておきたいですね。

コメントとか欲しいです。ボッチなのでポケモンフレンドや自動化仲間が欲しいです。

では、よきプログラミングライフを!!

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5