Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/Duet3D/RepRapFirmware.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Crocker <dcrocker@eschertech.com>2018-02-15 19:29:12 +0300
committerDavid Crocker <dcrocker@eschertech.com>2018-02-15 19:29:28 +0300
commit6629a8d0d5372637c70217f3bdfb0c0d339f21d1 (patch)
tree9274b9311978326aa24989e758f3a8928cea0508 /src/Movement
parent56ce29027a745be0def9d53168513f8ecafd0208 (diff)
Version 1.21RC2
The filament usage comments generated by Ideamaker are now recognised A separate Z probe type (P9 in M558) is now used for BLTouch and compatible Z probes. When this is selected, the deployprobe.g macro is run just before each probing move, and retractprobe.g is run every time the probe triggers, or at the end of the probing move if it doesn't trigger All heaters are turned off during probing moves if parameter B1 is specified in the M558 command The M671 command can be used with just one pair of X and Y coordinates, which disables the manual bed calibration assistant Continuous rotation proximal and distal joints are now supported on SCARA printers, and continuous rotation turntables are assumed on Polar printers When beginning a print from SD card, macro /sys/start.g is run if it is present Sending M0 or M1 from a source other than the SD card no longer stops an SD card print that is not paused When a serial input channel detects a framing or overrun error other than in a GCode end-of-line comment, the line of GCode in which it occurs is discarded When the M207 Z hop setting was changed during a print while a travel move is in progress, at the end of the travel move the head was lowered by the new value for Z hop instead of the original value Endstop pins 5-9 (E2-E6) on the expansion connector are now working If neither of the /www/reprap.htm and /www/html404.htm files was present when the web server as asked to fetch a file, it returned a 404 error, however there was no associated plain text response so most browsers displayed a blank screen (fixed in Duet WiFi/Ethernet build only) If a G0 or G1 command resulted in no movement (e.g. because it was a duplicate of a previous line) then correct synchronisation between subsequent movement and non-movement commands was lost
Diffstat (limited to 'src/Movement')
-rw-r--r--src/Movement/DDA.cpp27
-rw-r--r--src/Movement/Kinematics/Kinematics.h3
-rw-r--r--src/Movement/Kinematics/PolarKinematics.cpp6
-rw-r--r--src/Movement/Kinematics/PolarKinematics.h1
-rw-r--r--src/Movement/Kinematics/ScaraKinematics.cpp22
-rw-r--r--src/Movement/Kinematics/ScaraKinematics.h4
-rw-r--r--src/Movement/Kinematics/ZLeadscrewKinematics.cpp5
-rw-r--r--src/Movement/Move.cpp6
8 files changed, 60 insertions, 14 deletions
diff --git a/src/Movement/DDA.cpp b/src/Movement/DDA.cpp
index 3d41bdc8..54fe9e95 100644
--- a/src/Movement/DDA.cpp
+++ b/src/Movement/DDA.cpp
@@ -271,6 +271,8 @@ bool DDA::Init(GCodes::RawMove &nextMove, bool doMotorMapping)
float accelerations[DRIVES];
const float * const normalAccelerations = reprap.GetPlatform().Accelerations();
const size_t numAxes = reprap.GetGCodes().GetTotalAxes();
+ const Kinematics& k = move.GetKinematics();
+
for (size_t drive = 0; drive < DRIVES; drive++)
{
accelerations[drive] = normalAccelerations[drive];
@@ -280,7 +282,27 @@ bool DDA::Init(GCodes::RawMove &nextMove, bool doMotorMapping)
}
endCoordinates[drive] = nextMove.coords[drive];
- const int32_t delta = (drive < numAxes) ? endPoint[drive] - positionNow[drive] : endPoint[drive];
+ int32_t delta;
+ if (drive < numAxes)
+ {
+ delta = endPoint[drive] - positionNow[drive];
+ if (k.IsContinuousRotationAxis(drive))
+ {
+ const int32_t stepsPerRotation = lrintf(360.0 * reprap.GetPlatform().DriveStepsPerUnit(drive));
+ if (delta > stepsPerRotation/2)
+ {
+ delta -= stepsPerRotation;
+ }
+ else if (delta < -stepsPerRotation/2)
+ {
+ delta += stepsPerRotation;
+ }
+ }
+ }
+ else
+ {
+ delta = endPoint[drive];
+ }
if (drive < numAxes && doMotorMapping)
{
@@ -390,7 +412,6 @@ bool DDA::Init(GCodes::RawMove &nextMove, bool doMotorMapping)
// There is some XY movement, so normalise the direction vector so that the total XYZ movement has unit length and 'totalDistance' is the XYZ distance moved.
// This means that the user gets the feed rate that he asked for. It also makes the delta calculations simpler.
// First do the bed tilt compensation for deltas.
- const Kinematics& k = move.GetKinematics();
directionVector[Z_AXIS] += (directionVector[X_AXIS] * k.GetTiltCorrection(X_AXIS)) + (directionVector[Y_AXIS] * k.GetTiltCorrection(Y_AXIS));
totalDistance = NormaliseXYZ();
@@ -446,7 +467,7 @@ bool DDA::Init(GCodes::RawMove &nextMove, bool doMotorMapping)
// for diagonal moves. On a delta, this is not OK and any movement in the XY plane should be limited to the X/Y axis values, which we assume to be equal.
if (doMotorMapping)
{
- reprap.GetMove().GetKinematics().LimitSpeedAndAcceleration(*this, normalisedDirectionVector); // give the kinematics the chance to further restrict the speed and acceleration
+ k.LimitSpeedAndAcceleration(*this, normalisedDirectionVector); // give the kinematics the chance to further restrict the speed and acceleration
}
// 7. Calculate the provisional accelerate and decelerate distances and the top speed
diff --git a/src/Movement/Kinematics/Kinematics.h b/src/Movement/Kinematics/Kinematics.h
index bfc90fef..b6bd0c5e 100644
--- a/src/Movement/Kinematics/Kinematics.h
+++ b/src/Movement/Kinematics/Kinematics.h
@@ -156,6 +156,9 @@ public:
// The speeds along individual Cartesian axes have already been limited before this is called.
virtual void LimitSpeedAndAcceleration(DDA& dda, const float *normalisedDirectionVector) const = 0;
+ // Return true if the specified axis is a continuous rotation axis
+ virtual bool IsContinuousRotationAxis(size_t axis) const { return false; }
+
// Override this virtual destructor if your constructor allocates any dynamic memory
virtual ~Kinematics() { }
diff --git a/src/Movement/Kinematics/PolarKinematics.cpp b/src/Movement/Kinematics/PolarKinematics.cpp
index 0084dd85..c9781ada 100644
--- a/src/Movement/Kinematics/PolarKinematics.cpp
+++ b/src/Movement/Kinematics/PolarKinematics.cpp
@@ -250,6 +250,12 @@ void PolarKinematics::LimitSpeedAndAcceleration(DDA& dda, const float *normalise
}
}
+// Return true if the specified axis is a continuous rotation axis
+bool PolarKinematics::IsContinuousRotationAxis(size_t axis) const
+{
+ return axis == 1;
+}
+
// Update the derived parameters after the master parameters have been changed
void PolarKinematics::Recalc()
{
diff --git a/src/Movement/Kinematics/PolarKinematics.h b/src/Movement/Kinematics/PolarKinematics.h
index 58b0cc36..fa5c670c 100644
--- a/src/Movement/Kinematics/PolarKinematics.h
+++ b/src/Movement/Kinematics/PolarKinematics.h
@@ -30,6 +30,7 @@ public:
bool QueryTerminateHomingMove(size_t axis) const override;
void OnHomingSwitchTriggered(size_t axis, bool highEnd, const float stepsPerMm[], DDA& dda) const override;
void LimitSpeedAndAcceleration(DDA& dda, const float *normalisedDirectionVector) const override;
+ bool IsContinuousRotationAxis(size_t axis) const override;
private:
static constexpr float DefaultSegmentsPerSecond = 100.0;
diff --git a/src/Movement/Kinematics/ScaraKinematics.cpp b/src/Movement/Kinematics/ScaraKinematics.cpp
index 2fae5433..34634891 100644
--- a/src/Movement/Kinematics/ScaraKinematics.cpp
+++ b/src/Movement/Kinematics/ScaraKinematics.cpp
@@ -61,10 +61,10 @@ bool ScaraKinematics::CalculateThetaAndPsi(const float machinePos[], bool isCoor
if (armMode != switchedMode)
{
// The following equations choose arm mode 0 i.e. distal arm rotated anticlockwise relative to proximal arm
- if (psi >= psiLimits[0] && psi <= psiLimits[1])
+ if (supportsContinuousRotation[1] || (psi >= psiLimits[0] && psi <= psiLimits[1]))
{
theta = atan2f(SCARA_K1 * y - SCARA_K2 * x, SCARA_K1 * x + SCARA_K2 * y);
- if (theta >= thetaLimits[0] && theta <= thetaLimits[1])
+ if (supportsContinuousRotation[0] || (theta >= thetaLimits[0] && theta <= thetaLimits[1]))
{
break;
}
@@ -73,10 +73,10 @@ bool ScaraKinematics::CalculateThetaAndPsi(const float machinePos[], bool isCoor
else
{
// The following equations choose arm mode 1 i.e. distal arm rotated clockwise relative to proximal arm
- if ((-psi) >= psiLimits[0] && (-psi) <= psiLimits[1])
+ if (supportsContinuousRotation[1] || ((-psi) >= psiLimits[0] && (-psi) <= psiLimits[1]))
{
theta = atan2f(SCARA_K1 * y + SCARA_K2 * x, SCARA_K1 * x - SCARA_K2 * y);
- if (theta >= thetaLimits[0] && theta <= thetaLimits[1])
+ if (supportsContinuousRotation[0] || (theta >= thetaLimits[0] && theta <= thetaLimits[1]))
{
psi = -psi;
break;
@@ -430,17 +430,27 @@ void ScaraKinematics::LimitSpeedAndAcceleration(DDA& dda, const float *normalise
}
}
+// Return true if the specified axis is a continuous rotation axis
+bool ScaraKinematics::IsContinuousRotationAxis(size_t axis) const
+{
+ return axis < 2 && supportsContinuousRotation[axis];
+}
+
// Recalculate the derived parameters
void ScaraKinematics::Recalc()
{
proximalArmLengthSquared = fsquare(proximalArmLength);
distalArmLengthSquared = fsquare(distalArmLength);
- twoPd = proximalArmLength * distalArmLength * 2.0f;
+ twoPd = proximalArmLength * distalArmLength * 2;
minRadius = sqrtf(proximalArmLengthSquared + distalArmLengthSquared
- twoPd * max<float>(cosf(psiLimits[0] * DegreesToRadians), cosf(psiLimits[1] * DegreesToRadians))) * 1.005;
- if (psiLimits[0] < 0.0 && psiLimits[1] > 0.0)
+ // If the total angle range is greater than 360 degrees, we assume that it supports continuous rotation
+ supportsContinuousRotation[0] = (thetaLimits[1] - thetaLimits[0] > 360.0);
+ supportsContinuousRotation[1] = (psiLimits[1] - psiLimits[0] > 360.0);
+
+ if (supportsContinuousRotation[1] || (psiLimits[0] <= 0.0 && psiLimits[1] >= 0.0))
{
// Zero distal arm angle is reachable
maxRadius = proximalArmLength + distalArmLength;
diff --git a/src/Movement/Kinematics/ScaraKinematics.h b/src/Movement/Kinematics/ScaraKinematics.h
index 36efbe83..b6193b6a 100644
--- a/src/Movement/Kinematics/ScaraKinematics.h
+++ b/src/Movement/Kinematics/ScaraKinematics.h
@@ -41,6 +41,7 @@ public:
bool QueryTerminateHomingMove(size_t axis) const override;
void OnHomingSwitchTriggered(size_t axis, bool highEnd, const float stepsPerMm[], DDA& dda) const override;
void LimitSpeedAndAcceleration(DDA& dda, const float *normalisedDirectionVector) const override;
+ bool IsContinuousRotationAxis(size_t axis) const override;
private:
static constexpr float DefaultSegmentsPerSecond = 100.0;
@@ -63,9 +64,10 @@ private:
float distalArmLength;
float thetaLimits[2]; // minimum proximal joint angle
float psiLimits[2]; // minimum distal joint angle
- float crosstalk[3]; // if we rotate the distal arm motor, for each full rotation the Z height goes up by this amount
+ float crosstalk[3]; // proximal to distal, proximal to X and distal to Z crosstalk
float xOffset; // where bed X=0 is relative to the proximal joint
float yOffset; // where bed Y=0 is relative to the proximal joint
+ bool supportsContinuousRotation[2]; // true if the (proximal, distal) arms support continuous rotation
// Derived parameters
float minRadius, minRadiusSquared;
diff --git a/src/Movement/Kinematics/ZLeadscrewKinematics.cpp b/src/Movement/Kinematics/ZLeadscrewKinematics.cpp
index db43dbc1..1e263e8b 100644
--- a/src/Movement/Kinematics/ZLeadscrewKinematics.cpp
+++ b/src/Movement/Kinematics/ZLeadscrewKinematics.cpp
@@ -29,6 +29,7 @@ bool ZLeadscrewKinematics::Configure(unsigned int mCode, GCodeBuffer& gb, const
{
// Configuring leadscrew positions.
// We no longer require the number of leadscrews to equal the number of motors. If there is a mismatch then auto calibration just prints the corrections.
+ // We now allow just 1 pair of coordinates to be specified, which in effect clears the M671 settings.
bool seenX = false, seenY = false;
size_t xSize = MaxLeadscrews, ySize = MaxLeadscrews;
if (gb.Seen('X'))
@@ -48,7 +49,7 @@ bool ZLeadscrewKinematics::Configure(unsigned int mCode, GCodeBuffer& gb, const
bool seenP = false;
gb.TryGetFValue('P', screwPitch, seenP);
- if (seenX && seenY && xSize == ySize && xSize > 1)
+ if (seenX && seenY && xSize == ySize)
{
numLeadscrews = xSize;
return false; // successful configuration
@@ -56,7 +57,7 @@ bool ZLeadscrewKinematics::Configure(unsigned int mCode, GCodeBuffer& gb, const
if (seenX || seenY)
{
- reply.copy("Specify 2, 3 or 4 X and Y coordinates in M671");
+ reply.copy("Specify 1, 2, 3 or 4 X and Y coordinates in M671");
return true;
}
diff --git a/src/Movement/Move.cpp b/src/Movement/Move.cpp
index b779b735..93adf343 100644
--- a/src/Movement/Move.cpp
+++ b/src/Movement/Move.cpp
@@ -217,6 +217,7 @@ void Move::Spin()
{
AxisAndBedTransform(nextMove.coords, nextMove.xAxes, nextMove.yAxes, true);
}
+
if (ddaRingAddPointer->Init(nextMove, !IsRawMotorMove(nextMove.moveType)))
{
ddaRingAddPointer = ddaRingAddPointer->GetNext();
@@ -234,6 +235,7 @@ void Move::Spin()
lastStateChangeTime = now;
}
}
+
#if 0 // see above
// Save the amount of extrusion not done
for (size_t drive = numAxes; drive < DRIVES; ++drive)
@@ -373,7 +375,7 @@ bool Move::IsRawMotorMove(uint8_t moveType) const
// Return true if the specified point is accessible to the Z probe
bool Move::IsAccessibleProbePoint(float x, float y) const
{
- const ZProbeParameters& params = reprap.GetPlatform().GetCurrentZProbeParameters();
+ const ZProbe& params = reprap.GetPlatform().GetCurrentZProbeParameters();
return kinematics->IsReachable(x - params.xOffset, y - params.yOffset, false);
}
@@ -1168,7 +1170,7 @@ float Move::GetProbeCoordinates(int count, float& x, float& y, bool wantNozzlePo
y = probePoints.GetYCoord(count);
if (wantNozzlePosition)
{
- const ZProbeParameters& rp = reprap.GetPlatform().GetCurrentZProbeParameters();
+ const ZProbe& rp = reprap.GetPlatform().GetCurrentZProbeParameters();
x -= rp.xOffset;
y -= rp.yOffset;
}