I'm trying to use a joystick to control the brightness of two LED's (which will eventually be replaced by stepper motors). The resting analog value for the joystick on the X axis is 504, with the minimum and maximum of course being 0 and 1023, respectively. My goal is to use a conditional to determine which LED to light, and how bright it should be. As the analog value approaches 1023, it should get brighter. as the analog value approaches 0, the other bulb should increase in brightness.
Here is the relevant code so far:
if (xVal < 500) {
analogWrite(7, map(xVal, 0, 500, 255, 0));
}
else if (xVal > 510) {
analogWrite(6, map(xVal, 510, 1023, 0, 255));
}
if the value is greater than 510, it behaves as wanted. The brightness steps up, until hitting 1023 where it reaches its maximum value.
For less than 500 however, the behavior doesn't work. It just does a maximum brightness when true, without adjusting the PWM. If I understand map functions right, shouldn't it be mapping an analog value of 0 to the maximum PWM value?
The answer was quite simple and actually did not fall within a code issue. I'm an arduino noob and I realized pin 7 (for the less than condition) does not support PWM. I changed it to pin 5 and it began working. I also opted to modify the map function to make it more sensible.
analogWrite(5, map(xVal, 500, 0, 0, 255));
}
This is how I changed it. Using the map to invert the value, I thought it made more sense to have the first range flipped, rather than the PWM range.
Related
I am having a problem with my analog joystick. I have set it up to move the mouse position accordingly to the joystick values. On a technicality, it does work, as it does control the mouse. However, the calibration is off and when I test it, the mouse stays off-centered on the screen at rest and can only move around from that "center" position. I have scoured the internet trying to find a solution, but alas I must ask.
Snippet:
int xMapped = map(xread, 0, 1023, 0, 1920);
int yMapped = map(yread, 0, 1023, 0, 1080);
I have done testing to the joystick and can confirm the min and max values are correct.
(I feel like I may have weirdly worded the situation, so here is a ms paint visual :D)
Expectation
Circle-Mouse
Rounded Rectangle-Range
Rectangle-Screen
What Happens
I'm trying to control my 180 degree servo motors through a Adafruit 1411 Servo shield. However I don't find it simple enough to write the servo's position in angles like the normal servo library without the shield.
Using the Adafruit 1411 Servo shield and Adafruit_PWMServoDriver-library lets you control a servomotor by modifying its pulselength as far as I've realised. To my question..
Is there a way for me to either use the servo shield's output and still write in degrees OR somehow convert these pulselength into angle-degree?
Example of the differences:
Adafruit_PWMServoDriver-library:
pwm.setPWM(Servo, 0, pulseLength);
Servo-library:
Servo.write(45); //Writing in angles like this would be optimal for my project.
Any help in the right direction is much appreciated!
Use the Arduino map function. The following is from the Adafruit instructions:
pulselength = map(degrees, 0, 180, SERVOMIN, SERVOMAX);
Where SERVOMIN and SERVOMAX are values you set according to the range of travel of your servo. This linearly maps a value between 0 and 180 into the range between SERVOMIN and SERVOMAX.
Since you've been doing this with pulse widths so far, you probably already knew the values you need to use.
QPainter has many composition modes but none called additive. I'm interested because additive blending is used all the time in games for lighting / particles whatever.
The overlay mode is the only one that had something like the effect of lighting.
EDIT: I figured it out, heres how you can efficiently make different coloured lights in Qt.
In constructor or where ever, not in paint event:
light = QPixmap("light.png");
QPainter pix(light);
pix.setCompositionMode(QPainter::CompositionMode_Overlay);
pix.fillRect(light.rect(), QColor(255, 0, 0, 255)); // colorize the light in any color
Paint Event:
// Do drawing, e.g. a background
p.drawPixmap(0, 0, QPixmap("background.png"));
// draw the lighting
p.setCompositionMode(QPainter::CompositionMode_Plus);
p.drawPixmap(100, 100, light);
You can reuse the same pixmap as much as you like and draw it with different opacity or size etc.
The documentation for QPainter::CompositionMode_Plus says:
Both the alpha and color of the source and destination pixels are added together.
I'm trying to create a robot using three HC-SR04 ultrasonic sensors and my Arduino Pro Mini but I've run into a few problems. In short the robot's function is as follows:
The robot is dual wheeled, with an H-bridge (SN754410) driving each wheel.
There's one HC-SR04 sensor on each side of the robot, the left one activates the left wheel motor when it detects a hand in front of it, vice versa for the right side.
i.e. To make the robot go forward, we place our hands near the left and right side of the robot, to make it turn right, we remove the right hand and keep the left one in place, vice versa for turning left, etc.
A third HC-SR04 is located the top of the robot, such that it activates a third motor when the user's hand is hovering above the robot.
My test code is as follows:
#include <NewPing.h>
#define SONAR_NUM 3 // Number of sensors.
#define MAX_DISTANCE 20 // Maximum distance (in cm) to ping.
NewPing sonar[SONAR_NUM] = { // Sensor object array.
NewPing(4, 5, MAX_DISTANCE), // Each sensor's trigger pin, echo pin, and max distance to ping.
NewPing(6, 7, MAX_DISTANCE),
NewPing(8, 9, MAX_DISTANCE)
};
#define ena1 10 //trigger for left motor H-bridge
//#define ena2 11 //trigger for right motor
//#define ena3 12 //for top motor
long sensors[3]; //array to store sensor distances
void setup() {
Serial.begin (115200);
pinMode(ena1, OUTPUT);
//pinMode(ena2, OUTPUT);
//pinMode(ena3, OUTPUT);
}
void loop() {
for (uint8_t i = 0; i < SONAR_NUM; i++) { // Loop through each sensor and display results.
delay(50); // Wait 50ms between pings (about 20 pings/sec). 29ms should be the shortest delay between pings.
sensors[i] = sonar[i].ping_cm();
}
Serial.println(sensors[0]);
if (sensors[0] > 0 && sensors[0] <= 20){
Serial.println("detected");
digitalWrite(ena1, HIGH);
}else{
Serial.println("NA");
digitalWrite(ena1,LOW);
}
}
As you can see, I'm using the NewPing.h library to collect the sensor data. After each iteration of the for loop, the distances detected by the sensors are stored in a sensor array. When a hand is placed about 15-20 cm away from a sensor, the arduino sends a digital "HIGH" trigger signal to the respective H-bridge, activating the respective motor (I only have one of these pins, "ena1", enabled in my code, the other two are commented for the test).
To test my code, I simply connected the H-bridge trigger pin "ena1" to an LED, this pin is activated by the sensor whose distance data is stored in variable "sensors[0]". However, after I compile and upload my code, I notice that the LED simply flickers faintly as I put my hand in front of the sensor. As if the LED is being turned on and off very fast.
The output from the serial monitor is as follows:
15
detected
0
NA
16
detected
0
NA
14
detected
As you can see, by putting my hand about ~15cm in front of the sensor, the sensor returns the correct distance and the "ena1" pin is set to high (as evidenced by "detected" being printed to the screen).
However, the sensor always returns a "0" value at the next iteration of the main loop (while my hand is still in front of the sensor), subsequently setting the "ena1" pin to LOW again, which might explain why the LED is being turned on and off so fast.
I'm not sure why this is happening... Interestingly, by removing the digitalWrite lines from the code, the sensor returns the correct values (i.e. no "0" value when my hand is in front of the sensor).
Any ideas on how I can fix this?
Thanks in advance!
This might be a hardware error. I've seen cases where, if the pins of the HC-SR04 were a brass (gold-ish) color, the sensor had a tendency to throw out a 0 for distance.
My suggestion is to get an other ultrasonic sensor, preferably with more silver-ish colored pins.
Your code looks good though!
Good luck!
I am using an ultrasonic proximity sensor to get how close an object is. If the object is equal to or less than 50cm away from the sensor, it will convert the number (between 0-50) to a number between 0-255 so it can be used to change an LED brightness.
How can I convert the number from one range to another in my code?
Cheers,
Fjpackard.
Ps. Please don't flag this as a clone – I tried to find a question like this but none of them met the right criteria...
You could try something like this:
brightness = distance <= 50 ? distance * 255 / 50 : 255;
Reading between the lines though I suspect you want the brightness to increase as the distance decreases, so you probably want something more like this:
brightness = distance < 50 ? (50 - distance) * 255 / 50 : 0;