electronic-leadscrew
electronic-leadscrew copied to clipboard
Spindle position display option
Greetings. I've just completed my ELS install today and have it working on my PM-1130v lathe. Thanks to all who have made this project possible!
There is another piece of data the the ELS controller has that would be helpful. The ELS controller knows the spindle position to a resolution of a tiny bit better than a 10th of a degree. Displaying this position would allow the lathe operator to rotate the spindle and workpiece to a particular position. For example, I could scribe the side of a pulley busing with two marks at exactly 90 degrees for subsequent drilling of set screw holes.
Someone who wanted to use this capability in its full glory might want to add a spindle lock and/or some mechanism to rotate the spindle more accurately or quickly than can be done by hand. But even w/o anything other than a toolbit to scratch a mark, this feature would allow using the spindle to rotate and mark workpieces to a 1/10th degree accuracy. A big win, IMHO.
There are only two operator inputs needed.
- There needs to be a way to toggle between RPM and Spindle Position.
- This could be a configuration switch in the code (I'd probably chose this over RPM since I already have a RPM gauge on the lathe).
- It could be something shown when the ELS is in the "powered off" state (seems far more useful than just showing a zero :-).
- It could be a combo of buttons (multiple buttons do get confusing though)
- It could be a button press before and during power up
- It would be nice to be able to zero the angular position readout. This would allow display of angle just like a DRO. One can set the zero position and then rotate relative to that.
I'd vote to show the rotational angle measurement anytime the ELS is "off". And to allow the the set button in this mode to zero the current angle, so that relative movement doesn't require math on the operator's part.
Is there any interest in this?
RR
Here you go https://github.com/clough42/electronic-leadscrew/issues/231
Position Display will show the angular position of the spindle instead of RPM. To exit go back into the menu and select 'RPM'.
Seconding @tomvikse 's answer. I think that #231 is currently effectively the primary upstream for this firmware; it implements features that @clough42 anticipated potentially adding, and James hasn't been merging PRs generally into his branch. (I've offered to rebase it to make it easier to merge into mainstream, preserving the default configuration, but James hasn't taken me up on the offer.)
I used the angle display to accurately tune my feed rate with a dial indicator for my lathe; I have both a lead screw and a feed bar, and I didn't characterize the gear ratios in my apron, so I just took the backlash out, then measured error while turning the chuck by hand. Super handy, and since I don't have a dividing head for my spindle, probably the most accurate thing I could do.
However, #231 doesn't have your idea of zeroing out the angle, I think. That would be a potentially useful addition! ☺
I'm not sure I'm ready to digest all the changes in the #231 firmware, but it sounds a good portion of the RPM code that I want is in there. Having the angular position when the ELS is "off" and having it operate normally when on is still of interest. Since all the hard coding is probably done and available, I might overcome my coding aversion and try implementing it at some point when I need a dividing head. But, I need to ponder for a bit.
FYI, you don't really need the angular position display to calibrate for a feed vs a thread operation. I marked the spindle with a sharpy and put a corresponding mark on the sheet metal above that mark. While rotating the spindle by hand and lining it up by eye is prone to minor errors they can be reduced to almost nothing by rotating the spindle 10x rather than 1x to get the distance per revolution. And, to top it off, I don't see any need for great precision on feed rates. At least for me, .11 mm/rev and .13 mm/rev would be so close to .12mm/rev that I wouldn't know the difference. Not saying that the precise approach isn't better....just that it's akin to polishing a cannonball.
Strangely enough, my calculated "microsteps" for my feed bar is 4.71 (compared to 3 for the thread microsteps). Not sure what gearing is in place to get that weird ratio, but I can't argue with success.
I was having fun getting it more precise than it needed to be. I used 10 revolutions and measured angular position with the encoder. I used a sharpie to see when the mark was getting close, then finished by watching the angular position get to zero. The question wasn't "why?" it was "why not?" ☺
Honestly the hardest part of coding up angular position zeroing is deciding how to access it. The thread-to-shoulder branch uses a lot more of the previously unused button press options...
Angular position via a display seems useless if the lathe is running. So I suspect that a reset of angular position is only useful (and therefore only desired) when the lathe is not running. In the "powered off" state, I was hoping that the "set" button might be available.
This morning, I read thru the #231 description again. I now realize that the "set" button would not be available to reset the angle in position mode (it appears to be used in order to exit this mode). However, that's not a problem if entering position mode resets the angle. This should be sufficient and is actually better (since it avoids the complexity of another control sequence that must be remembered). If one doesn't like where the zero angle is currently, it should be easy enough to rotate the spindle to the new desired location, exit position mode and then return to position mode, thus resetting the angle to zero. If entering position mode doesn't yet do the reset to a zero angle, that should be a fix that even I could add to the code :-)
So, the position mode of #231 should fulfill my desired feature request. And, to be honest, the other two modes do look useful. If I can convince myself that the code is stable, I'll jump onto that branch.
That seems smart.
I'd think that if entering the position mode reset the angle, it would also reset threading start, though. :thinking:
I wonder whether having a separate "display angle" offset and resetting that offset such that the display is zero when entering position mode would be the best way? Maybe the UserInterface
could hold and apply the offset, leaving the angle in the Encoder
alone?
Don't you lose threading start when you go to position mode regardless? You'd have to leave the "Thread to Shoulder" mode to select a new mode. And if you wanted to go back to threading, you'd need to select a new mode?
The display angle can definitely be different than the "encoder" value. To zero (at the start of position mode), it should read and store the initial encoder value (effectively storing the zero position). Then the display routine can display the difference of the current encoder position to the saved encoder position. Converted to degrees and tenths. Always a positive value that is never more than 360. I'm sure there's a modulo operation and an ABS operation in the line...or something like that.
I may get to load and try the #231 code this afternoon.
You are right, I was over-thinking it.
In any case, the angle is kept in a Uint16
integer that holds (I think) tenths of a degree, so you can use the %
modulo operator. Just add a positive offset and then % 3600
I didn't get to try it, but I am looking at the code. In Encoder.cpp of the #231 branch, the last few lines read:
Uint16 Encoder :: getSpindleAngle(void) { spindleAngle = (getPosition() % ENCODER_RESOLUTION * 3600) / ENCODER_RESOLUTION; return spindleAngle; }
There are are least two statements in that file initializing spindle angle to zero.
I got the #231 code built and loaded.
Unfortunately, the angle readout currently doesn't get reset when the "position mode" is entered. It's hard to hit zero, but it is possible with a tapity-tap-tap action on the spindle.
I'm going to think a bit about next steps. I like the idea of the other features, but it does add significant complexity to the operator interface. The limits of the display and the buttons are the biggest cause of this.
One other thought nagging at me is that there is no emergency stop for the feed in Thread to Shoulder. The thread to Shoulder function moves the carriage based on a button press and stopping that would not be easy using the "power" key on the Clough42 display.
I'm just glancing at the code, and haven't thought through it, but I'm expecting that resetting the encoder when exiting the menu if showing the angle has been selected would work. Something vaguely like this:
case kShowPosition+2: // run loop
showAngle = !showAngle;
if (showAngle) {
encoder->reset();
}
clearMessage();
this->menuState = kQuitMenu;
break;
For emergency stop, I think that a real emergency stop never depends on logic in code. I power my ELS through a power supply behind a contactor that is piggy-backed off the main lathe contactor, so the lathe emergency stop stops the ELS along with the lathe motor.
I agree....that's where it needs to go.
Our "reset solution" at the beginning of Position mode is viable only if there's no usage/need for carrying Encoder state information thru to allow any other function to work.
- I believe all of the legacy functions are stateless with respect to any particular set of encoder values.....it's just moving the carriage feed in response to changes in the encoder readings.
- The Custom Threads mode doesn't use encoder functionality, it's just building and setting a parameter to be used by other modes.
- The Thread to Shoulder mode does use encoder values for moving between the Start and the Shoulder position (and vice versa). But I believe there's no possible way to return into the Thread to Shoulder mode that would continue a previous Thread to Shoulder operation. So Thread to Shoulder, as defined will always load new values from the encoder at the beginning of operation to set Start and Shoulder.
I'll give this new code a try. If it works, I think we should ask that it be merged into this branch. Beginning Position mode with a known angle (zero) shouldn't ever be worse than starting it with a random angle (after all, it could be zero by chance). And, for those who are math challenged, it's much better.
I did say "vaguely" — but I've edited out the errant character.
If it works, I don't mind creating the PR for it.
No dice. for the test. :-(
The change does reset the displayed angle to zero. But there's an artifact. At the moment of the hitting "set" to select Position mode, there's a sudden movement of the leadscrew (or hex bar). I didn't spend much time characterizing the movement...but it was not subtle. On the one occurrence where I opened the gear cover to watch, it rotated the input shaft to the gearbox ~180 degrees. To me, it's unacceptable (and a bit scary) to see unintended motion.
While I suspect it is possible to code some sort of safe reset, it now definitely seems like a better idea to record the initial reported angle upon entering position mode. Then modify the angle display routine to offset the current angle by the initial angle each time the angle is displayed. This seems like a very safe option.
OK, back to my original idea of storing an offset in the UserInterface
...
kwackers/electronic-leadscrew#4 is my untested attempt to implement that. I'm away from my lathe at the moment, so like my first idea it's untested. But if you test it and it works, I can take it out of draft and ask @kwackers to consider merging it.
Hello guys. I just got the notification that someone had posted something, so a quick scan of the posts and a quick scan of the code to see what's happening. Bearing in mind the code falls into the category of "code I wrote more than a week ago" I'm just wondering if something like "press and hold set to reset" wouldn't be better?
I did at some point consider allowing the display to show the physical position of the saddle too - "press and hold" would also work there (should it ever get implemented).
My main thoughts are: Press and hold is a common way to zero something. It's use doesn't preclude coming out of the angle mode and going back in without losing the position.
Thoughts?
That would delay the menu until releasing SET, but yeah that could work. No promises but I might take a crack at it...
Press and Hold set to reset the displayed angle sounds great with one caveat. "Resetting the displayed angle" should never make the stepper or servo seek a new position.
If we need to create a separate angle variable for the display in order to avoid upsetting the other functionality of the ELS, Michael Johnson has graciously offered a starting point for the code.
I'm willing to do testing as needed.
Yeah, I won't reset()
the encoder — your earlier test showed that would be a bad idea. My original idea three days ago was right after all. :grin:
Restating to make sure I understand right: The proposal here is that instead of resetting the display-only offset when going into angle display mode, we should reset the display-only offset only on a long-press of SET, only if it is already in angle display mode. (Later, it might reset the display-only linear carriage offset, only if it is already in the proposed new carriage offset mode.)
@R-Ronald I don't know whether what I just force-pushed to the branch will even compile, since I'm not even near the system that has the development environment installed let alone near the lathe, but if you'd like to test it, let me know both of any stupid mistakes like the extra .
as well as whether it works...
I had a different idea about how things should work.
I thought that Position Mode could be selected w/o forcing the angle to zero by a short set button press or it could be selected along with forcing the initial angle to zero by a long set button press. Both options enter the mode and are doing a similar function.
Otherwise, once in Position mode the set button press either exits the mode (when short) or resets the angle (when long). The two options use one key, but are totally different functions.
Quick look at the code (whilst waiting for stuff to build here). In ControlPanel :: isStable the code waits for the keypresses to settle, this function could be expanded to allow the setting of a ControlPanel::isHeld value if the button is held beyond some predetermined time. I'd change the line if( this->stableCount < MIN_CONSECUTIVE_READS ) to check against HELD_TIME instead and set 'isHeld' if that occurs (as well as clearing it when the statement isn't true).
In UserInterface :: mainLoop that needs to enter a state when the set button is pressed instead of immediately calling the menu. e.g. "WaitForSetReleaseOrHeld" - that sort of thing. Then each loop it'll check that state and make sure the set button is still held, if not then call the menu, if it is then wait until Control::isHeld becomes true at which point you can clear the angle. Once the angle is cleared the above state needs to advance so that it knows not to call the menu when the button is finally released.
I can easily add this functionality as some point if you wish - just need a bit of time to grab the controller off the lathe for testing.
FWIW I think the current system of having the 'mode' for the display permanent until deliberately changed is preferable to 'cancelling' it by pressing the Set button and I can't say I'd be a fan of having two mechanisms of entering angle mode one of which clears. Simply clearing it by pressing and holding Set seems far simpler and less confusing to me.
I think I'll want to actually trace through this when I get back to my lathe to make sure I understand the state machines in the UserInterface
correctly.
I think the code to read the keypad should look something like this: (With suitable value for HOLD_TIME)
bool ControlPanel :: isStable(KEY_REG testKeys) {
// don't trust any read key state until we've seen it multiple times consecutively (noise filter)
if( testKeys.all != stableKeys.all )
{
this->stableKeys = testKeys;
this->stableCount = 1;
this->isHeld = false;
}
else
{
if (this->stableCount < HOLD_TIME)
{
this->stableCount++;
}
else
{
this->isHeld = true;
}
}
return this->stableCount >= MIN_CONSECUTIVE_READS;
}
OK, doing it in the ControlPanel
instead. I wondered which way would make more sense. Then I can throw away my current attempt and start over once I have the chance to debug at my lathe... ☺
And the code for the keypress in UserInterface::mainLoop like this: (With setHeldState added and the function clearAngle defined)
if( keys.bit.SET )
{
// set pressed
this->setHeldState = 1;
// has it been held long enough?
if (this->controlPanel.isHeld)
{
// clear angle and prevent menu appearing when released
clearAngle();
this->setHeldState = 2;
}
}
else
{
// set has been pressed and released
if (this->setHeldState == 1)
beginMenu();
this->setHeldState = 0;
}
Of course I haven't tried any of the above... ;)
So, I was busy today...actually running my lathe. I'd 3d printed a gear to drive the ELS encoder, and was machining an aluminum replacement (3d part is fine, but I have a lathe and feel compelled to use it :-)
The ELS was great. Makes everything much quieter. And quieter seems less stressful too.
But, I can see a couple more operations that could be improved by ELS modes. So I'll just throw these out as an idea to see what you think.
- First, I was boring out an 8mm bore pulley to 48mm. I'm uncertain of my workholding, so I didn't want to take big cuts. Was doing .5 to .7 mm off the diameter for each pass. Thus, I had to do a lot of cuts (~70?). It would be nice to have something like the Thread to Shoulder for normal cuts (I was doing an internal bore, but external would be the same).
Set the Start, Set the end, and go. For the feeding I was doing the spindle didn't even need to stop. Feed from start to end, stop feed, reverse feed back to start and repeat. It could be done w/o any further operator panel interaction. You could have a pause of a second or two at each direction change to allow time to move the cross slide....or not (you actually already have a mechanical pause during reversals due to backlash.
I'd call it PingPong mode. One could cut in both directions (although I would have been chicken to do this since it would be trying to pull the weakly held part from the chuck)....or the reverse could be at a faster travel rate.
Turning off the spindle could be used to signal a stop for the PingPong action.
- Once I completed the bore, I had to broach a keyway. Lots of hard work running the carriage back and forth w/o the spindle even turning. Again, there's a start point and a stop point. Ping pong between the two. On this, you'd almost certainly not want to stop at the endpoints.
The broach operation is a bit scary. If you attempt to cut too deeply when moving the carriage by hand for broaching, it just klunks to a stop. Not sure what the servo would do if it was pushing and was stopped (trips off?) and whether the resistance makes for a hard crash or just stall w/o breaking anything.
RR
I found that a gear printed in PETG actually allowed me to increase stiffness without feedback (as indicated in my Hobby-Machinist comment in the thread we're both in there: https://www.hobby-machinist.com/threads/has-anyone-installed-clough42s-electronic-leadscrew-on-a-pm-machine.95057/post-1094101 — So even though I bought 1.5 module cutters expressly to cut a brass gear, I changed my mind and haven't used them.
On my lathe, the feed bar has a clutch. If that tripped, it would of course invalidate position. (I've never tripped it, as far as I recall.)
I'd almost certainly use a "turn to shoulder" mode myself. I've thought already about adding it. If I do I'll put up a PR for it. But I'd suggest tracking that as a separate feature suggestion. I would definitely cut in one direction and just use fast reverse, which the ELS makes easy.
I definitely wouldn't use it for broaching. If the servo trips overcurrent, you have to power-cycle it. And broaching is a higher force operation, more likely to do damage.
Thread to shoulder together with fine feed works well for machining stuff but an automatic return would be nice (I've never owned a lathe that didn't take a shaving off returning). So some sort of ping pong mode is worth a punt, needs playing with a bit since often you want to move the carriage out of the way to take some measurements (or at least I do) so would need some mechanism to allow that without losing the setup.