Есть какие-нибудь новости?
Вид для печати
Есть какие-нибудь новости?
После долгой паузы работа над проектом продолжена.
Уточнены условия работы полного привода (ПП).
Критика, дополнения и комментарии приветствуются.
Каждая из частных задач была ранее реализована отдельно, сейчас просто свожу в один проект и один модуль.
В железе все воплощено, скетч в черне готов.
Проект оброс мясом и сейчас выглядит следующим образом.
Задачи:
1. Включение муфты ПП по 3х позиционному переключателю "AUTO"-"4x2"-"4x4"
- AUTO - режим работы муфты для распределения крутящего момента 75/25 (пер./задний мост)
- 4х2 - муфта выкл.
- 4х4 - режим работы муфты для распределения крутящего момента 60/40 (пер./задний мост)
- звуковое оповещение о вкл. муфте (реализовано)
- индикация о вкл. муфте на панели приборов (реализовано)
2. Управление видеокамерами (задняя, две боковые мертвых зон) - от сигнала заднего хода и при включении поворотников, доп. управление (переключение) камерами с рулевых кнопок (было реализовано, в наст. момент в доработке)
3. Управление Головным устройством (ГУ) с рулевых кнопок через ИК передатчик - "+/-" звук, след. трек.
4. Индикация на ЖКИ панели приборов рекомендуемой передачи КПП в зависимости от скорости движения (было реализовано, в наст. момент в доработке)
Реализация:
В проекта использованы модули:
- Seeeduino Mega 1280 (http://www.seeedstudio.com/wiki/Seeeduino_Mega)
- Monster moto shield (http://arduino.ru/forum/programmirov...er-moto-shield)
- 8 Relay Shield (http://big-e.ru/images/4х4_arduino/8...e-Arduino1.jpg)
- Шилд питания
- ИК передачик от пульта TV
- Отдельные решения ввода-вывода сигналов
Эл. схема проекта: http://big-e.ru/images/4х4_arduino/1.pdf
Фото готового модуля:
http://big-e.ru/images/4х4_arduino/P1040464.JPG
http://big-e.ru/images/4х4_arduino/P1040465.JPG
http://big-e.ru/images/4х4_arduino/P1040466.JPG
Скетч (пока в отладке, основные моменты работают):
Спасибо огромное отзывчивому и крайне терпеливому Администратору данного сайта.Код://#include <SPI.h>
#include <avr/wdt.h>#if DEBUG
#include <SoftwareSerial.h>
#include <TVout.h>
#include <fontALL.h>
#include "pitches.h"
#include <EEPROM.h>
//#include <MsTimer2.h>
#include <TimerFive.h>
#include <IRremote.h>
//**TODO
/*
*/
// Программа для управления контроллером муфты ITM, камерами заднего и бокового видов, кнопками руля и магнитолой автомобиля Chery Tiggo
#define DEBUG 1 // используется при отладке
long MOMENT1=128;
long MOMENT2=224;
long MOM=0;
IRsend irsend;
//long Timer_Time=300000; //mcsec
//boolean at_once=true; // переменная для контроля одноразового выполнения
//Начальная мелодия
/**
int melody[] = {NOTE_C5, NOTE_E5,NOTE_E4, NOTE_C4};
int noteDurations[] = {10,10,10,4};
*/
int melody[] = {NOTE_C5, NOTE_A4,NOTE_F4, NOTE_E5};
int noteDurations[] = {5,15,15,6};
volatile unsigned long Speed_ImpulseTime = 0; // время между импульсами датчика скорости
volatile unsigned long Speed_time=0; // время для отсчета импульсов
volatile int Speed_impulse_count = 0; // кол-во импульсов датчика скорости
volatile float Speed=0; // скорость с датчика скорости
volatile unsigned long Taho_ImpulseTime = 0; // время между импульсами тахометра
volatile unsigned long Taho_time=0; // время для отсчета импульсов
volatile int Tahometr_impulse_count = 0; // кол-во импульсов тахометра
volatile float Taho=0; // обороты двигателя
#define BRAKEVCC 0
#define CW 1
#define CCW 2
#define BRAKEGND 3
#define CS_THRESHOLD 100
char LastGear='0';
char RecommendGear='0';
//*****************ИК порт
#define TOPBIT 0x80000000
#define NEC_HDR_MARK 9000
#define NEC_HDR_SPACE 4500
#define NEC_BIT_MARK 560
#define NEC_ONE_SPACE 1690
#define NEC_ZERO_SPACE 560
#define NEC_BITS 32
#define DUTY_CYCLE 1/3 // Carrier duty cycle
#define PERIOD 26 // 38kHz, 1/38kHz =~ 26us
#define ACTIVE_HIGH (PERIOD * DUTY_CYCLE)
#define ACTIVE_LOW (PERIOD - (PERIOD * DUTY_CYCLE))
unsigned long SRC=0x04;
unsigned long VOLDOWN=0x1F;
unsigned long VOLUP=0x5C;
unsigned long code[96]= {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F};
unsigned long codehex[96]= {0xAA00FF, 0xAA807F, 0xAA40BF, 0xAAC03F, 0xAA20DF, 0xAAA05F, 0xAA609F, 0xAAE01F, 0xAA10EF, 0xAA906F, 0xAA50AF, 0xAAD02F, 0xAA30CF, 0xAAB04F, 0xAA708F, 0xAAF00F, 0xAA08F7, 0xAA8877, 0xAA48B7, 0xAAC837, 0xAA28D7, 0xAAA857, 0xAA6897, 0xAAE817, 0xAA18E7, 0xAA9867, 0xAA58A7, 0xAAD827, 0xAA38C7, 0xAAB847, 0xAA7887, 0xAAF807, 0xAA04FB, 0xAA847B, 0xAA44BB, 0xAAC43B, 0xAA24DB, 0xAAA45B, 0xAA649B, 0xAAE41B, 0xAA14EB, 0xAA946B, 0xAA54AB, 0xAAD42B, 0xAA34CB, 0xAAB44B, 0xAA748B, 0xAAF40B, 0xAA0CF3, 0xAA8C73, 0xAA4CB3, 0xAACC33, 0xAA2CD3, 0xAAAC53, 0xAA6C93, 0xAAEC13, 0xAA1CE3, 0xAA9C63, 0xAA5CA3, 0xAADC23, 0xAA3CC3, 0xAABC43, 0xAA7C83, 0xAAFC03, 0xAA02FD, 0xAA827D, 0xAA42BD, 0xAAC23D, 0xAA22DD, 0xAAA25D, 0xAA629D, 0xAAE21D, 0xAA12ED, 0xAA926D, 0xAA52AD, 0xAAD22D, 0xAA32CD, 0xAAB24D, 0xAA728D, 0xAAF20D, 0xAA0AF5, 0xAA8A75, 0xAA4AB5, 0xAACA35, 0xAA2AD5, 0xAAAA55, 0xAA6A95, 0xAAEA15, 0xAA1AE5, 0xAA9A65, 0xAA5AA5, 0xAADA25, 0xAA3AC5, 0xAABA45, 0xAA7A85, 0xAAFA05};
//*****************ИК порт
volatile unsigned long Time_On=0;
int RearCamNum=1;
#define SignalOn HIGH
#define SignalOff LOW
TVout TV;
boolean mode=false;
char prog_version_major =1;
char prog_version_manor1 =0;
char prog_version_manor2 =0;
int speed_kmh=0;
int taho_obm=0;
//\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
////// ********Описание периферии********** ///////////
// Контакт 0 для - зарезервировано, не использовать!!!
// Контакт 1 для - зарезервировано, не использовать!!!
#define TahometrPin 2 // Тахометр - требуется подтяжка, с прерыванием - ШИМ
#define SpeedSensorPin 3 // Спидометр - требуется подтяжка, с прерыванием - ШИМ
#define HandBrakePin 4 // Ручник - требуется подтяжка
#define RearGearPin 5 // З.Х. - требуется подтяжка
#define LeftTurnPin 6 // Лев. пов. - требуется подтяжка
#define RightTurnPin 7 // Прав. пов. - требуется подтяжка
#define MonsterMoto8 8// Контакт 8 для шилда управления муфты - MONSTER MOTO INB: Counter-clockwise input ШИМ
#define MonsterMoto9 9// Контакт 9 для шилда управления муфты - MONSTER MOTO INB: Counter-clockwise input ШИМ
#define SpeakerPin 10// Контакт 10 для динамика
// Контакт 11 для Tvout Sync ЗАНЯТО!!!!
//Контакт 12-21 СВОБОДНО
#define FOURxFOURLedPin 22 // Индикатор 4х4
#define FOURxFOURSwitchPin 23 // Включатель 4х4 (50/50) - требуется подтяжка
#define AWDSwitchPin 24 // Включатель AWD (70/30) - требуется подтяжка
#define Relay_Camera1_Video_Pin 25// Контакт для реле - Камера З.Х.
#define Relay_Camera2_Video_Pin 26// Контакт для реле - Камера лев.
#define Relay_Camera3_Video_Pin 27// Контакт для реле - Камера прав.
#define Relay_GU_12V_Pin 28// Контакт для реле - 12V питание на ГУ (имитация заднего хода)
// Контакт 29 для Tvout Video ЗАНЯТО!!!!
#define Relay_Camera1_12V_Pin 30// Контакт для реле - питание прав.
#define Relay_Camera2_12V_Pin 31// Контакт для реле - питание лев.
#define Relay_Camera3_12V_Pin 32// Контакт для реле - питание З.Х.
#define Relay_MonsterMoto_12V_Pin 33// Контакт для реле - питание контроллера муфты
#define LCDGearP_Indicate_Pin 34 // Контакт 34 для индикации Передачи P на ЖКИ
#define ModeButtonPin 35// Контакт кнопка-режим
// Контакт 36-37 СВОБОДНО
#define LCDGear1_Indicate_Pin 38 // Контакт 38 для индикации Передачи 1 на ЖКИ
#define LCDGear2_Indicate_Pin 39 // Контакт 39 для индикации Передачи 2 на ЖКИ
#define LCDGear3_Indicate_Pin 40 // Контакт 40 для индикации Передачи 3 на ЖКИ
#define LCDGear4_Indicate_Pin 41 // Контакт 41 для индикации Передачи 4 на ЖКИ
#define LCDGearD_Indicate_Pin 42 // Контакт 42 для индикации Передачи D на ЖКИ
#define LCDGearN_Indicate_Pin 43 // Контакт 43 для индикации Передачи N на ЖКИ
#define LCDGearR_Indicate_Pin 44 // Контакт 44 для индикации Передачи R на ЖКИ
#define IRPin 45 // ИК выход
#define MonsterMoto4 46 // Контакт 46 для муфты на шилде MonsterMoto
#define MonsterMoto5 47// Контакт 47 для муфты на шилде MonsterMoto
#define MonsterMoto6 48// Контакт 48 для муфты на шилде MonsterMoto
#define MonsterMoto7 49// Контакт 49 для муфты на шилде MonsterMoto
// Контакт 50 MISO СВОБОДНО
// Контакт 51 MOSI СВОБОДНО
// Контакт 52 SCK СВОБОДНО
// Контакт 53 SS СВОБОДНО
//аналоговые входы
// Контакт 0-3 СВОБОДНО
#define MonsterMoto0 4//A4 для муфты на шилде MonsterMoto
#define MonsterMoto1 5//A5 для муфты на шилде MonsterMoto
#define MonsterMoto2 6//A6 для муфты на шилде MonsterMoto
#define MonsterMoto3 7//A7 для муфты на шилде MonsterMoto
#define WheelButtonsPin 8 //A8 // кнопки руля
// Контакт 9-15 СВОБОДНО
// описание контактов шилда Monster Moto
int inApin[2] = {
MonsterMoto7, MonsterMoto4}; // INA: Clockwise input
int inBpin[2] = {
MonsterMoto8, MonsterMoto9}; // INB: Counter-clockwise input
int pwmpin[2] = {
MonsterMoto5, MonsterMoto6}; // PWM input
int cspin[2] = {
MonsterMoto2, MonsterMoto3}; // CS: Current sense ANALOG input
int enpin[2] = {
MonsterMoto0, MonsterMoto1}; // EN: Status of switches output (Analog pin)
//описание переменных
//boolean RelayOn = false;
double RPM;
unsigned long Check_time ;
// переменные нажатия рулевых кнопок
unsigned long math_time,old_time,real_time, res_dt1, res_d;
int LIMIT=10;
char ButtonName='X'; // +, -, >, R=>>|, L=|<<, S=SRC, X=None
// переменные нажатия рулевых кнопок - конец
//###################################################################
//общие настройки
void setup()
{
wdt_enable (WDTO_8S); // сторожевой таймер от зависания
TV.begin(PAL,120,96); // 1 ширина, 2 высота
TV.select_font(font6x8); // 1 ширина, 2 высота
TV.clear_screen();
//*************************Описание пинов**************************
//Контакт 0 для - зарезервировано, не использовать!!!
//Контакт 1 для - зарезервировано, не использовать!!!
//Контакт 2 !!!!!!!!!ПРЕРЫВАНИЕ 0
pinMode(TahometrPin, INPUT); // Контакт для тахометра !!!!!!!!!ПРЕРЫВАНИЕ 0
digitalWrite(TahometrPin, HIGH); //внутренняя подтяжка входа тахометра
attachInterrupt(0, TahometrImpulse_on, FALLING); //RISING);// настройка прерывания и функции на него
//Контакт 3 !!!!!!!!!ПРЕРЫВАНИЕ 1
pinMode(SpeedSensorPin, INPUT); // Контакт для датчика скорости !!!!!!!!!ПРЕРЫВАНИЕ 1
digitalWrite(SpeedSensorPin, HIGH); //внутренняя подтяжка входа датчика скорости
attachInterrupt(1, SpeedImpulse_on, FALLING); // настройка прерывания и функции на него
//Контакт 4
pinMode(HandBrakePin, INPUT); // Контакт для ручника
digitalWrite(HandBrakePin, HIGH); //внутренняя подтяжка входа ручника
//Контакт 5-7
pinMode(RearGearPin , INPUT);// Контакт для сигнала от заднего хода
digitalWrite(RearGearPin , HIGH); //внутренняя подтяжка входа +++++
pinMode(LeftTurnPin, INPUT);// Контакт для сигнала от левого поворотника
digitalWrite(LeftTurnPin, HIGH); //внутренняя подтяжка входа +++++
pinMode(RightTurnPin, INPUT);// Контакт для сигнала от правого поворотника
digitalWrite(RightTurnPin, HIGH); //внутренняя подтяжка входа +++++
//Контакт 8-9 MonsterMoto
for (int i=0; i<2; i++)
{
pinMode(inApin[i], OUTPUT);
pinMode(inBpin[i], OUTPUT);
pinMode(pwmpin[i], OUTPUT);
}
// Initialize braked
for (int i=0; i<2; i++)
{
digitalWrite(inApin[i], LOW);
digitalWrite(inBpin[i], LOW);
}
pinMode(SpeakerPin, OUTPUT); // Контакт 10 для динамика
//Контакт 11 для TVout
//Контакт 12-21 СВОБОДНО
//Контакт 22 Индикатор 4х4
pinMode(FOURxFOURLedPin, OUTPUT);// Контакт Индикатор 4х4
//Контакт 23 Включатель 4х4
pinMode(FOURxFOURSwitchPin, INPUT);// Контакт Включатель 4х4
digitalWrite(FOURxFOURSwitchPin , HIGH); //внутренняя подтяжка входа +++++
//Контакт 24 Включатель AWD
pinMode(AWDSwitchPin, INPUT);// Контакт Включатель AWD
digitalWrite(AWDSwitchPin , HIGH); //внутренняя подтяжка входа +++++
//Контакт 25-28
pinMode(Relay_Camera1_Video_Pin, OUTPUT);
pinMode(Relay_Camera2_Video_Pin, OUTPUT);
pinMode(Relay_Camera3_Video_Pin, OUTPUT);
pinMode(Relay_GU_12V_Pin, OUTPUT);
// Контакт 29 для Tvout Video ЗАНЯТО!!!!
//Контакт 30-33
pinMode(Relay_Camera1_12V_Pin, OUTPUT);
pinMode(Relay_Camera2_12V_Pin, OUTPUT);
pinMode(Relay_Camera3_12V_Pin, OUTPUT);
pinMode(Relay_MonsterMoto_12V_Pin, OUTPUT);
//34
pinMode(LCDGearP_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи P на ЖКИ
//Контакт 35 кнопка-режим
pinMode(ModeButtonPin, INPUT);// Контакт кнопка-режим
digitalWrite(ModeButtonPin , HIGH); //внутренняя подтяжка входа +++++
// Контакт 36-37 СВОБОДНО
//38
pinMode(LCDGear1_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи 1 на ЖКИ
//39
pinMode(LCDGear2_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи 2 на ЖКИ
//40
pinMode(LCDGear3_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи 3 на ЖКИ
//41
pinMode(LCDGear4_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи 4 на ЖКИ
//42
pinMode(LCDGearD_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи D на ЖКИ
//43
pinMode(LCDGearN_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи N на ЖКИ
//44
pinMode(LCDGearR_Indicate_Pin, OUTPUT);// Контакт для индикации Передачи R на ЖКИ
//Контакт 45 ИК выход
pinMode(IRPin, OUTPUT);
//46-49 Контакты MonsterMoto
// Контакт 50 MISO
// Контакт 51 MOSI
// Контакт 52 SCK
// Контакт 53 SS
//выключаем ЖКИ, камеры и муфту
Gear_LCD_Clear();
Cameras_OFF();
motorOff(0);
motorOff(1);
//
Startup(); // стартовое приветствие
// MsTimer2::set(1500, Timer2_Timer); // таймер будет срабатывать через каждые 500ms
// MsTimer2::start();//запустить таймер
Timer5.initialize(5000000);
Timer5.attachInterrupt(Beep);
#if DEBUG
Serial.begin(9600);
#endif
}
void Beep(void)
{
if ((digitalRead(FOURxFOURSwitchPin)==LOW)|| (digitalRead(AWDSwitchPin)==LOW))// если переключатель в положении 4х4 или Auto
{
TV.tone(NOTE_E5,400);
}
}
// главный цикл
void loop()
{
wdt_reset();
Cameras(); //Работа с камерами
WheelButtons(); //Работа с кнопками руля
Indicate_Recommended_Gear(Speed); //отображение рекомендуемой передачи на LCD
FOURxFOURButton(); //Работа с переключателем 4x4
ModeButton();//Работа с кнопкой mode
}
boolean notyetdoes=false;
//Работа с кнопкой mode
void ModeButton()
{
if (digitalRead(ModeButtonPin)==LOW)
{
mode=!mode;
notyetdoes=false;
TV.tone(NOTE_D6,200);
delay(1000);
}
if (mode)
{
//TV.begin(PAL,120,96); // 1 ширина, 2 высота
//TV.select_font(font6x8); // 1 ширина, 2 высота
//TV.clear_screen();
TVoutPrint();
}
if ((!mode) && (!notyetdoes))
{
TV.clear_screen();
notyetdoes=true;
//TV.end();
}
}
/*
#define note_len 200000
#define play_c 3830
#define play_d 3400
#define play_e 3038
*/
void Startup() //Стартовое приветствие
{
for (int thisNote = 0; thisNote < 4; thisNote++) {
int noteDuration = 1000/noteDurations[thisNote];
TV.tone(melody[thisNote],noteDuration);
int pauseBetweenNotes = noteDuration * 1.30;
TV.delay(pauseBetweenNotes);
TV.noTone();
}
}
/*
void Timer2_Timer() //обработка событий в таймере - Работа с статусными событиями в таймере
{
}
*/
/*
void playTone(int note) {
long elapsed_time = 0;
while (elapsed_time < note_len) {
digitalWrite(SpeakerPin,HIGH);
delayMicroseconds(note / 2);
digitalWrite(SpeakerPin, LOW);
delayMicroseconds(note / 2);
elapsed_time += (note);
}
}
*/
//###################################################################
//Работа с переключателем 4x4
void FOURxFOURButton()
{
if (digitalRead(FOURxFOURSwitchPin)==LOW) // если переключатель в положении 4х4
{
digitalWrite(FOURxFOURLedPin, HIGH);
digitalWrite(Relay_MonsterMoto_12V_Pin, HIGH);
motorGo(0,CW,MOMENT2);
}
if (digitalRead(AWDSwitchPin)==LOW) // если переключатель в положении Auto
{
digitalWrite(FOURxFOURLedPin, HIGH);
digitalWrite(Relay_MonsterMoto_12V_Pin, HIGH);
motorGo(0,CW,MOMENT1);
}
if ((digitalRead(FOURxFOURSwitchPin)==HIGH)&&(digitalRead(AWDSwitchPin)==HIGH)) // если переключатель в положении 4х2
{
digitalWrite(FOURxFOURLedPin, LOW);
digitalWrite(Relay_MonsterMoto_12V_Pin, LOW);
motorOff(0);
}
}
void motorOff(int motor)
{
// Initialize braked
for (int i=0; i<2; i++)
{
digitalWrite(inApin[i], LOW);
digitalWrite(inBpin[i], LOW);
}
analogWrite(pwmpin[motor], 0);
}
/* motorGo() will set a motor going in a specific direction
the motor will continue going in that direction, at that speed
until told to do otherwise.
motor: this should be either 0 or 1, will selet which of the two
motors to be controlled
direct: Should be between 0 and 3, with the following result
0: Brake to VCC
1: Clockwise
2: CounterClockwise
3: Brake to GND
pwm: should be a value between ? and 255, higher the number, the faster
it'll go
*/
void motorGo(uint8_t motor, uint8_t direct, uint8_t pwm)
{
if (motor <= 1)
{
if (direct <=4)
{
// Set inA[motor]
if (direct <=1)
digitalWrite(inApin[motor], HIGH);
else
digitalWrite(inApin[motor], LOW);
// Set inB[motor]
if ((direct==0)||(direct==2))
digitalWrite(inBpin[motor], HIGH);
else
digitalWrite(inBpin[motor], LOW);
analogWrite(pwmpin[motor], pwm);
}
}
#if DEBUG
Serial.print("4x4_PWM=");
Serial.println(pwm);
#endif
}
//###################################################################
//Работа с кнопками руля
void WheelButtons()
{
char But='X';
if (WheelButonPush_IsPushed()){ But=ButtonName; }
/*
if (But=='>'){sendNEC(SRC);}
if (But=='-'){sendNEC(VOLDOWN);}
if (But=='+'){sendNEC(VOLUP);}
*/
if (But=='>'){irsend.sendNEC(codehex[SRC], 32);}
if (But=='-'){irsend.sendNEC(codehex[VOLDOWN], 32);}
if (But=='+'){irsend.sendNEC(codehex[VOLUP], 32);}
#if DEBUG
Serial.print("WH_But=");
Serial.println(But);
#endif
}
//###################################################################
//Работа с камерами
void Cameras()
{
int Camera_Num=0;
//boolean Start_Video=false;
if (digitalRead(RearGearPin)==SignalOn) {RearCamNum=1;} // если задняя передача выключена, то установить значение камеры задней =1
if ((digitalRead(RearGearPin)==SignalOff) && (ButtonName=='S')) //если задняя передача включена и нажата кнопка SOURCE, то сменить камеру
{
RearCamNum++;
if (RearCamNum>3) {RearCamNum=1;}
}
if ((digitalRead(RearGearPin)==SignalOff) && (ButtonName=='L')) //если задняя передача включена и нажата кнопка <<, то сменить камеру левую
{
RearCamNum=2;
}
if ((digitalRead(RearGearPin)==SignalOff) && (ButtonName=='R')) //если задняя передача включена и нажата кнопка <<, то сменить камеру правую
{
RearCamNum=3;
}
if ((digitalRead(LeftTurnPin)==SignalOn) && (digitalRead(RightTurnPin)==SignalOff)) {Camera_Num=2; Time_On=millis();}
if ((digitalRead(LeftTurnPin)==SignalOff) && (digitalRead(RightTurnPin)==SignalOn)) { Camera_Num=3; Time_On=millis();}
if (digitalRead(RearGearPin)==SignalOff) {Camera_Num=RearCamNum; Time_On=millis();}
if ((digitalRead(LeftTurnPin)==SignalOn) && (digitalRead(RightTurnPin)==SignalOn) && (digitalRead(RearGearPin)==SignalOn)) {Cameras_OFF();}
//if ((digitalRead(LeftTurnPin)==SignalOff) && (digitalRead(RightTurnPin)==SignalOff) && (digitalRead(RearGearPin)==SignalOff)){Cameras_OFF();}
#if DEBUG
//Serial.println(digitalRead(RearGearPin));
#endif
//if ((Start_Video) && (Camera_Num>0))
//{
if ((Time_On+1000)>millis()) {Camera_ON(Camera_Num);} //если время после события (поворота или заднего хода) не болле 1 сек, то камеру включить
else {Cameras_OFF();}
//}
//if ((Time_On+1000)<millis()) {Cameras_OFF();}
#if DEBUG
Serial.print("Cam_Num=");
Serial.println(Camera_Num);
#endif
delay(300);
}
//гасим ЖКИ
void Gear_LCD_Clear()
{
digitalWrite(LCDGear1_Indicate_Pin, LOW);
digitalWrite(LCDGear2_Indicate_Pin, LOW);
digitalWrite(LCDGear3_Indicate_Pin, LOW);
digitalWrite(LCDGear4_Indicate_Pin, LOW);
digitalWrite(LCDGearD_Indicate_Pin, LOW);
digitalWrite(LCDGearN_Indicate_Pin, LOW);
digitalWrite(LCDGearR_Indicate_Pin, LOW);
digitalWrite(LCDGearP_Indicate_Pin, LOW);
}
/*
//###################################################################
void Indicate_Gear_On_LCD(char GearName)
{
Gear_LCD_Clear();
if (GearName=='1'){digitalWrite(LCDGear1_Indicate_Pin, HIGH);}
if (GearName=='2'){digitalWrite(LCDGear2_Indicate_Pin, HIGH);}
if (GearName=='3'){digitalWrite(LCDGear3_Indicate_Pin, HIGH);}
if (GearName=='4'){digitalWrite(LCDGear4_Indicate_Pin, HIGH);}
if (GearName=='5'){digitalWrite(LCDGearD_Indicate_Pin, HIGH);}
if (GearName=='R'){digitalWrite(LCDGearR_Indicate_Pin, HIGH);}
if (GearName=='N'){digitalWrite(LCDGearN_Indicate_Pin, HIGH);}
}
*/
//###################################################################
void Indicate_Recommended_Gear(float Speed_kmh)
{
if (Speed_kmh<=0) {RecommendGear='N';} // N
if ((Speed_kmh>0) && (Speed_kmh<=7)) {RecommendGear='1';} // 1
if ((Speed_kmh>10) && (Speed_kmh<=22)) {RecommendGear='2';} // 2
if ((Speed_kmh>25) && (Speed_kmh<=40)) {RecommendGear='3';} // 3
if ((Speed_kmh>43) && (Speed_kmh<=85)) {RecommendGear='4';} // 4
if (Speed_kmh>90) {RecommendGear='D';} // 5
if (digitalRead(RearGearPin)==SignalOff){RecommendGear='R';} // R
if (LastGear!=RecommendGear)
{
if (LastGear=='1'){digitalWrite(LCDGear1_Indicate_Pin, HIGH);}
if (LastGear=='2'){digitalWrite(LCDGear2_Indicate_Pin, HIGH);}
if (LastGear=='3'){digitalWrite(LCDGear3_Indicate_Pin, HIGH);}
if (LastGear=='4'){digitalWrite(LCDGear4_Indicate_Pin, HIGH);}
if (LastGear=='D'){digitalWrite(LCDGearD_Indicate_Pin, HIGH);}
if (LastGear=='N'){digitalWrite(LCDGearN_Indicate_Pin, HIGH);}
if (LastGear=='R'){digitalWrite(LCDGearR_Indicate_Pin, HIGH);}
if (LastGear=='P'){digitalWrite(LCDGearP_Indicate_Pin, HIGH);}
if (RecommendGear=='1'){digitalWrite(LCDGear1_Indicate_Pin, LOW);}
if (RecommendGear=='2'){digitalWrite(LCDGear2_Indicate_Pin, LOW);}
if (RecommendGear=='3'){digitalWrite(LCDGear3_Indicate_Pin, LOW);}
if (RecommendGear=='4'){digitalWrite(LCDGear4_Indicate_Pin, LOW);}
if (RecommendGear=='D'){digitalWrite(LCDGearD_Indicate_Pin, LOW);}
if (RecommendGear=='N'){digitalWrite(LCDGearN_Indicate_Pin, LOW);}
if (RecommendGear=='R'){digitalWrite(LCDGearR_Indicate_Pin, LOW);}
if (RecommendGear=='P'){digitalWrite(LCDGearP_Indicate_Pin, LOW);}
LastGear=RecommendGear;
#if DEBUG
Serial.print("R_GEAR=");
Serial.println(RecommendGear);
#endif
}
}
//###################################################################
// обработчик событий тахометра
void TahometrImpulse_on() //сидит на прерывании 0, срабатывает при возникновении событий на 2 цифровом входе
{
//TimeImpulse1=
Tahometr_impulse_count++; //увеличить счетчик импульсов
//Speed=0;
if (Tahometr_impulse_count >=2) //2имп=1 оборот коленвала
{
Taho_ImpulseTime = micros()-Taho_time; //время прихода между импульсами
Taho_time = micros(); //обнулить
Taho=((Tahometr_impulse_count*60*1000000)/(2*Taho_ImpulseTime)); // перевод в об/мин, формула универсальна для Тигго, 1 об на 2 ммпульса,1000000 - перевод мкс в сек., 60 - перевод сек в мин.
#if DEBUG
Serial.print("TIT=");
Serial.println(Taho_ImpulseTime);
Serial.print("Taho=");
Serial.println(Taho);
#endif
Tahometr_impulse_count = 0;
}
}
//###################################################################
// обработчик событий датчика скорости
void SpeedImpulse_on() //сидит на прерывании 1, срабатывает при возникновении событий на 3 цифровом входе
{
//TimeImpulse1=
Speed_impulse_count++; //увеличить счетчик импульсов
//Speed=0;
if (Speed_impulse_count >=2) //2имп=0,8м 5имп=2м
{
Speed_ImpulseTime = micros()-Speed_time; //время прихода между импульсами
Speed_time = micros(); //обнулить
Speed=((Speed_impulse_count*2*3.6*1000000)/(5*Speed_ImpulseTime)); // перевод в км/ч, формула универсальна для Тигго, 2=2м за 5 ммпульсов, 3.6 - перевод м/с в км/ч, 1000000 - перевод мкс в сек., 5 - 5 импульсов
#if DEBUG
Serial.print("SIT=");
Serial.println(Speed_ImpulseTime);
Serial.print("Speed=");
Serial.println(Speed);
#endif
Speed_impulse_count = 0;
}
}
void TVoutPrint()
{
//TV.clear_screen();
TV.set_cursor(0,0);
TV.print(" MONSTER IV v1.0.0");
/*TV.print(prog_version_major);
TV.print(".");
TV.print(prog_version_manor1);
TV.print(prog_version_manor2);*/
TV.set_cursor(0,6);
TV.print("-------------------");
TV.set_cursor(0,11);
TV.print("SPD=");
speed_kmh=Speed;
TV.print(speed_kmh);
TV.print(" ");
TV.set_cursor(60,11);
TV.print("TAH=");
taho_obm=RPM;
TV.print(taho_obm);
TV.print(" ");
TV.set_cursor(0,17);
TV.print("-------------------");
TV.set_cursor(0,22);
TV.print("MODE=");
TV.print(int(mode));
TV.set_cursor(60,22);
TV.print("REAR=");
TV.print(digitalRead(RearGearPin));
TV.set_cursor(0,30);
TV.print("LEFT=");
TV.print(digitalRead(LeftTurnPin));
TV.set_cursor(60,30);
TV.print("RIGH=");
TV.print(digitalRead(RightTurnPin));
TV.set_cursor(0,38);
TV.print("GEAR=");
TV.print(RecommendGear);
TV.set_cursor(60,38);
TV.print("WHEL=");
TV.print(ButtonName);
TV.set_cursor(0,46);
TV.print("4x4=");
TV.print(digitalRead(FOURxFOURSwitchPin));
TV.set_cursor(60,46);
TV.print("AWD=");
TV.print(digitalRead(AWDSwitchPin));
TV.set_cursor(0,54);
TV.print("-------------------");
TV.set_cursor(0,59);
TV.print("C1_12V=");
TV.print(digitalRead(Relay_Camera1_12V_Pin));
TV.set_cursor(60,59);
TV.print("C1_VID=");
TV.print(digitalRead(Relay_Camera1_Video_Pin));
TV.set_cursor(0,67);
TV.print("C2_12V=");
TV.print(digitalRead(Relay_Camera2_12V_Pin));
TV.set_cursor(60,67);
TV.print("C2_VID=");
TV.print(digitalRead(Relay_Camera2_Video_Pin));
TV.set_cursor(0,75);
TV.print("C3_12V=");
TV.print(digitalRead(Relay_Camera3_12V_Pin));
TV.set_cursor(60,75);
TV.print("C3_VID=");
TV.print(digitalRead(Relay_Camera3_Video_Pin));
TV.set_cursor(0,83);
TV.print("-------------------");
TV.set_cursor(0,88);
TV.print("MN_12V=");
TV.print(digitalRead(Relay_MonsterMoto_12V_Pin));
TV.set_cursor(60,88);
TV.print("MOM=");
if ((digitalRead(AWDSwitchPin)==HIGH)&& (digitalRead(FOURxFOURSwitchPin)==HIGH)){TV.print(0);}
if (digitalRead(AWDSwitchPin)==LOW) {MOM=((MOMENT1*100)/512); TV.print(MOM);}
if (digitalRead(FOURxFOURSwitchPin)==LOW) {MOM=((MOMENT2*100)/512); TV.print(MOM);}
TV.print("% ");
// TV.print(rear_status);
}
/*
void play_OK()
{
tone(SpeakerPin, NOTE_E4,800);
}
void play_reset()
{
tone(SpeakerPin, NOTE_A5,1000); // reset
}
void play_caution()
{
tone(SpeakerPin, NOTE_D7,800);
}
void mute()
{
noTone(SpeakerPin);
}
*/
void Cameras_OFF()
{
Camera_OFF(1);
Camera_OFF(2);
Camera_OFF(3);
}
void Camera_ON(int Camera_Num)
{
if (Camera_Num==1)
{
Camera_OFF(2);
Camera_OFF(3);
digitalWrite(Relay_Camera1_12V_Pin, HIGH);
digitalWrite(Relay_Camera1_Video_Pin, HIGH);
digitalWrite(Relay_GU_12V_Pin, HIGH);
}
if (Camera_Num==2)
{
Camera_OFF(1);
Camera_OFF(3);
digitalWrite(Relay_Camera2_12V_Pin, HIGH);
digitalWrite(Relay_Camera2_Video_Pin, HIGH);
digitalWrite(Relay_GU_12V_Pin, HIGH);
}
if (Camera_Num==3)
{
Camera_OFF(1);
Camera_OFF(2);
digitalWrite(Relay_Camera3_12V_Pin, HIGH);
digitalWrite(Relay_Camera3_Video_Pin, HIGH);
digitalWrite(Relay_GU_12V_Pin, HIGH);
}
if ((Camera_Num<1)||(Camera_Num>3)){Cameras_OFF();}
}
void Camera_OFF(int Camera_Num)
{
if (Camera_Num==1)
{
digitalWrite(Relay_Camera1_12V_Pin, LOW);
digitalWrite(Relay_Camera1_Video_Pin, LOW);
digitalWrite(Relay_GU_12V_Pin, LOW);
}
if (Camera_Num==2)
{
digitalWrite(Relay_Camera2_12V_Pin, LOW);
digitalWrite(Relay_Camera2_Video_Pin, LOW);
digitalWrite(Relay_GU_12V_Pin, LOW);
}
if (Camera_Num==3)
{
digitalWrite(Relay_Camera3_12V_Pin, LOW);
digitalWrite(Relay_Camera3_Video_Pin, LOW);
digitalWrite(Relay_GU_12V_Pin, LOW);
}
}
//###################################################################
// Функция проверки нажатия рулевой кнопки
// Возвращает false если кнопка не была нажата
// и true если нажата
// ButtonName принимает значения в зависимости от нажатой кнопки +, -, >, R=>>|, L=|<<, S=SRC, X=None
boolean WheelButonPush_IsPushed()
{
bool result;
result=false;
unsigned long buttonVal;
buttonVal=0;
ButtonName='X';
res_d = analogRead(WheelButtonsPin);
if( res_d < LIMIT) res_d = LIMIT;
delay(10);
res_dt1 = analogRead(WheelButtonsPin);
old_time = millis();
math_time = 0;
while(math_time < 200)
{
real_time = millis();
math_time = real_time - old_time;
res_dt1 = analogRead(WheelButtonsPin);
if(res_dt1 < res_d-LIMIT || res_dt1 > res_d+LIMIT)break;
}
if( math_time > 70)
{
buttonVal=res_d;
ButtonName='X';
// Serial.println (res_d);
if ((buttonVal>25) && (buttonVal<45))
{
ButtonName='-'; //35-36
result=true;
}
if ((buttonVal>60) && (buttonVal<85))
{
ButtonName='+'; //72-73
result=true;
}
if ((buttonVal>110) && (buttonVal<135))
{
ButtonName='S'; //122
result=true;
}
if ((buttonVal>175) && (buttonVal<200))
{
ButtonName='R'; //187
result=true;
}
if ((buttonVal>275) && (buttonVal<295))
{
ButtonName='L'; //285
result=true;
}
if ((buttonVal>415) && (buttonVal<440))
{
ButtonName='>'; //429
result=true;
}
if ((buttonVal>645) && (buttonVal<670))
{
ButtonName='X'; //658-659
result=false;
}
buttonVal=0;
}
return result;
}
//Функции работы с ИК портом
void mark(long time)
{
for(int i = 0; i < (time / PERIOD); i++)
{
digitalWrite(IRPin, HIGH);
delayMicroseconds(ACTIVE_HIGH - 4); // digitalWrite() takes 4us
digitalWrite(IRPin, LOW);
delayMicroseconds(ACTIVE_LOW - 4); // digitalWrite() takes 4us
}
}
void sendNEC(unsigned long data)
{
// Leader code
mark(NEC_HDR_MARK);
delayMicroseconds(NEC_HDR_SPACE);
for (int i = 0; i < NEC_BITS; i++)
{
mark(NEC_BIT_MARK);
if (data & TOPBIT)
delayMicroseconds(NEC_ONE_SPACE);
else
delayMicroseconds(NEC_ZERO_SPACE);
data <<=1;
}
// stop bit
mark(NEC_BIT_MARK);
}
Которого и прошу с пристрастием посмотреть схему и скетч.
Сильно тормозит работу TVout от которого видимо придется отказаться.
Прошу помощи.
Подключил к ардуино резистивные кнопки руля по такой схеме
http://big-e.ru/images/4х4_arduino/wheel_but.jpg
(полная схема постом выше)
При этом ардуино была запитана от источника питания от бортсети и компа через USB.
При отладке нажимал кнопки руля и их значения выводил в Serial.
Потом прописал в скетче нужные значения с допусками.
(При этом обратил внимание, что одна из кнопок руля при нажатии выводит значение 0, чего быть не должно, так как стоит резистор. Не нажатые кнопки= 667 из 1023).
Скетч работал нормально.
Отключив ардуино от USB кнопки перестали работать нормально, перепутались, сместились (как будто сопротивление от них другое стало приходить).
Новые значения не могу посмотреть, комп-то отключен.
Возможно где-то нужно землю соединить Arduino и бортсети авто?
Проблема том что при подключении от USB питание будет примерно 4,5в, а при питании от 12в плюс минус 5вЦитата:
Отключив ардуино от USB кнопки перестали работать нормально, перепутались, сместились (как будто сопротивление от них другое стало приходить).
Ну и соответственно все показания сьедут
Так что советую серьезно уделить внимание питанию ардуины
Спасибо.
Модуль запитан от источника питания 12В->7В.
Естественно борт сеть авто 11-14В.
Куда вот только значения кнопок выводить, чтобы визуально знать какое значение при нажатии.
Как вариант можно приспособить крошечный OLED дисплей и подключить его по I2C
Что-то я не правильно сделал.
Почему-то при подключении внешнего питания, при нажатии на некоторые кнопки (82ом и 164ом) выдается отрицательное напряжение (смотрел по мультиметру).
Раньше на arduino mega это работало.
Сейчас на seeeduino mega - нет.
Замерил все одинаково и обвязка в том числе.
Резистор 2к, кондер 153 в обоих случаях.
Вот только почему-то на arduino mega сопротивление между пинами + и - 0,95к, а на seeeduino mega - 0,4к(мерил при выкл. контроллерах) может в этом дело?
Откуда там взятся отрицательному напряжению?
Так мультиметр показывал.
Одна из кнопок руля при нажатии выводит значение 0, чего быть не должно (должно быть ~65 из 1023, так как стоит резистор 82ом. Не нажатые кнопки= 667 из 1023
Ума не приложу, где ошибся.
Может в этом причина и резистор 2к, заменить на какой-то другой номинал?Цитата:
на arduino mega сопротивление между пинами + и - 0,95к, а на seeeduino mega - 0,4к