Ganponブログ

趣味の模型作り、ドライブ、旅行など
since Mar.2017

RC可動 1/35 メルカバMk.1 プログラム

2022-09-29 10:43:50 | 1/35 メルカバmk1

 
  1. /*PS3_ESP32_tank_JQ6500mp3_DRV8835_merkava_v7.0
  2.   2022-09-29
  3.   【操作方法】
  4.   PS3コントローラで操縦します。
  5.   車体の電源をONし、コントローラのPSボタンでペアリング開始。
  6.   インジケータランプ4個高速点滅後に1個点灯でペアリング完了。

  7.   コントローラーの左スティック上下で前後進、右スティックの左右でステアリングを制御。
  8.   ステアリングを切っていくと緩旋回、一杯切るとで信地旋回する。
  9.   また、左スティック中央でステアリング左右一杯で超信地旋回。

  10.   △ボタンで砲身UP、?ボタンで砲身DOWN、□ボタンでセンター位置になる。
  11.   左スティック左右で砲塔旋回。離した位置で止まる。

  12.   R1ボタンで主砲発射。L1ボタンで機銃射撃。
  13.   RIGHTボタンでヘッドライト点灯、LEFTボタンで消灯。
  14.   R2ボタンで右超信地旋回 + 砲塔左旋回 = 疑似砲塔追尾デモ
  15.   L2ボタンで左超信地旋回 + 砲塔右旋回 = 疑似砲塔追尾デモ
  16.   //SQUAREボタンで疑似砲塔追尾でも終了

  17.   砲撃時のリコイルアクション車体+砲身

  18.   メインCPU:  ESP32 DevKitC
  19.   ボード : ESP32 Dev Module
  20.   モータドライバ:DRV8835
  21.   MP3プレイヤー:JQ6500 MP3プレイヤーモジュール
  22. */

  23. #include <Arduino.h>
  24. #include <JQ6500_Serial.h>
  25. HardwareSerial Serial_df(2); //16pin=RX, 17pin=TX
  26. JQ6500_Serial mp3(Serial_df);
  27. void printDetail(uint8_t type, int value);
  28. #include <Ps3Controller.h>

  29. #include <ESP32Servo.h>
  30. Servo servo1;
  31. int servo1Pin = 27;
  32. Servo servo2;
  33. int servo2Pin = 14;
  34. Servo servo3;
  35. int servo3Pin = 12;

  36. int LED_1 = 23; //ブレーキランプ
  37. int LED_2 = 22; //ヘッドライト
  38. int LED_3 = 19; //砲撃
  39. int LED_4 = 18; //銃撃

  40. int k = 0;
  41. int s = 0;
  42. int d_time = 30;

  43. int angle_servo1 = 90; // 上下
  44. int anglenow = angle_servo1 ;
  45. int angle_servo3 = 90; // リコイル
  46. int motor_speed;
  47. float steering;
  48. int pos_y;
  49. int pos_x;
  50. int pos_lx;

  51. int AIN1 = 32;
  52. int BIN1 = 25;
  53. int PWMApin = 33;
  54. int PWMBpin = 26;
  55. int PWMA = 2;
  56. int PWMB = 3;
  57. int cnt = 0;

  58. void setup() {
  59.   servo1.setPeriodHertz(50);
  60.   servo1.attach(servo1Pin, 500, 2400);
  61.   servo2.setPeriodHertz(50);
  62.   servo2.attach(servo2Pin, 900, 2100);
  63.   servo3.setPeriodHertz(50);
  64.   servo3.attach(servo3Pin, 500, 2400);

  65.   Serial.begin(115200);
  66.   //mySoftwareSerial.begin(9600);
  67.   Serial_df.begin(9600); // RX2 = 16, TX2 = 17
  68.   mp3.reset();
  69.   mp3.setVolume(25);

  70. Ps3.begin("00:11:22:33:44:55"); //SixaxisPairToolで調べたmac adresに修正
  71.   Serial.println("PS3 Ready");

  72.   ledcSetup(PWMA, 12000, 8);
  73.   ledcAttachPin(PWMApin, PWMA);
  74.   ledcSetup(PWMB, 12000, 8);
  75.   ledcAttachPin(PWMBpin, PWMB);
  76.   pinMode(AIN1, OUTPUT);
  77.   pinMode(BIN1, OUTPUT);
  78.   pinMode(LED_1, OUTPUT);
  79.   pinMode(LED_2, OUTPUT);
  80.   pinMode(LED_3, OUTPUT);
  81.   pinMode(LED_4, OUTPUT);

  82.   LEDtenmetsu(LED_2);

  83.   servo1.write(angle_servo1); // CENTER
  84.   delay(50);
  85.   servo2.write(90); // STOP
  86.   delay(50);
  87.   servo3.write(angle_servo3); // 仰角0°
  88.   delay(50);

  89.   //myDFPlayer.play(3); //エンジン始動
  90.   mp3.playFileByIndexNumber(3);
  91.   delay(500);

  92. }

  93. void loop() {

  94.   if (Ps3.isConnected()) {
  95.     pos_lx = Ps3.data.analog.stick.lx;
  96.     pos_lx = pos_lx + 128;

  97.     //砲塔旋回
  98.     if ( pos_lx > 230) { //右旋回
  99.       mp3.playFileByIndexNumber(31);
  100.       servo2.write(76);
  101.       //delay(50);
  102.     } else if (pos_lx < 25) { //左旋回
  103.       mp3.playFileByIndexNumber(31);
  104.       servo2.write(104);
  105.       //delay(50);
  106.     } else { //停止
  107.       servo2.write(90);
  108.     }

  109.     //砲身上下
  110.     if ( Ps3.event.button_down.square) { // center
  111.       if (anglenow > angle_servo1) {
  112.         for (anglenow = anglenow; anglenow >= angle_servo1; anglenow -= 1) {
  113.           servo1.write(anglenow);
  114.           delay(40);
  115.         }
  116.         //delay(100);
  117.       }
  118.       else {
  119.         for (anglenow = anglenow; anglenow <= angle_servo1; anglenow += 1) {
  120.           servo1.write(anglenow);
  121.           delay(40);
  122.         }
  123.         //delay(100);
  124.       }
  125.     }

  126.     if ( Ps3.event.button_down.cross) { // down
  127.       for (anglenow = anglenow; anglenow <= (angle_servo1 + 15); anglenow += 1 ) {
  128.         servo1.write(anglenow);
  129.         delay(40);
  130.       }
  131.       //delay(100);
  132.     }

  133.     if ( Ps3.event.button_down.triangle) { // up
  134.       for (anglenow = anglenow; anglenow >= (angle_servo1 - 40); anglenow -= 1 ) {
  135.         servo1.write(anglenow);
  136.         delay(40);
  137.       }
  138.       //delay(100);
  139.     }

  140.     if (Ps3.event.button_down.circle) {
  141.       if (s == 0) {
  142.         s = 1;
  143.         //myDFPlayer.play(3); //エンジン始動
  144.         mp3.playFileByIndexNumber(3);
  145.         delay(1000);
  146.         //myDFPlayer.loop(5); //Loop 5th mp3 アイドリング
  147.         mp3.playFileByIndexNumber(5);
  148.         mp3.setLoopMode(MP3_LOOP_ONE);
  149.         delay(d_time);
  150.       } else {
  151.         //myDFPlayer.disableLoop(); //アイドリング停止
  152.         mp3.pause();
  153.         mp3.setLoopMode(MP3_LOOP_ONE_STOP);
  154.         s = 0;
  155.         delay(100);
  156.       }
  157.     }

  158.     if (Ps3.event.button_down.r3) {
  159.       //myDFPlayer.disableLoop(); //アイドリング停止
  160.       mp3.pause();
  161.       mp3.setLoopMode(MP3_LOOP_ONE_STOP);
  162.       s = 0;
  163.     }

  164.     if (Ps3.event.button_down.right) {
  165.       digitalWrite(LED_2, HIGH); // ヘッドライト ON
  166.     }

  167.     if (Ps3.event.button_down.left) {
  168.       digitalWrite(LED_2, LOW); // ヘッドライト off
  169.     }

  170.     if (Ps3.data.button.r2) { //右超信地旋回疑似砲塔追尾デモ
  171.       servo2.write(104); //砲塔左旋回
  172.       motor_speed = 165;
  173.       motor_run(motor_speed, 0, motor_speed, 1, 0);
  174.       delay(500);
  175.     }

  176.     if (Ps3.data.button.l2) { //左超信地旋回疑似砲塔追尾デモ
  177.       servo2.write(76); //砲塔右旋回
  178.       motor_speed = 165;
  179.       motor_run(motor_speed, 1, motor_speed, 0, 0);
  180.       delay(500);
  181.     }

  182.     if (Ps3.event.button_down.r1) { //砲撃 + リコイル(砲身&車体)
  183.       digitalWrite(LED_3, HIGH); //主砲発光
  184.       //mp3.playFileByIndexNumber(14);
  185.       mp3.playFileByIndexNumber(2);
  186.       delay(50);
  187.       digitalWrite(LED_3, LOW);
  188.       servo3.write(angle_servo3 + 40); // 砲身リコイル
  189.       delay(20);
  190.       motor_run(180, 1, 180, 1, 1); // 車体リコイル
  191.       //digitalWrite(LED_3, LOW);
  192.       delay(60);
  193.       motor_run(0, 0, 0, 0, 1);
  194.       // digitalWrite(LED_3, LOW);
  195.       for (int ang3 = (angle_servo3 + 50); ang3 >= angle_servo3; ang3 -= 1 ) {
  196.         servo3.write(ang3);
  197.         delay(15);
  198.       }
  199.       //digitalWrite(LED_3, LOW);
  200.       motor_run(100, 0, 100, 0, 1);
  201.       delay(80);
  202.       motor_run(0, 0, 0, 0, 1);
  203.       delay(100);
  204.       if (s == 1) {
  205.         //myDFPlayer.loop(5); //Loop 5th mp3 アイドリング
  206.         mp3.playFileByIndexNumber(5);
  207.         mp3.setLoopMode(MP3_LOOP_ONE);
  208.         delay(d_time);
  209.       }
  210.     }

  211.     if (Ps3.event.button_down.l1) { //銃撃
  212.       //myDFPlayer.play(24);
  213.       mp3.playFileByIndexNumber(24);
  214.       //delay(20);
  215.       for ( k = 0; k < 6; k++) {
  216.         digitalWrite(LED_4, HIGH); //発光
  217.         delay(80);
  218.         digitalWrite(LED_4, LOW);
  219.         delay(120);
  220.       }
  221.       if (s == 1) {
  222.         //myDFPlayer.loop(5); //Loop 5th mp3 アイドリング
  223.         mp3.playFileByIndexNumber(5);
  224.         mp3.setLoopMode(MP3_LOOP_ONE);
  225.         delay(d_time);
  226.       }
  227.     }

  228.     //走行コントロール
  229.     pos_y = Ps3.data.analog.stick.ly;
  230.     pos_x = Ps3.data.analog.stick.rx;
  231.     pos_y = pos_y + 128;
  232.     pos_x = pos_x + 128;

  233.     /* //左スティックがセンター付近は停止(ブレーキ)
  234.         if (pos_x > 102 && pos_x < 152 && pos_y > 102 && pos_y < 152) {
  235.           motor_run(0, 0, 0, 0, 1);
  236.         }
  237.     */

  238.     //前進
  239.     if (pos_y <= 102 && pos_x >= 102 && pos_x <= 152) {
  240.       motor_speed = map(pos_y, 102, 0, 0, 255);
  241.       motor_run(motor_speed, 0, motor_speed, 0, 0);
  242.     }

  243.     //後進
  244.     else if ( pos_y >= 152 && pos_x >= 102 && pos_x <= 152) {
  245.       motor_speed = map(pos_y, 152, 255, 0, 255) ;
  246.       motor_run(motor_speed, 1, motor_speed, 1, 0);
  247.     }

  248.     //前進右緩旋回、信地旋回
  249.     //else if ( pos_y <= 102 && pos_x > 152 && pos_x <= 245) {
  250.     else if ( pos_y <= 102 && pos_x >= 152) {
  251.       motor_speed = map(pos_y, 102, 0, 0, 255);
  252.       steering = motor_speed * (1.00 - (map(pos_x, 152, 255, 0, 255) / 255.00));
  253.       motor_run(motor_speed, 0, steering, 0, 0);
  254.     }

  255.     //前進左緩旋回、信地旋回
  256.     //else if ( pos_y <= 102 && pos_x < 102 && pos_x >= 10) {
  257.     else if ( pos_y <= 102 && pos_x <= 102) {
  258.       motor_speed = map(pos_y, 102, 0, 0, 255);
  259.       steering = motor_speed * (1.00 - (map(pos_x, 102, 0, 0, 255) / 255.00));
  260.       motor_run(steering, 0, motor_speed, 0, 0);
  261.     }

  262.     //後進右緩旋回、信地旋回
  263.     //else if ( pos_y >= 152 && pos_x > 152 && pos_x <= 245) {
  264.     else if ( pos_y >= 152 && pos_x >= 152 ) {
  265.       motor_speed = map(pos_y, 152, 255, 0, 255);
  266.       steering = motor_speed * (1.00 - (map(pos_x, 152, 255, 0, 255) / 255.00));
  267.       motor_run(motor_speed, 1, steering, 1, 0);
  268.     }

  269.     //後進左緩旋回、信地旋回
  270.     //else if ( pos_y >= 152 && pos_x < 102 && pos_x >= 10) {
  271.     else if ( pos_y >= 152 && pos_x <= 102 ) {
  272.       motor_speed = map(pos_y, 152, 255, 0, 255);
  273.       steering = motor_speed * (1.00 - (map(pos_x, 102, 0, 0, 255) / 255.00));
  274.       motor_run(steering, 1, motor_speed, 1, 0);
  275.     }

  276.     //右超信地旋回
  277.     else if (pos_x >= 245 && pos_y >= 102 && pos_y <= 152) {
  278.       motor_speed = 165;
  279.       motor_run(motor_speed, 0, motor_speed, 1, 0);
  280.     }

  281.     //左超信地旋回
  282.     else if (pos_x <= 10 && pos_y >= 102 && pos_y <= 152) {
  283.       motor_speed = 165;
  284.       motor_run(motor_speed, 1, motor_speed, 0, 0);
  285.     }

  286.     else { //停止(ブレーキ)
  287.       motor_run(0, 0, 0, 0, 1);
  288.     }
  289.   }
  290. }


  291. void motor_run(int D0, int D1, int D2, int D3, int D4) {
  292.   //D0 : モータスピード(左)
  293.   //D1 : モータA(左)1 = HIGH / 0 = LOW
  294.   //D2 : モータスピード(右)
  295.   //D3 : モータB(右)1 = HIGH / 0 = LOW
  296.   //D4 : LED_3 ON/OFF 1 = HIGH / 0 = LOW

  297.   //analogWrite(PWMA, D0);
  298.   ledcWrite(PWMA, D0); //(チャンネル,解像度)
  299.   digitalWrite(AIN1, D1);
  300.   //analogWrite(PWMB, D2);
  301.   ledcWrite(PWMB, D2); //(チャンネル,解像度)
  302.   digitalWrite(BIN1, D3);
  303.   digitalWrite(LED_1, D4);
  304. }

  305. void LEDtenmetsu(int LED) {
  306.   for (int i = 0; i < 2; i++) {
  307.     digitalWrite(LED, HIGH);
  308.     delay(500);
  309.     digitalWrite(LED, LOW);
  310.     delay(500);
  311.   }
  312. }


コメントを投稿