подключение анемометра RM Young 05103 к Ардуино.

d00m
Offline
Зарегистрирован: 21.02.2013

выношу свой вопрос в отдельную тему.

изначально он был тут:

http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina2...

ниже дублирую текст и добавляю новые данные.

решил апнуть тему, так как возникли проблемы...

постараюсь вкратце напомнить о моей системе, хотя текста наверняка будет много.. спасибо всем, кто дочитает до конца))
итак, есть устройство - анемометр RM Young - https://s.campbellsci.com/documents/ca/manuals/05103l_man.pdf
на 4 стр. указана схема его подключения к штатному устройству считывания данных.
опустим историю про ситуацию которая привела меня к необходимости подключения таких анемомтеров вместо штатного даталогера к Arduino.
так как этот анемометр на выходе выдает данные по "протоколу" 4-20mA - то использую датчик  INA219.
итак, анемометр может выдавать 4 - 20mA, то скорость ветра по формуле из дока может быть 0 - 100 m/s.
конечно же таких ветров у нас не бывает. и даже 50мс - это уже ураган.
довольно долго я разбирался как его подключить и в итоге у меня получилось - почти два года назад.
в процессе разбирательств пришлось поменять резистор-шунт на плате с R100 - 0.1 ohm на 10 ohm.
резистор обычный 0.25Вт, погрешность 1%. 
цветовая маркировка: коричневый, черный, черный, золотой, коричневый.
 
код в setup () использую такой:
 
01 ina219_WS.configure(1, 3, 12, 12, 7);
02 //              32v, 320mv  
03  
04 ina219_WD.configure(1, 3, 12, 12, 7);
05 //              32v, 320mv 
06  
07 ina219_WS.calibrate(10, 0.32, 32, 0.02);
08               // R_шунта, напряж_шунта, макcнапряж, максток
09               // 10ohm, 320mv, 32v, 20mA
10  
11 ina219_WD.calibrate(10, 0.32, 32, 0.02);
12               // R_шунта, напряж_шунта, макcнапряж, максток
13               // 10ohm, 320mv, 32v, 20mA

сейчас уже точно не вспомню, почему такие параметры, но когда все это собиралось вместе - прошерстил все форумы, старался изучить даташит, советовался с другими и вродебы таки параметры должны быть верные.

тем более, что все эти два года девайсы работают исправно - скорость ветра и направление измеряется.
есть только одна проблема - максимальная скорость ветра.
исходя из информации в доке на анемометр - он передает на выход ток - от 4 до 20мА и значит что даже если на выходе появилось 10мА - это уже 50м/c
и вот такие вот значения не часто, но все таки приходят на ардуину. 
например вот такой лог (верхняя строка - самое новое значение):
 
01 date_time:WS_mA_mean:WS_mean(m/s):WS_mA_max:WS_max(m/s)
02 08-12-21_12-00-24: 4.632: 3.952: 6.190: 13.689:    
03 08-12-21_11-30-23: 5.609: 10.054: 8.879: 30.495:   
04 08-12-21_11-00-26: 6.195: 13.721: 10.209: 38.807   
05 08-12-21_10-30-24: 6.559: 15.991: 10.750: 42.190   
06 08-12-21_10-00-26: 7.563: 22.271: 11.327: 45.794   
07 08-12-21_09-30-23: 7.137: 19.608: 10.444: 40.276   
08 08-12-21_09-00-23: 7.797: 23.730: 11.144: 44.650   
09 08-12-21_08-30-25: 7.599: 22.491: 11.110: 44.437   
10 08-12-21_08-10-21: 8.467: 27.918: 11.932: 49.576   
11 08-12-21_07-30-26: 9.073: 31.709: 12.015: 50.095   
12 08-12-21_07-00-23: 8.384: 27.397: 12.543: 53.396   
13 08-12-21_06-30-23: 8.396: 27.478: 12.686: 54.288   
14 08-12-21_06-00-23: 7.359: 20.995: 12.440: 52.749   
15 08-12-21_05-30-23: 5.687: 10.545: 11.693: 48.084   
16 08-12-21_05-00-23: 6.188: 13.675: 10.034: 37.714

конкретно этот анемометр установлен на высоте 2200м. 8 декабря был сильный ветер. так что и средние значения довольно большие - видно, что с 5 утра дуло больше 10мс и нередко превышало даже 20мс.

это норм для такого места. но вот максимальные значения удручают.. явно я чтото делаю не так.

функция которая считает скорость ветра:
 
01 float check_WS() {
02  
03   Data_ina219_WS = ina219_WS.shuntCurrent() * 1000; // A * 1000 -> mA
04  
05   // m/s = ( 6.250 * mA ) - 25
06   WS = (6.250 * (Data_ina219_WS)) - 25;
07  
08   Serial.print( Data_ina219_WS, 3 ); Serial.print(F(" mA; ")); Serial.print( WS, 2 ); Serial.print(F(" m/s : "));
09   
10   lcd.setCursor(0, 0);
11   lcd.print(Data_ina219_WS, 3); lcd.print(": "); lcd.print(WS, 2); lcd.print(" m/s ");
12   /**/
13  
14   return Data_ina219_WS;
15 }

она вызывается в loop():

01 WS_curr = check_WS();
02  if ( WS_max < WS_curr ) { WS_max = WS_curr; }
03  WS_summ = WS_summ + WS_curr;
04  
05  /*
06  Serial.print("WS_curr: "); Serial.println(WS_curr, 3);
07  Serial.print("WS_max: "); Serial.println(WS_max, 3);
08  Serial.print("WS_summ: "); Serial.println(WS_summ, 3);
09  /**/
10  
11  WD_curr = check_WD();
12  WD_summ = WD_summ + WD_curr;
13  
14  i++;
15  WS_mean = WS_summ / i;
16  WD_mean = WD_summ / i;

и далее раз в полчаса с этой ардуины данные снимаются по радиоканалу - передается struct srv_wsd_data:

1 srv_wsd_data.WS_mA_mean = WS_mean;
2 srv_wsd_data.WS_mA_max = WS_max;       
3 srv_wsd_data.WD_mA_mean = WD_mean;       
4 i = 0;
5 WS_mean = 0;
6 WS_max = 0;
7 WS_summ = 0;
8 WD_mean = 0;
9 WD_summ = 0;

после передачи все переменные обнуляются.

то есть код в течении получаса суммирует значения с датчиков скорости и направления, инкрементирует счетчик "i" и вычисляет среднее арифметическое.
помимо этого, в отдельную переменную WS_max сохраняется максимальное значение с датчика за этот период.
такая вот логика, возможно и наверняка что-то можно поменять, но должен сказать, что среднее значение ветра система показывает +- верно.
направление ветра - тоже верно. это позволяет мне думать, что может и не идеально, но все работает.
 
Но вот откуда могут браться такие завышенные значения когда система говорит, что максимальная скорость ветра бывает более 30мс - я не могу представить..
вопросы у меня такие:
- возможно, что я неправильно сконфигурировал INA219? я почемуто грешу на вот это:
  ina219_WS.configure(1, 3, 12, 12, 7); 
 
  не уверен, что тут все правильно..
 
- может влиять на неверное измерение тот обычный резистор на 10ом? я так понимаю там должен быть шунт, а это не совсем обычный резистор..
 
очень хочу разобраться с этой проблемой и-или понять, что там не так.
готов компенсировать время и желание помочь, особенно если это приведет к положительным результатам)
 
ниже - схема подключения, которая сейчас используется.
красный прямоугольник с крестом означает, что этот блок в моей схеме отсутствует - подключаюсь напрямую к 4м контактам на плате анемометра.
d00m
Offline
Зарегистрирован: 21.02.2013

чтото схема очень маленькая. добавлю отдельный участок.

DetSimen
DetSimen аватар
Offline
Зарегистрирован: 25.01.2017

Ужос.  Это вот всё всего лишь для одного ананиметра?

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

и где у тебя резистор в минусе INA219, для расчета которого даже формула  приведена?

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

высота 2200, это что? Кисловодск?

d00m
Offline
Зарегистрирован: 21.02.2013

ua6em пишет:

и где у тебя резистор в минусе INA219, для расчета которого даже формула  приведена?

два года назад, мне посоветовали не ставить туда ничего (причину уже не припомню), и оно както завелось без  этого резистора - при 0 показывает 4мА на двух датчиках.

датчик направления в таком виде работает нормально - от 0 до 360. это позволило предположить, что и по скорости не будет проблем.

 

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

d00m пишет:

ua6em пишет:

и где у тебя резистор в минусе INA219, для расчета которого даже формула  приведена?

два года назад, мне посоветовали не ставить туда ничего (причину уже не припомню), и оно както завелось без  этого резистора - при 0 показывает 4мА на двух датчиках.

датчик направления в таком виде работает нормально - от 0 до 360. это позволило предположить, что и по скорости не будет проблем.

тебе повезло, что заветный белый дым не пошёл, а он на нём работает...сейчас в качестве нагрузки 10 Ом, что очень мало

d00m
Offline
Зарегистрирован: 21.02.2013

добавлю код:

#include <Arduino.h>

#define SERVER_ADDRESS 101

// payload data >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
typedef struct {

  int           srvId; 
  boolean       start;
  int           lastRSSI;
  float         WS_mA_mean;
  float         WS_mA_max;  
  float         WD_mA_mean;
  float         ts_int;

} Payload;
Payload srv_wsd_data;

// payload data <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

// INA219 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
#include <INA219.h>

//WS - wind speed
INA219 ina219_WS;
volatile float Data_ina219_WS = 0;
volatile float WS = 0;
volatile float WS_curr = 0;
volatile float WS_summ = 0;
volatile float WS_max = 0;
volatile float WS_mean = 0;

// measured on 0 m/s connecting to a sensor
// 4.037
// 4 - 4.037 == -0.037

float WS_mod = -0.037;
float check_WS();

//WD - wind directions
INA219 ina219_WD;
volatile float Data_ina219_WD = 0;
volatile float WD = 0;
volatile float WD_curr = 0;
volatile float WD_summ = 0;
volatile float WD_mean = 0;

// measured on 360 grad connecting to a sensor
// 4.1
// 4 - 4.1 == -0.1
float WD_mod = -0.1;
float check_WD();

// INA219 <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

//LCD 16x2 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
#include <LiquidCrystal_I2C.h>
LiquidCrystal_I2C lcd(0x27, 16, 2);
//LCD 16x2 <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

// radio >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
// rf95_reliable_datagram_server.pde
// -*- mode: C++ -*-
// Example sketch showing how to create a simple addressed, reliable messaging server
// with the RHReliableDatagram class, using the RH_RF95 driver to control a RF95 radio.
// It is designed to work with the other example rf95_reliable_datagram_client
// Tested with Anarduino MiniWirelessLoRa
#include <RHReliableDatagram.h>
#include <RH_RF95.h>
#include <SPI.h>

// Singleton instance of the radio driver
RH_RF95 driver;
// Class to manage message delivery and receipt, using the driver declared above
RHReliableDatagram manager(driver, SERVER_ADDRESS);
// radio <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

void setup()
{

//LCD
  lcd.init();
  lcd.backlight();
  lcd.setCursor(0, 0);
  lcd.print("WSD 0.1, INA219");
// 

//INA219 
  ina219_WS.begin(0x40);
  ina219_WD.begin(0x41);

  ina219_WS.configure(1, 3, 12, 12, 7); 
  //              32v, 320mv   

  ina219_WD.configure(1, 3, 12, 12, 7); 
  //              32v, 320mv  

  ina219_WS.calibrate(10, 0.32, 32, 0.02); 
                // R_шунта, напряж_шунта, макcнапряж, максток
                // 10ohm, 320mv, 32v, 20mA

  ina219_WD.calibrate(10, 0.32, 32, 0.02); 
                // R_шунта, напряж_шунта, макcнапряж, максток
                // 10ohm, 320mv, 32v, 20mA

//R100 - 0.1 ohm
//R010 - 0.01 ohm

    // 4 - 20 mA
    // between 4 and 20 is 16 mA
    // 0 - 100 m/s 

    //wind speed in m/s == (6.250 * X mA) - 25
    // so 1 m/s in mA is: 
    // 1 m/s == 26-25  =>  26 == 6.25 * X  =>  X == 26/6.25 == 4.16

    // 1 m/s == 0.16 mA == 0.00016 A == 0.04v (with 250 Ohm) == 40mv
    // 0.1 m/s == 0.016 mA == 0.004v      

    Serial.begin(9600);

//RADIO

    if (!manager.init())
        Serial.println(F(">>>>> server init failed"));
  // Defaults after init are 434.0MHz, 13dBm, Bw = 125 kHz, Cr = 4/5, Sf = 128chips/symbol, CRC on
    else {
            Serial.print(F(">>>>> server #"));
            Serial.print(SERVER_ADDRESS);
    }
}//end setup()

// Dont put this on the stack:
uint8_t buf[RH_RF95_MAX_MESSAGE_LEN]; //for receive request from client.

unsigned long i = 0; //
unsigned long k = 0; //

//##############################################################################################################################################
void loop() {

  //Serial.println(srv_data.start);
  srv_wsd_data.srvId = SERVER_ADDRESS;

  WS_curr = check_WS() + WS_mod;
  if ( WS_max < WS_curr ) { 
    WS_max = WS_curr; 

  }
  WS_summ = WS_summ + WS_curr;

  /*
  Serial.print("WS_curr: "); Serial.println(WS_curr, 3);
  Serial.print("WS_max: "); Serial.println(WS_max, 3);
  Serial.print("WS_summ: "); Serial.println(WS_summ, 3);
  /**/

  WD_curr = check_WD() + WD_mod;
  WD_summ = WD_summ + WD_curr;

  i++;
  WS_mean = WS_summ / i;
  WD_mean = WD_summ / i;

  /*
  Serial.print(F("i: ")); Serial.println(i);
  Serial.print("WS_mean: "); Serial.println(WS_mean, 3);
  /**/

// start test

  if (true) { //wsd101 powered from ext power source    
      if (manager.waitAvailableTimeout(600)) { // STEP_0: wait (3x200)600ms and check if client is sending requests
    // Wait for a message addressed to us from the client
      uint8_t len = sizeof(buf);
      uint8_t from;
// *********************************************************************************************************
      if (manager.recvfromAck(buf, &len, &from)) { // STEP_1_end: receive data request from client: (>) and send ACK back
       
        // prepare arithmetic mean of WS and WD
        srv_wsd_data.WS_mA_mean = WS_mean;
        srv_wsd_data.WS_mA_max = WS_max;        
        srv_wsd_data.WD_mA_mean = WD_mean;        
        i = 0;
        WS_mean = 0;
        WS_max = 0;
        WS_summ = 0;
        WD_mean = 0;
        WD_summ = 0;

// *********************************************************************************************************
        if (manager.sendtoWait((uint8_t*)&srv_wsd_data, sizeof(srv_wsd_data), from)) { // STEP_2_start: send all data to client and wait for ACK
        // Blocks until an ACK is received or all retries are exhausted (ie up to retries*timeout milliseconds) defaults: 3x200

          if (srv_wsd_data.start) { srv_wsd_data.start = false; }
          memset(&srv_wsd_data, 0, sizeof(srv_wsd_data)); //clear srv_wsd_data
          srv_wsd_data.lastRSSI = driver.lastRssi(); // write last session RSSI
    
        }
// *********************************************************************************************************

      }// end if (manager.recvfromAck) - received data request from client => send ACK back => start collect and send sensors data

    }//end if (manager.waitAvailableTimeout) - no requests from Client => go sleep
  }
}//end loop()

// monitoring WS and WD >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
float check_WS() {

  Data_ina219_WS = ina219_WS.shuntCurrent() * 1000; // A * 1000 -> mA

  // m/s = ( 6.250 * mA ) - 25
  WS = (6.250 * (Data_ina219_WS + WS_mod)) - 25;

  Serial.print( Data_ina219_WS, 3 ); Serial.print(F(" mA; ")); Serial.print( WS, 2 ); Serial.print(F(" m/s : ")); 
  
  lcd.setCursor(0, 0);
  lcd.print(Data_ina219_WS, 3); lcd.print(": "); lcd.print(WS, 2); lcd.print(" m/s ");
  /**/

  return Data_ina219_WS;
}  
// <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

float check_WD() {

  Data_ina219_WD = ina219_WD.shuntCurrent() * 1000; // A * 1000 -> mA
  
  // DEGREES = ( 22.5 * mA ) - 90
  WD = (22.5 * (Data_ina219_WD + WD_mod)) - 90;

  Serial.print( Data_ina219_WD, 3 ); Serial.print(F(" mA; ")); Serial.print( WD, 2 ); Serial.println((char)176); 
  
  lcd.setCursor(0, 1);
  lcd.print(Data_ina219_WD, 3); lcd.print(": "); lcd.print(WD, 2); lcd.print((char)223);  lcd.print(" ");
  /**/

  return Data_ina219_WD;
}  
// <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

 

d00m
Offline
Зарегистрирован: 21.02.2013

ua6em пишет:

..сейчас в качестве нагрузки 10 Ом

я так и говорил в другом топике.

мало или нет - мне сложно понять.

все работает, за исключением проблемы в первом сообщении.

если посоветуете, что поменять в схеме - проверю и отпишусь.

b707
Offline
Зарегистрирован: 26.05.2017

d00m пишет:

добавлю код:

еще дайте ссылку на использованную библиотеку INA219. а то их несколько

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

d00m пишет:

ua6em пишет:

..сейчас в качестве нагрузки 10 Ом

я так и говорил в другом топике.

мало или нет - мне сложно понять.

все работает, за исключением проблемы в первом сообщении.

если посоветуете, что поменять в схеме - проверю и отпишусь.

в минус Vin воткнуть 560 Ом

rkit
Offline
Зарегистрирован: 23.11.2016

Никакого, мать его, дыма от 20мА не будет.

d00m
Offline
Зарегистрирован: 21.02.2013

b707 пишет:

d00m пишет:

добавлю код:

еще дайте ссылку на использованную библиотеку INA219. а то их несколько

https://github.com/johngineer/ArduinoINA219

да, действительно их несколько разных.

вроде тогда выбрал самую новую

d00m
Offline
Зарегистрирован: 21.02.2013

ua6em пишет:

в минус Vin воткнуть 560 Ом

это может помочь с моей основной проблемой? учитывая, что и без него все "работает".

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

d00m пишет:

ua6em пишет:

в минус Vin воткнуть 560 Ом

это может помочь с моей основной проблемой? учитывая, что и без него все "работает".

я старый КИПовец 8-го разряда, сначала всё делается, как прописано в документации, только после этого ищут проблему, если она есть )))

d00m
Offline
Зарегистрирован: 21.02.2013

ua6em пишет:

d00m пишет:

ua6em пишет:

в минус Vin воткнуть 560 Ом

это может помочь с моей основной проблемой? учитывая, что и без него все "работает".

я старый КИПовец 8-го разряда, сначала всё делается, как прописано в документации, только после этого ищут проблему, если она есть )))

поищу резюки такие.. проверю дома - если заведется, потом добавлю на полевом приборе.

фигня в том, что дома есть анемометр на котором работает только скорость ветра, направление "сгорело" после грозы.. чтото на плате анемометра вышло из строя и теперь по каналу направления выдает чуть больше 20мА всегда, как то так.. но это уже другая история.

спасибо за совет.

d00m
Offline
Зарегистрирован: 21.02.2013

ua6em пишет:

в минус Vin воткнуть 560 Ом

так?

Pyotr
Offline
Зарегистрирован: 12.03.2014

d00m, а что, направление ветра правильно показывает с таким усреднением?

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

Да!

d00m
Offline
Зарегистрирован: 21.02.2013

Pyotr пишет:

d00m, а что, направление ветра правильно показывает с таким усреднением?

да. причем довольно точно.

Pyotr
Offline
Зарегистрирован: 12.03.2014

d00m пишет:

Pyotr пишет:

d00m, а что, направление ветра правильно показывает с таким усреднением?

да. причем довольно точно.

Тоесть, при двух соседних значениях 350 и 10 градусов среднее будет верным ? Или я что-то упустил?

d00m
Offline
Зарегистрирован: 21.02.2013

Pyotr пишет:

Тоесть, при двух соседних значениях 350 и 10 градусов среднее будет верным ? Или я что-то упустил?

вообще только два значения не приедут - данные аккумулируются по 30 минут. за это время цикл выполнится более кол-во раз.. 

но кстати, это вероятно не правильно так считать. я не проверял при таких условиях, но похоже нужно по другому направление "усреднять". спасибо за хинт.

на точке проверяю просто - подключаю к прибору экран и смотрю что там пишется. при этом значения не усредняются, а выводятся такие как есть. а вот при передаче данных по радио - усредняются. тут и есть ошибка)

wdrakula
wdrakula аватар
Offline
Зарегистрирован: 15.03.2016

ua6em пишет:

d00m пишет:

ua6em пишет:

..сейчас в качестве нагрузки 10 Ом

я так и говорил в другом топике.

мало или нет - мне сложно понять.

все работает, за исключением проблемы в первом сообщении.

если посоветуете, что поменять в схеме - проверю и отпишусь.

в минус Vin воткнуть 560 Ом

Сережа! Ты читал все-таки ГОСТ 26.011-80 и ДШ на этот анемометр???

Написано, МЛЕАТЬ, - MAX (Ucc-12/0/02) Ом! Понимаешь, MAX означает НЕ БОЛЬШЕ, мля, 600Ом. Нет нижнего ограничения в токовой петле. И в ДШ тоже нет. Прекращай новичку моск ипать, если свой в 4-ом классе на жувачку выменял!

wdrakula
wdrakula аватар
Offline
Зарегистрирован: 15.03.2016

ТС, просто забей на выбросы. Мало-ли, помехи ловит какие-то? Есть статистическая обработка экспериментальных данных. Помнишь некое среднее скользящее постоянно, помнишь среднеквадратичное отклонение, и все данные, которые отклоняются более чем в (3,4,5 N,K или Омикрон ;)) раз) - просто игноришь совсем. Этому в любом вузе на кратком курсе по обработке экспериментальных данных учат. Меня в СССР учили даже в МГУ, хоть мы там вообще чистые теоретики все были.

b707
Offline
Зарегистрирован: 26.05.2017

Pyotr, ну вообще, "среднее значение направления " за более-менее длительный период - это что-то навроде "средней температуры по больнице" - величина, имеющая крайне низкий практический смысл. Кроме того, если посмотреть, как оно считается в коде - у меня возникает подозрение, что ТС эти данные очень долго подгонял под "правильные" путем добавления каких-то левых коэффициентов в формулу. Например величина WD_mod вычитается из каждого значения дважды - один раз внутри процедуры WD_check(). а второй - перед усреднением. То же самое относится и к WS_mod. Кроме этого в формулах есть какие-то безымянные константы...

Короче , я бы бы признателен автору, если ьы он пояснил. откуда взялись эти формулы. Я как-то не особенно им доверяю :)

 

d00m
Offline
Зарегистрирован: 21.02.2013

b707 пишет:

... возникает подозрение, что ТС эти данные очень долго подгонял под "правильные" путем добавления каких-то левых коэффициентов в формулу.

Например величина WD_mod вычитается из каждого значения дважды - один раз внутри процедуры WD_check(). а второй - перед усреднением. То же самое относится и к WS_mod. Кроме этого в формулах есть какие-то безымянные константы...

W*_mod - это значение с датчика на нулевой отметке измерения, когда датчик ДОЛЖЕН видеть только 4mA. то есть WS_mod для значения при полном штиле, WD_mod - для 0 градусов.

в реальности на нулевых отметках прибор показывает не точно 4mA, а немного меньше или больше. вот эту разницу я специально измеряю, остановив рукой пропеллер и выставив флюгер на север. при этом - во время этого измерения - в коде эти модификаторы РАВНЫ НУЛЮ!

таким образом, если при 0м/с я вижу на ЖК дисплее 4.05, я понимаю, что (4 - 4.05 == -0.05) и чтобы это привести к 4 надо прибавить -0.05. или, если я вижу 3.998, то (4 - 3.998 == 0.002). это и будет значение модификатора WS_mod. и тут я просто НАДЕЮСЬ, что эта погрешность будет линейной. проверить пока это не могу.

для каждого моего прибора эти модификаторы разные - видимо дают погрешность и сами INA219 и качество сборки и чтото еще. я просто обнаружил, что есть такая погрешность и решил ее компенсировать в коде для каждого прибора. 

ПОСЛЕ того как я вычислил значения модификаторов - я заношу их в код, собираю прошивку и заливаю на прибор. Да, вот так криво и не очень оптимально, но пока вот так вот.

далее, про "вычитание дважды" - в обеих функциях есть вывод на ЖК дисплей 1602. выводится там отдельная переменная WS или WD, и чтобы ее посчитать с учетом модификатора - я прибавляю модификатор датчика. и на экране я вижу текущее значение датчиков. но на выход функция отдает не эту модифицированную переменную, а сырое значение  с датчика - оно модифицируется в другой части кода, там где вычисляется среднее.
конечно можно делать модификацию только один раз. но пока сделано вот так. явно, не это не приводит к моей текущей проблеме.

безымянных констант учавствующих в вычислениях вроде не замечено)

это просто вывод значка градусов:

Serial.println((char)176); 
 
d00m
Offline
Зарегистрирован: 21.02.2013

wdrakula пишет:

ТС, просто забей на выбросы. Мало-ли, помехи ловит какие-то? Есть статистическая обработка экспериментальных данных. Помнишь некое среднее скользящее постоянно, помнишь среднеквадратичное отклонение, и все данные, которые отклоняются более чем в (3,4,5 N,K или Омикрон ;)) раз) - просто игноришь совсем. Этому в любом вузе на кратком курсе по обработке экспериментальных данных учат. Меня в СССР учили даже в МГУ, хоть мы там вообще чистые теоретики все были.

кажется я понимаю о чем вы...  сам "примат" в прошлом..

но думаю, что просто отбрасывать такие значения из выборки - не совсем верно.. они же приходят с датчика, когда ветер действительно усиливается и это точно не помеха. были бы помехи - они появлялись бы на всем периоде измерения..

тут вот

http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina2...

интересную мысль товарищ излагает, как мне кажется.

но я не так компетентен, чтобы понять ее

b707
Offline
Зарегистрирован: 26.05.2017

"безымянные константы", это например 6.25  в начале формулы и 25 в конце:

WS = (6.250 * (Data_ina219_WS + WS_mod)) - 25;

а насчет "WS_mod в коде РАВЕН НУЛЮ" я что-то не понял, вот строка 37:

float WS_mod = -0.037;

 

А ваш рассказ про то, что датчик при физическом нуле не дает инструментального нуля - вообще-то и называется "подгонка" и такие ошибки устраняются доработкой схемы, а не дописыванием левых членов в формулу.

 

d00m
Offline
Зарегистрирован: 21.02.2013

b707 пишет:

"безымянные константы", это например 6.25  в начале формулы и 25 в конце:

WS = (6.250 * (Data_ina219_WS + WS_mod)) - 25;

а насчет "WS_mod в коде РАВЕН НУЛЮ" я что-то не понял, вот строка 37:

float WS_mod = -0.037;

 

А ваш рассказ про то, что датчик при физическом нуле не дает инструментального нуля - вообще-то и называется "подгонка" и такие ошибки устраняются доработкой схемы, а не дописыванием левых членов в формулу.

 

6.25 и 25 - это из формулы вычисления скорости из документации на анемометр. 4 страница.

все верно - WS_mod - это уже после вычисления этого модификатора. значение добавлено в код для "подгонки".

возможно, что погрешность самого датчика INA219 + резистор на 10Ом который я туда сам припаял вместо штатного не позволят устранить такие ошибки и подгонка все же будет нужна. это еще наверное называется - калибровка.

d00m
Offline
Зарегистрирован: 21.02.2013

походу мнения разделились - одни говорят надо ставить эти резисторы, другие - не надо..

есть вообще предложение отказаться от INA219 и снимать данные на аналоговом пине ардуины..

но главное - никто явно не говорит, что моя текущая схема и код - совершенно неправильны.

я то думал, что там есть какойто очевидный баг, и опытные люди его сразу заметят

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

конечно есть баг, два резистора не поставил, тебе и 182 об этом сказал

rkit
Offline
Зарегистрирован: 23.11.2016

d00m пишет:

походу мнения разделились - одни говорят надо ставить эти резисторы, другие - не надо..

есть вообще предложение отказаться от INA219 и снимать данные на аналоговом пине ардуины..

но главное - никто явно не говорит, что моя текущая схема и код - совершенно неправильны.

я то думал, что там есть какойто очевидный баг, и опытные люди его сразу заметят

Вспомни самое первое, что я тебе сказал, солнце мое.

d00m
Offline
Зарегистрирован: 21.02.2013

я вообще мало что понял с того, что рассказал 182-й..  

так. у меня есть резюки на 300 и на 270 ом. похоже придется делать 570 вместо 560. надеюсь это Ок

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

d00m пишет:

я вообще мало что понял с того, что рассказал 182-й..  

так. у меня есть резюки на 300 и на 270 ом. похоже придется делать 570 вместо 560. надеюсь это Ок

...мыши жрали кактус, кололись, но продолжали жрать кактус...
он сказал, что ты подключил INA219 с нарушением даташита, к выводу Vin- должна быть подключена
нагрузка, а у тебя её нет, ты хоть какой -нибудь резистор подключи, стандартный ряд резисторов, 510, 560, 620

Pyotr
Offline
Зарегистрирован: 12.03.2014

b707 пишет:

Pyotr, ну вообще, "среднее значение направления " за более-менее длительный период - это что-то навроде "средней температуры по больнице" - величина, имеющая крайне низкий практический смысл. 

У меня вот флюгер на высоте 5.5-6 м где-то. Смотрю иногда за ним - как его мотает. Постоянно дергается из стороны в сторону. До полуоборота доходит амплитуда. Иногда вообще оборот сделает. Но всегда визуально можно видеть преимущественное направление ветра. Вот обработать данные за 1-3 мин для меня проблема. Чтоб по простому без синусов, косинусов. Пока могу усреднять только по два значения.

nik182
Offline
Зарегистрирован: 04.05.2015

Я писал исходя из собственного опыта. Ina у меня голая. Я её сам распаиваю. Платы как у ТС у меня нет. Поэтому я не знаю что там на плате установлено, какая схема. Возможно все что требует мануал там есть. В любом случае резистор нагрузка датчика, даже только 10 ом для диф входа ina должен стоять одним концом на землю. Но чисто из схемотехнических соображений, чтобы входной ОУ ina работал точно в линейном режиме, поставил бы нагрузочный резистор 270 ом на землю и за ним 10 Ом шунта для ina. Такая схема исключит хардверные выбросы показаний.
Ну и повторю. При такой схеме (270 + 10 Ом) с верхней точки 10 Ом резистора можно подать через резистор 1 кОм на вход А0. Параллельно входу на землю поставить или керамику 1 мкФ или электролит 1 мкФ и керамику 0.1 мкФ. Это ни как не повлияет на ina и позволит сравнивать измерения по двум каналам ina и АЦП ардуины. Тоже самое можно сделать для направления и подать на А1.

Pyotr
Offline
Зарегистрирован: 12.03.2014

Для считывания показаний, как уже говорили, достаточно 2 резистора по R=U/I=1.1B/0.02A=55 Ом. Берем ближайший меньший номинал 51 Ом. Опорное 1.1 В на МК. Все!

В даташите  направление ветра = (22.5 х мА) - 90 это чтоб запутать))

Почему не написать направление = 22.5 х (мА-4)

22.5 град/мА = 360 / (20-4) это характеристика флюгера 

d00m
Offline
Зарегистрирован: 21.02.2013

nik182 пишет:
Я писал исходя из собственного опыта. Ina у меня голая. Я её сам распаиваю. Платы как у ТС у меня нет. Поэтому я не знаю что там на плате установлено, какая схема. Возможно все что требует мануал там есть. В любом случае резистор нагрузка датчика, даже только 10 ом для диф входа ina должен стоять одним концом на землю. Но чисто из схемотехнических соображений, чтобы входной ОУ ina работал точно в линейном режиме, поставил бы нагрузочный резистор 270 ом на землю и за ним 10 Ом шунта для ina. Такая схема исключит хардверные выбросы показаний. Ну и повторю. При такой схеме (270 + 10 Ом) с верхней точки 10 Ом резистора можно подать через резистор 1 кОм на вход А0. Параллельно входу на землю поставить или керамику 1 мкФ или электролит 1 мкФ и керамику 0.1 мкФ. Это ни как не повлияет на ina и позволит сравнивать измерения по двум каналам ina и АЦП ардуины. Тоже самое можно сделать для направления и подать на А1.

я них не понимаю в этом - верний нижний, каким кто куда концом должен быть подключен.

можете ДОрисовать на схеме моей куда какой резистор припаять?

а пока только купил SMD резисторов пачку - там есть 560 - закончу работать и приделаю их и проверю.

mifar
Offline
Зарегистрирован: 07.04.2021

d00m пишет:

я них не понимаю в этом - верний нижний, каким кто куда концом должен быть подключен.

можете ДОрисовать на схеме моей куда какой резистор припаять?

а пока только купил SMD резисторов пачку - там есть 560 - закончу работать и приделаю их и проверю.

Там где у вас на схеме большой и жирный крест - вот туда и вставьте INA219 последовательно с резисторами

d00m
Offline
Зарегистрирован: 21.02.2013

mifar пишет:

Там где у вас на схеме большой и жирный крест - вот туда и вставьте INA219 последовательно с резисторами

я тут даже затрудняюсь, чтото внятное ответить..

там на схеме не только большой и жирный крест. 

mifar
Offline
Зарегистрирован: 07.04.2021

d00m
Offline
Зарегистрирован: 21.02.2013

премного благодарен. тут в 16 сообщении я нарисовал тоже самое) 

просто уже начились разговоры про какихто ДВА резистора в цепи одного датчика, и я не понял, что это значит - почему два и как их подключать

а вашу схему с одним резистором для датчика, как уже выше мне советовали - я конечно проверю.

nik182
Offline
Зарегистрирован: 04.05.2015

Как то так.  Если 10 Ом шунт стоит на плате, то его из схемы надо вырезать.

d00m
Offline
Зарегистрирован: 21.02.2013

nik182 пишет:

Как то так.  Если 10 Ом шунт стоит на плате, то его из схемы надо вырезать.

ого круто, спасибо! значит если на плате датчика уже стоит 10ом - то с вашей схемы его надо убрать и получится, что -Vin подключен через резистор 270 на землю?ок.

тогда получается, что схема такая же как в 16-м сообщении, только резисторы 270 ом вместо 560 ом.

и зачем то +Vin кроме того, что он подключен к выводу анемометра, еще подклюючен к аналоговому пину ардуины через 1к резистор..

nik182
Offline
Зарегистрирован: 04.05.2015

 Я ж писал, что одновременно оцифровывать по двум каналам, что понять кто глючит и откуда берутся выбросы на ina. Просто analogRead(A0) и analogRead(A1) добавить. формулу пересчёта в м/с я уже приводил в  http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina2...

Обидно однако. Я про это несколько раз там написал. 

d00m
Offline
Зарегистрирован: 21.02.2013

nik182 пишет:

 Я ж писал, что одновременно оцифровывать по двум каналам, что понять кто глючит и откуда берутся выбросы на ina. Просто analogRead(A0) и analogRead(A1) добавить. формулу пересчёта в м/с я уже приводил в  http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina2...

Обидно однако. Я про это несколько раз там написал. 

нене, про два измерения я понял еще там (за исключением как это подключить) - просто тогда подумал, что эти два подключения должны быть както изолированны друг от друга, а тут - они же одновременно подключены и к датчику и к аналог пину.. и показалось, что это как-то может мешать друг другу.. хотя если подумать - то с чего бы.. 

ок - приступаю к сборке. спасибо еще раз. разжевали и положили.

а кстати - так 270 или 560? вот где вопрос еще. почему так?

ua6em
ua6em аватар
Offline
Зарегистрирован: 17.08.2016

nik182 пишет:

 Я ж писал, что одновременно оцифровывать по двум каналам, что понять кто глючит и откуда берутся выбросы на ina. Просто analogRead(A0) и analogRead(A1) добавить. формулу пересчёта в м/с я уже приводил в  http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina2...

Обидно однако. Я про это несколько раз там написал. 

обидно знаете ли и, не тебе одному, такое впечатление, что ТС "то плакал,то смеялся, то скулил как будто ёж, он над нами измывался,...,что возьмёшь"...

nik182
Offline
Зарегистрирован: 04.05.2015

Влад подробно описал почему. 600 Ом это максимум - на нём при максимуме выходе будет половина напряжения питания. Но при этом на ina будут выбросы при пересечении 5 вольт. Я это подробно расписал  здесь http://arduino.ru/forum/apparatnye-voprosy/mini-obzor-monitora-toka-ina219-s-vykhodom-i2c?page=6#comment-634542

и здесь почему 300 Ом - у Вас 270 в наличии тоже подойдёт http://arduino.ru/forum/apparatnye-voprosy/podklyuchenie-anemometra-rm-young-05103-k-arduino#comment-634660

Опять обидно. Вы читаете что Вам пишут? Перечитываете Вашу тему?

 

d00m
Offline
Зарегистрирован: 21.02.2013

не сердитесь.. информацию про 600 и 270 - мне надо перечитывать много раз, чтобы хотябы примерно понять логику. конечно я читал это.. про 270 из второго линка понял только, что при такойм резисторе будет возможность одновременно и датчик и аналог пин использовать. а вот почему будет все так, как описано в первом линке - это чорная магия для меня.

пока же ищу способ раскрутить в домашних условиях анемометр, до 8-10мА.. пока только до 6 получается - шуриком обычным - зажал его на валу анемометра.. 6.100мА и около 13.1 м/с.. маловато для тестов, но если после добавления резисторов значения будут те же - значит иду по верному пути.

 

Pyotr
Offline
Зарегистрирован: 12.03.2014

d00m пишет:

просто уже начились разговоры про какихто ДВА резистора в цепи одного датчика, и я не понял, что это значит - почему два и как их подключать

Если это про мое сообщение, то один резистор 51 Ом вместо RL, который по цепи анемометра. На нем будет падать 0.2-1 В при токе 4-20 мА. Это напряжение измерять АЦП ардуино, без всяких ИНА.

Второй резистор 51 Ом вместо второго RL на схеме выше, который в цепи флюгера...

d00m
Offline
Зарегистрирован: 21.02.2013

пока такие результаты:

на моей старой схеме, без изменений - при включении, на канале WS (скорость), при 0m/s - программа показывает 3.999 - 4.000 mA.

почемуто раз в 2-3сек "мигает" значение..

после добавления в цепь резистора 270ом между -Vin датчика и GND - программа показывает 3.991-3.992 mA..

явно чтото поменялось) завтра придумаю, как раскрутить вал анемометра, чтобы было хотябы 8-9мА и доделаю цепь с аналог пином, для проверки значений..