Ganponブログ

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

タミヤ 1/35 マークⅣメール製作(回路とスケッチ)

2025-02-04 17:00:01 | 1/35 マークⅣメール

2025-02-04
主砲の旋回範囲を微調整し、アクリファイバーの不要分を切除して完成です。
完成画像、動画は後日にアップします。
今日はESP32用スケッチ(プログラム)と回路図を掲載します。

サーボモータの動作範囲はセンター90°、左右45°(45°~135°)としていましたが、
車体に組み込んで10°程度設定を調整しました。

【スケッチ】

  1. /*PS3_ESP32_tank_MP3_JQ8400_MK4_v1a
  2.    2025-02-04
  3.   最大1310720バイトのフラッシュメモリのうち、スケッチが1087009バイト(82%)を使っています。
  4.   最大327680バイトのRAMのうち、グローバル変数が39620バイト(12%)を使っていて、
  5.   ローカル変数で288060バイト使うことができます。
  6.  
  7.   ボード:ESP32 Dev Module
  8.   効果音はJQ8400i
  9.   モータドライバはDRV8835
  10.  
  11.   【操作手順】
  12.    電源スイッチON。
  13.    PSボタンでペアリング開始。
  14.    赤色インジケータランプ高速点滅。点灯でペアリング完了。
  15.  
  16.   【走行コントロール】
  17.    コントローラーの左スティック上下で前後進、
  18.    右スティックの左右でステアリングを制御。
  19.    ステアリングを振っていくと回転軸側が減速していき(緩旋回から信地旋回)、
  20.    一杯に倒すと回転軸側は停止。(信地旋回)
  21.    左スティック中央で右ステアリングを一杯に振ると超信地旋回(速度50%)
  22.  
  23.   【砲塔旋回】左十字キーRボタンで左側砲塔右旋回、Lボタンで左旋回。
  24.    右十字キー 〇ボタンで右側砲塔右旋回、□ボタンで左旋回。
  25.         ボタンを押している間旋回、放した位置で停止。
  26.    純正PS3コントローラでないと、旋回が上手く出来ない。
  27.  
  28.   【主 砲】R1ボタンで右主砲発砲、L1ボタンで左主砲発砲。
  29.   【機関銃】?ボタンで右機関銃発砲、DOWNボタンで左機関銃発砲、
  30.        △ボタンで前機関銃発砲。 
  31. */
  32.  
  33. #include <Arduino.h> // Arduino ヘッダインクルード
  34. //#include "SoftwareSerial.h" // EspSoftwareSerial
  35. //SoftwareSerial mySerial(16, 17); // RX, TX EspSoftwareSerial
  36. HardwareSerial Serial_df(2); // use HardwareSerial UART2 (16pin=RX, 17pin=TX)
  37. #include <JQ8400_Serial.h>
  38. JQ8400_Serial mp3(Serial_df);
  39.  
  40. #include <Ps3Controller.h>
  41. #include <ESP32Servo.h>
  42. Servo servo1;
  43. int servo1Pin = 27;
  44. Servo servo2;
  45. int servo2Pin = 14;
  46.  
  47. int LED_1 = 23; //左主砲
  48. int LED_2 = 22; //右主砲
  49. int LED_3 = 18; //左機関銃
  50. int LED_4 = 19; //右機関銃
  51. int LED_5 = 5; //前機関銃
  52.  
  53. int k = 0;
  54. int s = 0;
  55. int d_time = 50;
  56. int d_time1 = 10;
  57.  
  58. int angle_servo1 = 80; // 左砲塔旋回
  59. int anglenow1 = angle_servo1 ;
  60. int angle_servo2 = 90; // 右砲塔旋回
  61. int anglenow2 = angle_servo2 ;
  62.  
  63. int motor_speed;
  64. float steering;
  65. int pos_ly;
  66. int pos_lx;
  67. int pos_ry;
  68. int pos_rx;
  69.  
  70. int AIN1 = 32; // A入力1/APHASE 左モータ AIN1
  71. int BIN1 = 25; // B入力1/BPHASE 右モータ BIN1
  72. int PWMApin = 33; // A入力2/AENABLE 左モータ AIN2
  73. int PWMBpin = 26; // B入力2/BENABLE 右モータ BIN2
  74. int PWMA = 2; //PWMAチャンネル 0=NG 1=NG 0〜15
  75. int PWMB = 3; //PWMBチャンネル 0=NG 1=NG 0〜15 
  76.  
  77. void setup() {
  78.   servo1.setPeriodHertz(50); // Standard 50hz servo PWMサイクル:20mS FH-1083
  79.   servo1.attach(servo1Pin, 500, 2400); // (servo1Pin, minUs, maxUs)
  80.   servo2.setPeriodHertz(50); // Standard 50hz servo PWMサイクル:20mS
  81.   servo2.attach(servo2Pin, 500, 2400); // (servo1Pin, minUs, maxUs)
  82.  
  83.   //mySoftwareSerial.begin(9600);
  84.   Serial_df.begin(9600); // RX2 = 16, TX2 = 17
  85.   Serial.begin(116500);
  86.  
  87.   Ps3.begin("00:11:22:33:44:55"); //SixaxisPairToolで調べたmac adresに修正
  88.   Serial.println("PS3 Ready");
  89.  
  90.   // Now we cam reset.
  91.   mp3.reset();
  92.   mp3.setVolume(25);
  93.  
  94.   ledcSetup(PWMA, 5000, 8); //チャンネル,周波数,解像度(8bit=256段階)
  95.   ledcAttachPin(PWMApin, PWMA); //ledPinをPWMCHチャンネルに接続
  96.   ledcSetup(PWMB, 5000, 8); //チャンネル,周波数,解像度(8bit=256段階)
  97.   ledcAttachPin(PWMBpin, PWMB); //ledPinをPWMCHチャンネルに接続
  98.   pinMode(AIN1, OUTPUT);
  99.   pinMode(BIN1, OUTPUT);
  100.  
  101.   pinMode(LED_1, OUTPUT); //左主砲
  102.   pinMode(LED_2, OUTPUT); //右主砲
  103.   pinMode(LED_3, OUTPUT); //左機関銃
  104.   pinMode(LED_4, OUTPUT); //右機関銃
  105.   pinMode(LED_5, OUTPUT); //前機関銃
  106.  
  107.   servo1.write(angle_servo1); // 85
  108.   delay(100);
  109.   servo2.write(angle_servo2); // 90
  110.   delay(100);
  111.  
  112.   mp3.playFileByIndexNumber(3); //エンジン始動
  113.   delay(1000);
  114.  
  115.   LEDtenmetsu(LED_5); //Ready go
  116. }
  117.  
  118. void loop() {
  119.   if (Ps3.isConnected()) {
  120.     pos_lx = Ps3.data.analog.stick.lx;
  121.     pos_lx = pos_lx + 128;
  122.     pos_ly = Ps3.data.analog.stick.ly;
  123.     pos_ly = pos_ly + 128;
  124.     pos_rx = Ps3.data.analog.stick.rx;
  125.     pos_rx = pos_rx + 128;
  126.  
  127.     //主砲旋回
  128.     // 左側砲塔 右旋回
  129.     if ( abs(Ps3.event.analog_changed.button.right) && ( anglenow1 > 30 )) {
  130.       anglenow1 -= 1;
  131.       servo1.write(anglenow1);
  132.       delay(d_time1);
  133.     }
  134.  
  135.     //左側砲塔 左旋回
  136.     if ( abs(Ps3.event.analog_changed.button.left) && ( anglenow1 < 125 )) {
  137.       anglenow1 += 1 ;
  138.       servo1.write(anglenow1);
  139.       delay(d_time1);
  140.     }
  141.  
  142.     // 右側砲塔 右旋回
  143.     if ( abs(Ps3.event.analog_changed.button.circle) && ( anglenow2 > 45 )) {
  144.       anglenow2 -= 1;
  145.       servo2.write(anglenow2);
  146.       delay(d_time1);
  147.     }
  148.  
  149.     // 右側砲塔 左旋回
  150.     if ( abs(Ps3.event.analog_changed.button.square) && ( anglenow2 < 145 )) {
  151.       anglenow2 += 1 ;
  152.       servo2.write(anglenow2);
  153.       delay(d_time1);
  154.     }
  155.  
  156.     if (Ps3.event.button_down.r1) { //右主砲 発砲
  157.       digitalWrite(LED_2, HIGH); //右主砲発光
  158.       mp3.playFileByIndexNumber(1);
  159.       delay(300);
  160.       digitalWrite(LED_2, LOW);
  161.       delay(20);
  162.     }
  163.  
  164.     if (Ps3.event.button_down.l1) { //左主砲 発砲
  165.       digitalWrite(LED_1, HIGH); //左主砲発光
  166.       mp3.playFileByIndexNumber(1);
  167.       delay(300);
  168.       digitalWrite(LED_1, LOW);
  169.       delay(20);
  170.     }
  171.  
  172.     if (Ps3.event.button_down.cross) { //右機関銃
  173.       mp3.playFileByIndexNumber(10);
  174.       delay(100);
  175.       for ( k = 0; k < 5; k++) {
  176.         digitalWrite(LED_4, HIGH); //発光
  177.         delay(80);
  178.         digitalWrite(LED_4, LOW);
  179.         delay(120);
  180.       }
  181.     }
  182.  
  183.     if (Ps3.event.button_down.down) { //左機関銃
  184.       mp3.playFileByIndexNumber(10);
  185.       delay(100);
  186.       for ( k = 0; k < 5; k++) {
  187.         digitalWrite(LED_3, HIGH); //発光
  188.         delay(80);
  189.         digitalWrite(LED_3, LOW);
  190.         delay(120);
  191.       }
  192.     }
  193.  
  194.     if (Ps3.event.button_down.triangle) { //前機関銃
  195.       mp3.playFileByIndexNumber(10);
  196.       delay(100);
  197.       for ( k = 0; k < 5; k++) {
  198.         digitalWrite(LED_5, HIGH); //発光
  199.         delay(80);
  200.         digitalWrite(LED_5, LOW);
  201.         delay(120);
  202.       }
  203.     }
  204.  
  205.     //走行コントロール
  206.  
  207.     //前進
  208.     if (pos_ly <= 89 && pos_rx >= 89 && pos_rx <= 165) {
  209.       motor_speed = map(pos_ly, 89, 0, 0, 255);
  210.       motor_run(motor_speed, 0, motor_speed, 0);
  211.     }
  212.  
  213.     //後進
  214.     else if ( pos_ly >= 165 && pos_rx >= 89 && pos_rx <= 165) {
  215.       motor_speed = map(pos_ly, 165, 255, 0, 255) ;
  216.       motor_run(motor_speed, 1, motor_speed, 1);
  217.     }
  218.  
  219.     //前進右緩旋回、信地旋回
  220.     //else if ( pos_ly <= 89 && pos_rx > 165 && pos_rx <= 245) {
  221.     else if ( pos_ly <= 89 && pos_rx >= 165) {
  222.       motor_speed = map(pos_ly, 89, 0, 0, 255);
  223.       steering = motor_speed * (1.00 - (map(pos_rx, 165, 255, 0, 255) / 255.00));
  224.       motor_run(motor_speed, 0, steering, 0);
  225.     }
  226.  
  227.     //前進左緩旋回、信地旋回
  228.     //else if ( pos_ly <= 89 && pos_rx < 89 && pos_rx >= 10) {
  229.     else if ( pos_ly <= 89 && pos_rx <= 89) {
  230.       motor_speed = map(pos_ly, 89, 0, 0, 255);
  231.       steering = motor_speed * (1.00 - (map(pos_rx, 89, 0, 0, 255) / 255.00));
  232.       motor_run(steering, 0, motor_speed, 0);
  233.     }
  234.  
  235.     //後進右緩旋回、信地旋回
  236.     //else if ( pos_ly >= 165 && pos_rx > 165 && pos_rx <= 245) {
  237.     else if ( pos_ly >= 165 && pos_rx >= 165 ) {
  238.       motor_speed = map(pos_ly, 165, 255, 0, 255);
  239.       steering = motor_speed * (1.00 - (map(pos_rx, 165, 255, 0, 255) / 255.00));
  240.       motor_run(motor_speed, 1, steering, 1);
  241.     }
  242.  
  243.     //後進左緩旋回、信地旋回
  244.     //else if ( pos_ly >= 165 && pos_rx < 89 && pos_rx >= 10) {
  245.     else if ( pos_ly >= 165 && pos_rx <= 89 ) {
  246.       motor_speed = map(pos_ly, 165, 255, 0, 255);
  247.       steering = motor_speed * (1.00 - (map(pos_rx, 89, 0, 0, 255) / 255.00));
  248.       motor_run(steering, 1, motor_speed, 1);
  249.     }
  250.  
  251.     //右超信地旋回
  252.     else if (pos_rx >= 245 && pos_ly >= 89 && pos_ly <= 165) {
  253.       motor_speed = 204;
  254.       motor_run(motor_speed, 0, motor_speed, 1);
  255.     }
  256.  
  257.     //左超信地旋回
  258.     else if (pos_rx <= 10 && pos_ly >= 89 && pos_ly <= 165) {
  259.       motor_speed = 204;
  260.       motor_run(motor_speed, 1, motor_speed, 0);
  261.     }
  262.  
  263.     else { //停止(ブレーキ)
  264.       motor_run(0, 0, 0, 0);
  265.     }
  266.   }
  267. }
  268.  
  269.  
  270. void motor_run(int D0, int D1, int D2, int D3) {
  271.   //D0 : モータスピード(左)
  272.   //D1 : モータA(左)1 = HIGH / 0 = LOW
  273.   //D2 : モータスピード(右)
  274.   //D3 : モータB(右)1 = HIGH / 0 = LOW
  275.  
  276.   ledcWrite(PWMA, D0); //(チャンネル,解像度)
  277.   digitalWrite(AIN1, D1);
  278.   ledcWrite(PWMB, D2); //(チャンネル,解像度)
  279.   digitalWrite(BIN1, D3);
  280. }
  281.  
  282. void LEDtenmetsu(int LED) {
  283.   for (int i = 0; i < 2; i++) {
  284.     digitalWrite(LED, HIGH);
  285.     delay(500);
  286.     digitalWrite(LED, LOW);
  287.     delay(500);
  288.   }
  289. }

 

【回路図】



コメントを投稿