lesthegrngo Posted November 4, 2022 Posted November 4, 2022 (edited) *****EDIT**** Found the issue, one of the first PCB's I made and it has pins A & B transposed on one of the RS485 inputs Thanks for anyone who looked at this, sorry to have been a nuisance Hi all, in an attempt to get away from using EasyDriver boards, which have at least in my experience been very prone to blowing and super sensitive, I have developed the following sketch to drive the X27-168 stepper motors direct from the Nano boards. The advantages are that a) I avoid using the EasyDriver boards and b) I can still use the existing PCB's I have by just adding some jumpers to connect direct to the stepper from the Nano. The sketch below works fantastically via USB, reliably and while simple will hopefully serve as the basis for improving some other parts. However when I comment out the "#define DCSBIOS_DEFAULT_SERIAL" and uncomment the " #define DCSBIOS_RS485_SLAVE 33 /#define TXENABLE_PIN 2" I then have no success in getting it to work with RS485. I am checking that RS485 is active using another RS485 connected device, so can demonstrate that RS485 is working. here is the full sketch #define DCSBIOS_DEFAULT_SERIAL //#define DCSBIOS_RS485_SLAVE 33 //#define TXENABLE_PIN 2 #include "DcsBios.h" #include "SwitecX25.h" // 315 degrees of range = 315x3 steps = 945 steps int newValue; unsigned int maxSteps = 800; // declare motor1 with 945 steps on pins //SwitecX25 motor1(maxSteps, 9, 8, 10, 11); SwitecX25 motor1(maxSteps, 6, 5, 7, 8); void setup(void) { DcsBios::setup(); motor1.zero(); // this is a slow, blocking operation motor1.setPosition(500); } void onApuTempChange(unsigned int newValue) { unsigned int position = map(newValue, 0, 65535, 0, maxSteps); motor1.setPosition(position); } DcsBios::IntegerBuffer apuTempBuffer(0x10c0, 0xffff, 0, onApuTempChange); void loop(void) { motor1.update(); DcsBios::loop(); } Can anyone see why this would not work with RS485? I will try and splice in the stepper initialisation and configurations that are used in other stepper sketches one I work this out wrinkle Cheers Les Edited November 4, 2022 by lesthegrngo
lesthegrngo Posted November 4, 2022 Author Posted November 4, 2022 I have a knock on question, more for my information than a search for a solution I found that via USB, I could quite easily drive three stepper motors at any time, for example APU Temp, APU Revs and Eng 1 Fuel Flow would all display perfectly via USB. Once the sketch was converted to RS485 it was no longer able to deal with more than one stepper, as even two would just end up with random movement. I'm fine with one Nano per stepper as it would be how it was originally (and I'm amazed at how much more reliable it is) but am curious as to why there is a difference when connected to RS485 If anyone can offer any insight I would love to know why Les
No1sonuk Posted November 4, 2022 Posted November 4, 2022 Maybe the RS485 uses a slower data rate? OR it uses a different connection protocol the Arduino has to "pay more attention to" because it's not handed off to a dedicated interface chip. When you think about it, the USB interface device handles whether or not the data is for the device, then passes it on if it is. With the RS485 setup, I assume the main processor has to decide if it should do anything with the data it receives
lesthegrngo Posted November 5, 2022 Author Posted November 5, 2022 Yeah, maybe the way it handles the data. Still, It's certainly not a problem, as I said I had planned on using the 12 nanos for the gauges anyway so for me just deleting the EasyDriver boards is enough. So the sketch above works, but one thing I can't get the sketch to do is to zero the stepper. There is a section of the sketch that has "motor1.zero(); // this is a slow, blocking operation motor1.setPosition(500);" In theory this should zero the stepper, then set it to the position correlating to 500. It doesn't, in fact it appears to do nothing. In the SwitecX25.cpp file there is a section defining this, but for some reason it is not functioning What I want is for it to do as the other sketches that are based on Craig's original one, which has a subroutine that drives the gauge to max, then back to the min position so that the gauge always starts in the zero point. I have tried putting in multiple values into the setup to try this, but I can't get it to work I also tried putting this into the void setup section " motor1.setPosition(currentStep-500); motor1.update();" It accepts it but it does nothing. Any thoughts? It would certainly make the sketch complete to get the zeroing functioning Les
lesthegrngo Posted November 6, 2022 Author Posted November 6, 2022 Well, I got it to work with a zeroing routine at the beginning. I now have a nice light sketch that drives the X27 steppers without the ned for driver boards or a 12V input, and as long as the RS485 input has a good 5V supply attached to the 5v and GND pins, the steppers use so little power that it means only one four way connection is required for the whole lot Pretty pleased with myself! Cheers Les
Vinc_Vega Posted November 6, 2022 Posted November 6, 2022 (edited) Hi Les, why don't you use the lower hard stop of the stepper as zero point of your scale? Simply adjust it when puting in the pointer during assembly of the gauge. Than you let return the stepper within the sketch's SETUP routine to the absolute minimum (more steps than maxsteps backwards) and so have calibrated the scale. Regards, Vinc Edited November 6, 2022 by Vinc_Vega Regards, Vinc real life: Royal Bavarian Airforce online: VJS-GermanKnights.de [sIGPIC][/sIGPIC]
lesthegrngo Posted November 6, 2022 Author Posted November 6, 2022 Because I'm a stubborn so and so, after I got the zeroing working I went back to looking at seeing if multiple steppers could be driven by one nano using RS485. A thought ocurred that I had been using the 168 nanos rather than the 328 boards for the test and I know that they are more restrictive, having less memory. So after getting the zeroing working for two gauges via USB on a 328 board, I re-tried with the RS485 enabled. It didn't work, but it gave me a lead to follow. When you connect the USB version, the first thing it does is go through the zeroing routine, which of course is also what should happen if connecting via RS485. This wasn't happening. I wondered if that was due to low power getting to the Nanos so I attached a 5v supply to the RS485 connection, and improved the integrity of the RS485 connector to ensure that it wasn't a weak link. And away it went, two gauges running from one Nano via RS485 (APU REVS and APU TEMP, which are easy to play with on the ground) zeroing on power up and then working correctly in game. However all is not perfect yet as the movement of the gauges is jerky, and every minute or so the pointer with twitch and reduce the value shown, until after five minutes the gauge has fallen back to near the zero position despite the value being output by DCS BIOS being the steady. I suspect that the zeroing function is to blame for this, and it is being momentarily called causing the gauge pointer to fall back. I am trying to work out how to get the the zero function to be a run once command to see if this stops it For reference here is the sketch, and I ran the sketch without the zero function and it cured the issue of the gauge oposition dropping back. If anyone can help me with instering the 'run once' code for the zeroing function I would be grateful Les //#define DCSBIOS_DEFAULT_SERIAL #define DCSBIOS_RS485_SLAVE 34 #define TXENABLE_PIN 2 #include "DcsBios.h" #include "SwitecX25.h" // 315 degrees of range = 315x3 steps = 945 steps int newValue; unsigned int maxSteps = 800; unsigned int targetStep = -800; unsigned int currentStep; // declare motor1 with 945 steps on pins 8-11 //SwitecX25 motor1(maxSteps, 9, 8, 10, 11); SwitecX25 motor1(maxSteps, 5, 4, 6, 7); void setup(void) { DcsBios::setup(); motor1.zero(); // this is a slow, blocking operation motor1.setPosition(targetStep); //motor1.update(); } void onApuRpmChange(unsigned int newValue) { unsigned int position = map(newValue, 0, 65535, 0, maxSteps); motor1.setPosition(position); } DcsBios::IntegerBuffer apuRpmBuffer(0x10be, 0xffff, 0, onApuRpmChange); void loop(void) { motor1.update(); DcsBios::loop(); } 1 hour ago, Vinc_Vega said: Hi Les, why don't you use the lower hard stop of the stepper as zero point of your scale? Simply adjust it when puting in the pointer during assembly of the gauge. Than you let return the stepper within the sketch's SETUP routine to the absolute minimum (more steps than maxsteps backwards) and so have calibrated the scale. Regards, Vinc looks like our posts crossed Vinc! Essentially what I did is what you suggest, but need to refine the code to stop it influencing the gauge after startup Les
No1sonuk Posted November 6, 2022 Posted November 6, 2022 Putting it in the setup routine should make it run only once on startup. If you're having other power issues, could you be having a "brownout" - a glitch that causes the processor to restart? Maybe a 10uF or more capacitor on the 5V lines might help.
lesthegrngo Posted November 6, 2022 Author Posted November 6, 2022 Interesting, could that be the cause of some pointer flicker? Les
No1sonuk Posted November 6, 2022 Posted November 6, 2022 16 minutes ago, lesthegrngo said: Interesting, could that be the cause of some pointer flicker? Les Possibly. Might be noisy power lines caused by the inductive coils of the motors, too
lesthegrngo Posted November 6, 2022 Author Posted November 6, 2022 (edited) That flicker was something I saw with stepper driver versions too; I just assumed it was due to the data stream, maybe I have to re-evaluate, remember I always banged on about how jerky the movement was? It never occurred to me it may be power related. It still may not be, but I'm happy to experiment I still would like to nail down the 'run once' subroutine, I've been looking at some, errrrr, 'tutorials ' that purport to explain how to do so but assume a degree in astrophysics before you start. As for the forums, ooh, how I enjoy being made to feel stupid! This is why I so appreciate this forum; we all try to help without the expectation that we all are experts, which is the whole point of a help forum Les Edited November 6, 2022 by lesthegrngo
No1sonuk Posted November 6, 2022 Posted November 6, 2022 It REALLY annoys me how condescendingly arrogant some of the people on the "coding" forums are. Stepper drivers wouldn't stop you having power noise problems. They might even make it worse. And reading a bit more, 0.1uF across the supply might help with the noise as well as 10uF. The 10uF gets the low frequency and the 0.1uF gets the high.
lesthegrngo Posted November 7, 2022 Author Posted November 7, 2022 (edited) Thanks - as I understand it then, the capacitors would be attached at the power input end, effectively across the 5v and GND power in pins, and not one set for each device? An update on the stepper sketch, I managed to figure a way to make the zeroing run once, and now the sketch is rock solid with absolutely no pointer flicker when the gauge is indicating a steady reading. However when the stepper is moving the pointer, it is still flickering, and despite the gauges running from different Nanos the flicker happens simultaneously on both gauges. Is that a sign that there is power noise or some kind of glitching in the data stream to the nanos or RS485 master? Les Edited November 7, 2022 by lesthegrngo
No1sonuk Posted November 7, 2022 Posted November 7, 2022 Yup. Very likely power noise. The high frequency filtering works better if you have it on every device's 5V lines. If you have it on just the main supply, any local noise can still have an effect.
lesthegrngo Posted November 7, 2022 Author Posted November 7, 2022 (edited) so a pair of caps on each of the Nano inputs as well? Les Edited November 7, 2022 by lesthegrngo
No1sonuk Posted November 7, 2022 Posted November 7, 2022 The smaller ones may be enough for the individuals. Having said that, looking at the schematic, they're already built into the Arduinos, so extra ones may not help. So then maybe the glitching is a function of driving multiple motors from one device?
lesthegrngo Posted November 7, 2022 Author Posted November 7, 2022 No, the glitching is occurring even when only driving one stepper per nano As ever, solved one issue, another couple have cropped up just to keep me busy For some reason I can't fathom, yet again, suddenly my RS485 network will now not function at all. I've reflashed the master, the slaves, replaced the MAX487 chips, rebooted the PC, nothing. Literally from one moment to the next it stopped. Last time I ended up curing it by redownloading the Arduino IDE, so I will start there As for the glitching, it only happens on RS485 connected steppers; the ones connected via USB are stable cheers
lesthegrngo Posted November 7, 2022 Author Posted November 7, 2022 (edited) Right, reinstalled the IDE and reflashed the master and back up and running again. Don't know what happened there...... The glitching is affecting all the RS485 driven gauges, and is synchronised so they all twitch at the same time. I am trying to get an LCD device set up so I can see if the signal is jittery or not I also want to put a little subroutine in the sketches to make sure that when the gauge is supposed to go to zero that it really does go to zero, as I notice that some don't, and then start from the incorrect zero position. Eventually after a few cycles, the zero has moved to a completely different position. If I can get someting in there that says something like "if newValue is less than 100, move the pointer by -100 steps" so that it hard resets the zero every time. I tried with the following, but it isn't doing what I expected //#define DCSBIOS_DEFAULT_SERIAL #define DCSBIOS_RS485_SLAVE 37 #define TXENABLE_PIN 2 #include "DcsBios.h" #include "SwitecX25.h" // 315 degrees of range = 315x3 steps = 945 steps int newValue; unsigned int maxSteps = 800; unsigned int currentStep; unsigned int targetStep = -800; unsigned int targetSteppark = -100; int runXTimes = 0; int N = 1; // declare motor1 with 945 steps on pins SwitecX25 motor1(maxSteps, 7, 8, 5, 6); void setup(void) { DcsBios::setup(); } void onREngFuelFlowChange(unsigned int newValue) { unsigned int position = map(newValue, 0, 65535, 0, maxSteps); if (newValue < 100) { motor1.setPosition(targetSteppark); motor1.update(); } else { motor1.setPosition(position); motor1.update(); } DcsBios::IntegerBuffer rEngFuelFlowBuffer(0x10b0, 0xffff, 0, onREngFuelFlowChange); void loop(void) { if (runXTimes < N) { motor1.zero(); // this is a slow, blocking operation motor1.setPosition(targetStep); motor1.update(); runXTimes++; } motor1.update(); DcsBios::loop(); } cheers Les Edited November 7, 2022 by lesthegrngo
No1sonuk Posted November 7, 2022 Posted November 7, 2022 Maybe you're losing steps? It happens with CNC machines sometimes. What's your motor wiring like? If it's spaghetti, that might be part of the problem.
lesthegrngo Posted November 8, 2022 Author Posted November 8, 2022 virtually zero wiring, all hard wired apart from a short (2 inch) jumper cable to replace the stepper. And it doesn't do it when the exact same hardware (minus Max 487 chip) is used. Tried it with just one gauge and without the external power supply, so effectively powered by the Mega, it's the same. Today I will reinstall a stepper driver board and see if it continues with the original setup Cheers Les
No1sonuk Posted November 8, 2022 Posted November 8, 2022 Can you try it without the Max 487s? I.e. connect just one Nano direct to the Mega pins. TX on one to RX on the other. Plus common gnd. That should eliminate the RS485 bus as the problem.
lesthegrngo Posted November 8, 2022 Author Posted November 8, 2022 Didn’t know you could do that! Should be easy enough, let me give it a go cheers Les
No1sonuk Posted November 8, 2022 Posted November 8, 2022 I've not tried myself, but it should work as long as only one slave device is connected.
lesthegrngo Posted November 8, 2022 Author Posted November 8, 2022 (edited) Right, tried that, and it did make a difference. The pointer doesn't twitch as much, however it still does freeze momentarily, then jumps to the correct position, so it's a bit like watching a stop motion film It's better, but still not as smooth as the USB version (which to be truthful is not as good as I'd like it to be). Take a look at the video, via USB on the left, hard wired RS485 on the right I made an LCD monitor to look at the DCS output live for the APU temp (my test case above) and I don't see any spiking or unstable numbers being output, I'm going to see if there is any way to output the data to the Ardiono IDE serial monitor Les Edited November 8, 2022 by lesthegrngo
No1sonuk Posted November 8, 2022 Posted November 8, 2022 Hmm. Can you swap the devices? It might be the one on the right can't keep up with the input in RS485 mode because it needs to "hand-hold" the serial comms more than when running USB. I have two different "compatible" Unos that have very different latency when used for a CDU display.
Recommended Posts