Forum Replies Created
-
AuthorPosts
-
MichaelKeymaster
You are right, it is a timer issue. Generating video requires precision and takes up a lot of the microcontroller’s time. For example, to do serial communication, the pollserial library performs serial communication with polling instead of interrupts. The use of the pollserial library occurs during the horizontal blanking interval.
You may try pollserial for communication with another Arduino. The other Arduino can just use regular normal Serial library.
Or you can disable the video generation temporarily while you do i2c, then re-enable it, if your communication is infrequent. Just some ideas.MichaelKeymasterYes, you should be able to record and then playback delayed at 16KHz.
MichaelKeymasterTry changing this part in the function ISR(TIMER1_OVF_vect):
if (hours == 12) { pm = !pm; } if (hours == 13) { hours = 1; }
to this:
if ((hours == 12) || (hours == 24)) { pm = !pm; } if (hours == 24) { hours = 0; }
- This reply was modified 7 years, 9 months ago by Michael.
MichaelKeymasterOk, I’m just having a hard time understanding. I will send you a replacement board along with return postage for the bad unit. You can drop the bad unit in the same box as the new one and put the return label on the box. That way I can diagnose the bad unit and find out what is wrong.
MichaelKeymasterSo, you are saying that there is not continuity between the power jack (the connection at the end of it) and the 5V pad where the LEDs connect?
(There was when I tested it, because I connect an LED strip with pins to 3 pads for the LEDs, and I connect a power supply to the jack.)
Maybe you can send a picture of your LED strip connection.
MichaelKeymasterYou could try connecting the power source directly to the 5V and GND pins where you soldered the LED connector, but we need to figure out why the board is not working when you apply power.
Can you use a multimeter to see if you have shorted 5V and GND together when soldering the LED connector?
Does anything get hot when you try to power it?
MichaelKeymasterIs the power supply center positive?
I test every Lumazoid before shipment, so I’m not sure how it could stop working. Have you soldered a connector for the LEDs? Did you power it on before doing that?
MichaelKeymasterWhen you power it, does the blue LED one the Lumazoid board come on?
How are you powering the Lumazoid? It requires a 5V supply, center positive. It must be able to deliver 2A minimum.
Exactly which kind of LED strip did you connect?MichaelKeymasterThe newest version of the Arduino bootloader prevents Asteroids from working for some reason. Please read the instructions for loading the pre-compiled .hex file on the games page. Look at the section of the page for Asteroids:
MichaelKeymasterHere, try this for countdown():
void countdown() { int ledCounter = 0; int ledCounterThreshold = 100000; byte ledCurrentState = HIGH; byte defusePin; byte detPin; byte wrongPin1; byte wrongPin2; boolean wrongPin1Cut = false; boolean wrongPin2Cut = false; boolean defused = false; countdownRunning = true; int fractionalSecond; // assign random pins defusePin = random(WIRE_1, (WIRE_4 + 1)); detPin = defusePin; while (detPin == defusePin) { detPin = random(WIRE_1, (WIRE_4 + 1)); } wrongPin1 = detPin; while ((wrongPin1 == defusePin) || (wrongPin1 == detPin)) { wrongPin1 = random(WIRE_1, (WIRE_4 + 1)); } wrongPin2 = detPin; while ((wrongPin2 == defusePin) || (wrongPin2 == detPin) || (wrongPin2 == wrongPin1)) { wrongPin2 = random(WIRE_1, (WIRE_4 + 1)); } digitalWrite(LED_PM, LOW); // turn off the PM LED // Keep track of how far we are into the current // second so we can correct later. fractionalSecond = TCNT1 - TIMER1_SECOND_START; // Reset back to the last second boundary so we can start the countdown // immediately and so that the first second isn't truncated TCNT1 = TIMER1_SECOND_START; beep(3800, 30); digitalWrite(LED_DET, ledCurrentState); while ((countdownSeconds > 0) && (!defused)) { for (int i = 0; i < 10000; i++) { // get input if (digitalRead(detPin) == HIGH) { countdownSeconds = 0; break; } if (digitalRead(defusePin) == HIGH) { defused = true; break; } if ((digitalRead(wrongPin1) == HIGH) && !wrongPin1Cut) { if (countdownSeconds >= 3) { countdownSeconds = countdownSeconds - 3; } else { countdownSeconds = 0; } } if ((digitalRead(wrongPin2) == HIGH) && !wrongPin2Cut) { if (countdownSeconds >= 3) { countdownSeconds = countdownSeconds - 3; } else { countdownSeconds = 0; } } } delay(20); if (ledCounter++ > ledCounterThreshold) { ledCounter = 0; if (ledCurrentState == HIGH) { ledCurrentState = LOW; } else { ledCurrentState = HIGH; } digitalWrite(LED_DET, ledCurrentState); } } digitalWrite(LED_DET, LOW); countdownRunning = false; if (!defused) { detonate(); } else { beep(4500, 80); isDefused = true; } // Now to keep the time accurate, add back in the fractional // second that we took off when we started the countdown sequence. // Wait until we can add it back to TCNT1 without overflowing. while (TCNT1 >= (65535 - fractionalSecond)); TCNT1 += fractionalSecond; }
MichaelKeymasterNo, you put the code that checks whether wires are cut in the loop that checks the wires. In the loop where it says “get input”. That’s where it is checking if the detPin or defusePin are cut (they are HIGH).
MichaelKeymasterSorry, it’s defusePin, not defuseWire.
So to fix the wires, for example:
defusePin = WIRE_1; detPin = WIRE_3;
MichaelKeymasterHere is some more info about why reading an IR sensor and reading the audio at the same time is going to be a problem. The ISR code in an IR library will use a timer interrupt vector to run some code thousands of times per second:
ISR(TIMER2_COMPA_vect){ ... }
This is the code that will run on a constant basis, interrupting the Lumazoid code. The TIMER2 interrupt vector has higher priority than the ADC (analog to digital conversion) interrupt, so it will preempt the ADC conversion. See the Lumazoid code ISR:
ISR(ADC_vect) { ... }
This is the code that runs 9000 times per second to sample the analog input. It must run with precise timing between samples or the frequency analysis will be wrong.
But try it and see what happens!MichaelKeymasterHi Vadpol, I’m glad you reported back with your progress. Sounds like you’ve been having a lot of fun with it, so that’s great. Feel free to send pictures if you want.
Regarding the IR signal: you are correct that checking for the last received IR code could be done once every time through the loop(), but the problem is that the processor needs to measure the IR pin on a constant basis to pick up all the changes in the voltage. IR sensors modulate a 38KHz frequency, so the receiver has to read the sensor pin thousands of times per second. The IR library does this by scheduling an interrupt service routine (ISR) to run at this high frequency and keep track of the voltages. So, this code does need to run all the time as an ISR, and that would interrupt the Lumazoid code thousands of times every second. It would interfere with the collection of analog samples and probably ruin the audio analysis.Bottom line, even if you ask for the last code infrequently, the microcontroller has to make many perfectly timed measurements to receive the signal.
Here is a good description of how it works: https://learn.sparkfun.com/tutorials/ir-communication
Keep having fun with your project though — you are making lots of good improvements!
MichaelKeymasterWhen using the Video Experimenter, you have to enable overlay capability with some special code. This is demonstrated in all the example projects like: the overlay example
Try this code for your sketch. Note the initOverlay() function and the ISR(INT0_vect) function. They are required.
#include "TVout.h" #include "fontALL.h" TVout TV; void setup() { TV.begin(NTSC,90,40); initOverlay(); TV.select_font(font6x8); } // Initialize ATMega registers for video overlay capability. // Must be called after tv.begin(). void initOverlay() { TCCR1A = 0; // Enable timer1. ICES0 is set to 0 for falling edge detection on input capture pin. TCCR1B = _BV(CS10); // Enable input capture interrupt TIMSK1 |= _BV(ICIE1); // Enable external interrupt INT0 on pin 2 with falling edge. EIMSK = _BV(INT0); EICRA = _BV(ISC01); } // Required to reset the scan line when the vertical sync occurs ISR(INT0_vect) { display.scanLine = 0; } void loop() { TV.set_cursor(0,6); TV.print("XXXXX"); delay(60); }
- This reply was modified 7 years, 11 months ago by Michael.
-
AuthorPosts