Home › Forums › Elektronika / programavimas › E-Dviracio matuoklis
- This topic has 43 replies, 6 voices, and was last updated 10 years, 4 months ago by agniusm.
-
AuthorPosts
-
2013/07/21 at 16:01 #5940ArturasLParticipant
Patobulinau koda, plius dadejau animacijos. Video idet negaliu, nes pas mane labai letas internetas. Praktiskai beliko tik sensoriu apdorotus duomenis sudeti ir gatavas matuoklis. :) Gal kartais kas zinote, kaip U8GLIB atvaizduoti teksta plius kintamojo duomenis. Kai darau u8g.print(number + “km”); hieroglifus meto.
Naujas kodas:
//lcd
#include "U8glib.h"
U8GLIB_64128N u8g(13, 11, 10, 9, 8); //SPI Com: SCK = 13, MOSI = 11, CS = 10, A0 = 9
//lcd
int count;
int leftColumnLevel = 0;
int leftCenterNumber = 0;
int rightColumnLevel = 0;
//lcdLeftColumn function start
void lcdLeftColumn(void) {
leftColumnLevel = map(count, 0, 255, 50, 0);
//
u8g.drawBox(0,5,11,54);
if(leftColumnLevel != 0){
u8g.setColorIndex(0);
//min 1, max 50
u8g.drawBox(2,7,7,leftColumnLevel);
u8g.setColorIndex(1);
}
//
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(13, 12);
u8g.print("F");
//
u8g.setFont(u8g_font_5x8);
u8g.setPrintPos(13, 35);
u8g.print(count);
//
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(13, 59);
u8g.print("E");
}
//lcdLeftColumn function end
//lcdCenterColumn function start
void lcdCenterColumn(void) {
leftCenterNumber = constrain(count, 0, 99);
u8g.setFont(u8g_font_fub35n);
if(leftCenterNumber < 10){
u8g.setPrintPos(51, 50);
}
else{
u8g.setPrintPos(38, 50);
}
u8g.print(leftCenterNumber);
}
//lcdCenterColumn function end
//lcdRightColumn function start
void lcdRightColumn(void) {
//
u8g.drawFrame(117,5,11,54);
u8g.drawFrame(118,6,9,52);
rightColumnLevel = map(count, 0, 255, 7, 55);
//min 7 max 55
u8g.drawBox(119,rightColumnLevel,7,2);
//
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(110, 12);
u8g.print("D");
u8g.setFont(u8g_font_5x8);
u8g.setPrintPos(101, 35);
u8g.print(count);
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(110, 59);
u8g.print("R");
}
//lcdRightColumn function end
void setup(void) {
count = 0;
}
void loop(void) {
//lcd
u8g.firstPage();
do {
//lcdLeftColumn start
lcdLeftColumn();
//lcdLeftColumn end
//lcdCenterColumn start
lcdCenterColumn();
//lcdCenterColumn end
//lcdRightColumn start
lcdRightColumn();
//lcdRightColumn end
} while( u8g.nextPage() );
//lcd
if(count == 0){
delay(1000);
}
if(count == 255){
count = 0;
delay(1000);
}
else{
count = count + 1;
}
delay(100);
}
Atvaizdavimo greiti, milesekundemis, galima keisti su delay(100) (kodo gale). Ji istrinus greitis bus maksimalus.
2013/07/21 at 17:42 #5941agniusmParticipantNu tu cia ir greitas. As pasizaidziau su isdestymu truputi ir dar srifta pakeiciau, su jais daug zaidimo. Dabar atrodo taip:
https://www.youtube.com/watch?v=1_FYwjk_XvA
Quote:#include “U8glib.h”U8GLIB_64128N u8g(13, 11, 10, 9, 8);
//void draw(void)
//lcd
int count;
//lcdLeftColumn function start
void lcdTopColumn(void) {
//
u8g.drawFrame(7,0,114,9);
u8g.drawBox(9,2,42,5);
//
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(123, 8);
u8g.print(“F”);
u8g.setFont(u8g_font_5x8);
u8g.setPrintPos(0, 17);
u8g.print(“LIKO:”);
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(0, 25);
u8g.print(“23 5KM”);
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(0, 8);
u8g.print(“E”);
}
//lcdLeftColumn function end
//lcdCenterColumn function start
void lcdCenterColumn(void) {
//u8g.drawFrame(40,12,80,40);
//u8g.drawFrame(39,11,82,42);
u8g.drawLine(40,15,40,48);
u8g.drawLine(41,15,41,48);
u8g.setFont(arcade);
u8g.setFontPosCenter();
u8g.setPrintPos(44, 32);
if (count <10) {
u8g.print(“0”);
u8g.print(count);
}
else {
u8g.print(count);
}
}
//lcdCenterColumn function end
//lcdRightColumn function start
void lcdBottomColumn(void) {
//
u8g.drawFrame(7,55,114,9);
u8g.drawBox(58,57,10,5);
//
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(0, 63);
u8g.print(“+”);
u8g.setFont(u8g_font_5x8);
u8g.setPrintPos(0, 52);
u8g.print(“GALIA:”);
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(0, 45);
u8g.print(“0 75KW”);
u8g.setFont(u8g_font_6x10);
u8g.setPrintPos(123, 63);
u8g.print(“-“);
}
//lcdRightColumn function end
void setup(void) {
count = 10;
}
void loop(void) {
count = count + 1;
if(count == 99){
count = 1;
}
//lcd
u8g.firstPage();
do {
//lcdLeftColumn start
lcdTopColumn();
//lcdLeftColumn end
//lcdCenterColumn start
lcdCenterColumn();
//lcdCenterColumn end
//lcdRightColumn start
lcdBottomColumn();
//lcdRightColumn end
} while( u8g.nextPage() );
//lcd
//atvaizdavimo greitis ms
delay(100);
}
2013/07/21 at 18:00 #5942ArturasLParticipantVisai nieko tas didelis sriftas atrodo. Man patinka :)
Dabar brandinu ideja kaip pamatuoti kiekvienos celes itampa ir atvaizduoti ja ekranelyje. Netrukus bandysiu braizytis schema… Reiks dar forumieciu pagalbos…
2013/07/21 at 18:05 #5943agniusmParticipantBuvau rades parasyta programa kazkieno, ziuriu jau isemes, gerai, kad kopija pasidares buvau:)
Google Drive, parsisiuntimui
2013/07/21 at 19:45 #5944ArturasLParticipantAgniau, paziurejau schema kur pasarinai. Ten kiek supratau matuoja itampa su itampos dalikliu viso pako. Dar demesys krito i holo sensoriu. Kiek supratau is jo duomenys bus gaunami analoginiu budu :) Tai reiktu dabar tiksliai nustatyti kur ir kokie pas tave bus sensoriai ir kokiais duomenimis galima bus operuoti.
Nusiziurejau savo dviraciui holo sensoriu: http://www.ebay.com/itm/50A-100A-150A-200A-Bi-Uni-AC-DC-Current-Sensor-Module-arduino-compatible-/111040360152?pt=LH_DefaultDomain_0&var=&hash=item19da856ed8
Tik nezinau koki geriau butu imti Bi-Directional ar Uni-Directional ir ar apskritai vertas demesio sis sensorius?
Ir dar plokstes stilius kazkoks idomus. Gal (kas zinos ar) yra kazkokia programa ar standartai tokio stiliaus plokstei pasipaisyti?
2013/07/21 at 20:40 #5945agniusmParticipantAs taip pat ziurinejausi ta sensoriu ploksteje, bet veliau nuspredziau, kad labiau apsimoka pirkti 2 uz panasia kaina plikus :) Tiesa mano 100A. As galvoju, kad bi-directional veikia i abi kryptis, tai pakrovimui/regeneracijai ir iskrovimui?!
Linkas sensoriam.
Kiek maciau tai sitie dazniausiai naudojami, Allegro. Lino anksciau parduodamas BMS, FoundingPower taip par toki turi imontuota.
Del holo daviklio as ir nezinau, nelabai esu isigilines. O ka, kazkas prastai su analoginiu? Rezoliucija? Nepaspes ar kaip? Gal yra kaip geriau, ne pvz CA naudoja magneta ant laido kas man pasirode keista, bet tikriausiai su priezastim?
O kas del tos plokstes? Praktiskai ten nieko gi nera. As pasibraizau su SprintLayout ir kazkada Saruno rekomenduoti Elekon padaro.
As ir galvojau bendra itampa matuot itampos dalikliu, srove Allegro 100A sensoriumi o greiciui holo davikli pasijungt is valdiklio, tai dabar ir nzn.
2013/07/22 at 06:37 #5946jonasParticipantToks parašymas u8g.print(number + “km”);reiškia,kad nori suklyjuoti skirtingus kintamuosius. Tokiu atveju reikėtų išvesti number po to “km” su tam tikromis koordinatėmis. Jei nori išvesti viską išsyk, number konvertuok į string pridėk “km”ir išvesk. Tik bijau,kad ženklas + čia netiks.C kalboje yra tam tikros komandos eilutėms apdoroti.
Bidirectional Allegro daviklis ramybės būsenoje išėjime turi VCC/2 įtanpą. Kai vienakryptis turi 0. Tokiu atveju ADC rezoliucija mažėja dvigubai, į kiekvieną pusę lieka po 512 lygių.
2013/07/22 at 07:03 #5947ŠarūnasKeymasterTokioje aplikacijoje reikėtų naudoti tik bidirectional sensorių.
Jei labai trūksta rezoliucijos, galima naudoti oversampling (skaityti google).
2013/07/22 at 19:13 #5948agniusmParticipantPabandziau pasijungti Allegro sensoriu prie paprasto 24V 100W varikliuko. Gaunu kazkoki skaiciu 526 kuris vos kinta ijungus varikli. Tikriausiai priklauso nuo apkrovos. Koks geriausias budas butu kalibruoti? As turiu tas reples/multimetra, bet man rodos, kad jos nelabai tiksliai matuoja?
EDIT: kazka radau:
Quote:/* This sketch describes how to connect a ACS715 Current Sense Carrier (http://www.pololu.com/catalog/product/1186) to the Arduino, and read current flowing through the sensor.Vcc on carrier board to Arduino +5v
GND on carrier board to Arduino GND
OUT on carrier board to Arduino A0
Insert the power lugs into the loads positive lead circuit, arrow on carrier board points to load, other lug connects to power supply positive */
int analogInPin = A0; // Analog input pin that the carrier board OUT is connected to
int sensorValue = 0; // value read from the carrier board
int outputValue = 0; // output in milliamps
void setup() { // initialize serial communications at 9600 bps:
Serial.begin(9600); }
void loop() {
// read the analog in value:
sensorValue = analogRead(analogInPin);
// convert to milli amps
outputValue = (((long)sensorValue * 5000 / 1024) – 500 ) * 1000 / 133;
/* sensor outputs about 100 at rest. Analog read produces a value of 0-1023, equating to 0v to 5v. “((long)sensorValue * 5000 / 1024)” is the voltage on the sensor’s output in millivolts. There’s a 500mv offset to subtract. The unit produces 133mv per amp of current.*/
// print the results to the serial monitor:
Serial.print(“sensor = ” );
Serial.print(sensorValue);
Serial.print(“t Current (ma) = “);
Serial.println(outputValue);
// wait 10 milliseconds before the next loop
// for the analog-to-digital converter to settle // after the last reading:
delay(10); }
Tiesa, gal kas gali paaiskinti ar galima naudoti viena HUB’e esanciu holo davikliu greiciui matuoti? Kazkur paskaiciau, kad galima analogini signala versi skaitmeniniu su Schmitt trigeriu on/off?
Dar vienas klausimukas, kaip parinkti itampos daliklio rezistoriu R1? Suprantu kaip issiskaiciuoja R2, bet is kur traukia R1 reiksme niekaip nedasyla.
Dekui
P.S. su Arturo didele pagalba vel pritaikau:
2013/07/22 at 20:34 #5949ArturasLParticipantAgniau, del Allegro sensoriaus, kiek suprantu, reiksme priklauso ir nuo sensoriui paduotos itampos. Gal tau pades si nuoroda: http://forum.arduino.cc/index.php?PHPSESSID=q7l4uloqsj4pjb0q1o188bf8o6&topic=133144.0
Ryt pabandysiu parasyti funkcija daviklio parodymu konvertavimui i amperus. Kazkur turiu 5A sensoriu, bus proga paeksperimentuoti.
Pries Jono paaiskinima vis galvojau kaip tas sensorius gali isduoti minusi reiksme, kai lyg mikrovaldiklio analogine dalis isduota nuo 0 iki 1024. Dabar aisku :)
Galvoju kuri man pirkti – Allegro sensoriu ar ACS758LCB-050B-PFF-T ar ACS756KCA-050B-PFF-T. Kiek ziuriu dokumentacija, niekaip nesuprantu kuo jie skiriasi, iskirus tik, kad ACS758 platesnis temperaturos veikimo diapazonas.
u8g.print kaip suklijuoti skirtingus kintamuosius isprendziau taip:
String countToString = String(count);
u8g.print(countToString + "km");2013/07/22 at 22:24 #5950agniusmParticipantAisku, taip ir turejo buti. Tikriausiai tam galima panaudotisita kur jau buvo rasyta:
Quote:g readVcc() {long result;
// Read 1.1V reference against AVcc
ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);
delay(2); // Wait for Vref to settle
ADCSRA |= _BV(ADSC); // Convert
while (bit_is_set(ADCSRA,ADSC));
result = ADCL;
result |= ADCH<<8;
result = 1126400L / result; // Back-calculate AVcc in mV
return result;
}
void setup() {
Serial.begin(9600);
}
void loop() {
Serial.println( readVcc(), DEC );
delay(1000);
}
2013/07/23 at 04:38 #5951jonasParticipantAgniau, neesu tyrinėjęs holo daviklio hub’e, bet kiek mačiau blcd darbo laiko diagramas tai ten visada vaizduojamas stačiakampės holo daviklių formos, be to net ir sinusoidę pajungus prie loginės schemos įėjimo ji fiksuos loginį 0 arba 1 pagal savo matinimo įtampą. Išvada tokia, kad holo daviklio signalą galima imti tiesiogiai stabilitronu ribojant signalo lygį iki maximaliai leistino. Bet čia tik mano teoriniai išvedžiojimai. Paskutinis mano matuoklis yra universaliu įėjimu greičiui matuoti, prie jo galima jungti arba gerkoną arba holo daviklį. Tai pasirenkama programiškai. Tavo bandymas su Allegro matomai išpuolė ant dvipusio bidirectional sensoriaus, todėl išėjime turi vcc/2 ir jei pas tave atraminė įtampa yra lygi maitinimo įtampai tu gauni maždaug pusę skalės, tai yra apie 512. Kalibruoti geriausia su kalibruotais prietaisais. Aš kalibruoju pagal kokį nors rimtesnį multimetrą. Na ne už 20Lt.
2013/07/23 at 10:23 #5952agniusmParticipantDel sensoriaus. Vel pasijungiau su didesne apkrova, 10.4A. Sensoriaus Vout be apkrovos rodo 512. Lygiai puse 1024. Pagal allegro tech. kai apkrovos nera isejime Vin/2. Pas mane maitina allegro 4960mV, isejime be apkrovos 2460mV. As kaip suprantu vienam A isejime tektu 2460mV / 100 (100A sensoriui) = 24.6mV
Naudoju taip:
Quote:sensorValue = analogRead(analogInPin);
outputValue = (((long)sensorValue * 4960 / 1024) – 500 ) / 24.6; //(133)
/* sensor outputs about 100 at rest. Analog read produces a value of 0-1023, equating to 0v to 5v. “((long)sensorValue * 5000 / 1024)” is the voltage on the sensor’s output in millivolts. There’s a 500mv offset to subtract. The unit produces 133mv per amp of current.*/
Gaunu pieno riebuma. Ka as cia grybauju?
2013/07/23 at 11:26 #5953ŠarūnasKeymasterSensorius turi būti maitinamas nuo mikrovaldiklio Vcc kojos. ADC AREF turi jungtis tiesiai prie sensoriaus Vcc. Reikalingas antras ADC kanalas, kuris matuotų maitinimo įtampos pusę (per daliklį 2:1). Taip pat turi būti sudėti atitinkami RC filtrai.
Rezultate vis tiek gaunasi tam tikra paklaida (šitiems sensoriams berods iki 3%), todėl prieš naudojant reikia susikalibruoti nulį.
Yra tame šiek tiek matematikos…
2013/07/23 at 11:43 #5954jonasParticipantpanaikintas
2013/07/24 at 14:32 #5955ArturasLParticipantPajungiau 5A sensoriu ACS712. Gauti duomenys plaukioja mazdaug 507 iki 515. Parasiau funkcija, kuri paskaiciuotu vidurki is 256 reiksmiu. Duomenys gavosi mazdaug stabilus 512-513.
Pajungiau 1.5A apkrova duomenys pasislinko mazdaug iki 450. Pakeiciau matavimo galus vietomis. Reiksme gavau mazdaug 550.
Kazkaip nesinori aklai kopijuoti formules. Norisi suprasti ka skaiciuoju. Paemus tokia situacikja kaip dabar, jei daviklio reiksme butu 1023 arba 0, tai tikrai ne 5 amperai. Kazkas netaip arba as kazko dar nesuprantu. Ir ka reiskia dokumentacijoje daviklio jautrumas 185mV/A?
2013/07/24 at 17:21 #5956agniusmParticipantMan taip pat nedasyla sitas reikalas. Pas mane reiksmes nuo 10A nelabai daug svyruoja.
2013/07/25 at 06:54 #5957jonasParticipantprie 5A gaunasi 3,425V išėjime prie 5V VCC. Uout=VCC/2+5*0.185. Kai į kitą pusę bus Uout=VCC/2-5*0.185. 1.5A sudaro pokytį 0,2775V. Matuok su multimetru ir jei taip yra tai sensorius veikia pagal aprašymą.
2013/07/26 at 15:08 #5958agniusmParticipantNezinau kaip praleidau bet ES tik pasirode linkas I vokieciu puslapi su arduino kompu. Gali buti naudinga:
https://github.com/jenkie/Arduino-Pedelec-Controller/tree/master/Arduino_Pedelec_Controller
http://www.pedelecforum.de/wiki/doku.php?id=elektrotechnik:forumscontroller
2013/08/04 at 09:58 #5959ArturasLParticipantAtsirado siek tiek laisvo laiko. Prisedau prie holo daviklio. Aciu Jonai uz formules, jos padejo suprasti daviklio esme. Zodziu prie 5A ir 5v maitynimo, mikrovaldiklis izduoda mazdaug max reiksme 701, o i priesinga puse max 323. Tai reiskia, kad 5 amperams atvaizduoti i viena puse mikrovaldiklis turi 701 – 512 = 189 dalis. I kita 323 – 512 = -189.
Parsiau funkcija kuri matuoja srove atsizvelgiant i mikrovaldiklio itampa. Isbandziau, veikia mazdaug su 0.1v paklaida (dar nesukalibruota visa sistema). Stai kodas:
//lcd start
#include "U8glib.h"
U8GLIB_64128N u8g(13, 11, 10, 9, 8); //SPI Com: SCK = 13, MOSI = 11, CS = 10, A0 = 9
//lcd end
//hall config start
int hallSensorPin = 5;
int hallCountAverageQuantity = 255;
int hallMaxValueMAmps = 5000;
//float hallVccMV = 5000;
float hallVccMV;
float hallSensitivityMV = 185;
int hallSensorCalibration = 2;
//hall config end
//hall variables start
int hallSensorValue;
int hallSensorValuesAverage;
long hallTotal;
//hall variables end
//
long readVcc() {
long result;
// Read 1.1V reference against AVcc
ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);
delay(2); // Wait for Vref to settle
ADCSRA |= _BV(ADSC); // Convert
while (bit_is_set(ADCSRA,ADSC));
result = ADCL;
result |= ADCH<<8;
result = 1126400L / result; // Back-calculate AVcc in mV
return result;
}
//
//hall function start
float hallValueAmps() {
hallVccMV = readVcc();
float hallValueInAmps = 0.000;
//hall sensor values average start
hallTotal = 0;
for(int i = 0; i <= hallCountAverageQuantity; i++) {
hallSensorValue = analogRead(hallSensorPin);
hallTotal = hallTotal + hallSensorValue;
}
hallSensorValuesAverage = hallTotal / hallCountAverageQuantity + hallSensorCalibration;
//hall sensor values average end
hallValueInAmps = (hallSensorValuesAverage - 512) * (hallMaxValueMAmps / (1024/hallVccMV * hallMaxValueMAmps/1000 * hallSensitivityMV)) / 1000;
return hallValueInAmps;
}
//hall function end
void setup(void) {
}
void loop(void) {
//lcd start
u8g.firstPage();
do {
u8g.setFont(u8g_font_5x8);
u8g.setPrintPos(30, 30);
u8g.print(hallValueAmps(), 3);
} while( u8g.nextPage() );
//lcd end
//delay(1000);
}
Turiu klausima. Jei as matuoju mikrovaldiklio itampa Saruno rekomenduotu budu ar as galiu tuo paciu mikrovaldukliu papildomai matuoti itampa su itampos dalikliu? Nes siuo atveju VREF kintantis.
-
AuthorPosts
- You must be logged in to reply to this topic.