Out of the plane

What a mechanism cannot do

A mechanism's freedoms are a subspace of screw space. Everything orthogonal to that subspace under the reciprocal product is a force the mechanism carries without moving — so the constraints are not a separate thing to be worked out, they are what is left, and one matrix gives both.

Assumes Every motion is a screw and Counting and measuring mobility.

The spatial solver on this site has computed one number about every closed loop it has ever drawn: the rank of the matrix whose columns are the joint screws. That rank is the mobility, measured rather than counted, and it is what caught Kutzbach’s formula declaring a universal joint immobile.

A rank is an integer. It says how many independent directions a set of vectors has and nothing about which ones. For mobility that is enough, because mobility is a count. For everything else it is a receipt for a computation whose answer was thrown away.

This essay keeps the answer. The joint screws span a subspace of the six-dimensional space of screws — the mechanism’s screw system — and the subspace is a far more informative object than its dimension. In particular it has a complement, and the complement turns out to be the forces the mechanism carries.

What each loop's constraint system is made of. For each mechanism: the order of the screw system its joints span, the order of the reciprocal system — the wrenches it carries without moving, which is always six minus the first — and what those wrenches are. A planar four-bar carries one force and two couples; a mechanism whose motion lies in no subgroup carries screws of finite pitch instead, and 2 of these 6 do.
Fig. 1 Six loops, each solved, each reduced to two numbers and a phrase. The middle column is the order of the screw system the joints span; the right-hand column is what is reciprocal to it. Nothing in the computation was told that the first mechanism is planar or that the second is spherical — the phrase in each row is read off a subspace.

The definition, which is one line

From the previous rung: the reciprocal product of two screws is

$1,$2=ω1v2+ω2v1\langle \$_1, \$_2 \rangle = \omega_1 \cdot v_2 + \omega_2 \cdot v_1

and when one screw is read as a motion and the other as a force system, it is the rate at which the force does work on the motion.

So a force system that is reciprocal to every motion a chain permits does no work on that chain, ever, in any configuration it can reach. Push on it and nothing yields. That is what a constraint is, stated without using the word: a wrench the chain carries straight through to ground.

The set of such wrenches is the reciprocal system, and computing it is a change of variables and a null space. Reciprocity says ωim+vif=0\omega_i \cdot m + v_i \cdot f = 0 for every joint screw [ωi;vi][\omega_i ; v_i] and every constraint wrench [f;m][f ; m]. Swap the two halves of each joint screw, writing $^i=[vi;ωi]\hat\$_i = [v_i ; \omega_i], and the condition becomes an ordinary dot product:

$^i[f;m]=0\hat\$_i \cdot [f ; m] = 0

The reciprocal system is therefore the orthogonal complement of the swapped joint screws. That is the whole computation. Swap, take the complement.

Two things follow immediately and both are used everywhere downstream. Its dimension is 6r6 - r, where rr is the rank the solver was already computing — so a leg with three freedoms imposes three constraints and a leg with six imposes none, with no rule to remember. And it costs nothing beyond a decomposition of a six-by-n matrix that has already been formed.

Why rank could not do this

lib/mechanism.js has had a rank routine since the foundation. It row-reduces with partial pivoting, counts pivots, and reports how close the decision was. It is correct and it is useless here.

Row reduction destroys the geometry on the way to the count. The pivot rows it leaves behind do span the right space, but in a basis produced by whatever order the pivots happened to come out in, and the rows it discards are not a basis of the complement — they are zero. There is nothing left to draw.

So this field needed a second piece of linear algebra: an orthonormal eigenbasis of AATA A^{\mathsf T}, from which the column space and its complement both fall out, ordered by how strongly the matrix acts on each direction. symmetricEigen sits next to rank in lib/mechanism.js for that reason — cyclic Jacobi, sixty sweeps, six by six at most. Jacobi rather than anything cleverer because it is accurate on precisely the case that matters here, which is a matrix with a genuinely tiny eigenvalue. An overconstrained mechanism’s screw system is exactly that.

The eigenvalues are the squared singular values, so the same rank decision is available from the same evidence — and subspace reports the ratio of the smallest kept singular value to the largest discarded one, which is what rank has always reported and for the same reason. A ratio near one means the order is a matter of the tolerance, and that is the situation at a singularity. It is content, not an embarrassment.

Kutzbach's count against the measured mobility. Five closed loops of revolute joints. The count is 6(L − 1) − 5j, a statement about how many links and joints there are; the measurement is the number of joints minus the rank of the loop's screw system, which knows only where the axes point. They disagree for four of the five, and the one they agree on is the generic seven-joint loop — so the formula is not broken, it is blind to the special geometry that makes the other four work. The universal joint is counted at -2 degrees of freedom and is in every car built.
Fig. 2 What the rank was being used for until now. Five loops, Kutzbach’s count against the mobility measured from the rank of the joint screws, with the universal joint’s row marked. The count and the measurement disagree on four of the five. Everything in this essay is what happens when the subspace behind that rank is kept instead of discarded.

Normalising, and the thing it does not fix

A screw’s moment part grows with the distance from the origin to its axis. Two joints of the same mechanism, one near the frame and one at the far end of a long link, produce screws whose six numbers differ in size by whatever the ratio of those distances is.

Feed those to an eigendecomposition unnormalised and the far joints decide the rank. The answer then depends on where the coordinate frame was put, which is not a property of the mechanism at all.

So subspace normalises every screw to unit length first, and the docstring says plainly what that does and does not buy. It makes the decision depend on the directions and the relative positions, which is the geometry. It does not make the answer origin-independent, because nothing can: a rank threshold applied to a basis is a judgement, and a frame far enough away will still swamp it.

What holds the site to a frame where the answer is stable is a check. assertOrdersSurviveMovingTheOrigin translates the coordinate frame by about the size of the mechanism — (0.9, −0.6, 1.3), a shift of 1.69 against links of order one — recomputes every order and the redundancy, and requires them all to be unchanged. They are, on all nine loops the site builds. That is the kind of claim that should be tested rather than argued, because the argument is short and unconvincing and the test is one line.

What planar four-bar carries. The mechanism at 40°, with the wrench system reciprocal to its joint screws drawn on it. It carries one force and two couples: a force is drawn as its line of action, because that is all a force of zero pitch is, and a couple as a ring about its direction, because a couple has no line of action at all and acts the same about every point. Everything here comes from the 3-dimensional screw system the joints span; the wrenches are its orthogonal complement under the reciprocal product.
Fig. 3 A planar four-bar built as a spatial loop, with what it carries drawn on it. One force, whose line of action runs out of the plane, and two couples, drawn as rings about the directions they act about — a couple has no line of action at all, which is the thing about a couple worth seeing in a picture. Nothing told the computation that this mechanism is planar.

The planar result, which anybody can check against intuition

Take four revolute axes, all parallel to , through four points in the plane z=0z = 0. Their screws are [0,0,1 ; q×z^][0,0,1\ ;\ q \times \hat z], and since q lies in the plane, q×z^q \times \hat z lies in it too. The span of four such screws is

{(0, 0, ωz ; vx, vy, 0)}\{ (0,\ 0,\ \omega_z\ ;\ v_x,\ v_y,\ 0) \}

— three-dimensional, which is the three freedoms of planar motion arriving from the spatial description rather than being assumed.

Now ask which wrenches [f;m][f ; m] are reciprocal to all of it: ωzmz+vxfx+vyfy=0\omega_z m_z + v_x f_x + v_y f_y = 0 for every ωz,vx,vy\omega_z, v_x, v_y. That forces mz=0m_z = 0, fx=0f_x = 0 and fy=0f_y = 0, leaving

{(0, 0, fz ; mx, my, 0)}\{ (0,\ 0,\ f_z\ ;\ m_x,\ m_y,\ 0) \}

A force along , and couples about and ŷ. In words: a planar linkage resists nothing in its own plane and everything out of it. It carries a load pushing it out of the page, and it carries a bending moment trying to fold it about either in-plane axis, and it carries neither an in-plane force nor a twist about the perpendicular.

That is a sentence anybody who has held a piece of cardboard already believes, and the point of deriving it is not to establish it. The point is that the derivation was performed by a routine that was handed four columns of numbers and told nothing else, and that the same routine applied to a mechanism nobody has intuitions about will produce an answer of the same standing.

assertPlanarConstraintIsAForceAndTwoCouples gates it: order 3, one force, two couples, and the directions true to zero — not near zero, exactly zero, because the arithmetic in this case is exact.

What the other mechanisms carry

Running the same computation across the site’s loops gives the table in the hero figure, and four of its rows deserve saying in words.

The universal joint and the spherical four-bar carry three forces, all through the centre. Every axis of a spherical mechanism passes through one point, so every joint screw is [ω;0][\omega ; 0] and reciprocity requires ωm=0\omega \cdot m = 0 for all ω, hence m=0m = 0: three pure forces, no couples at all. Physically that is the statement that a spherical joint arrangement transmits force to its centre and no moment about it, which is why a universal joint’s yoke is loaded in bearing and not in torsion.

The Sarrus linkage carries one couple. Its six joint screws span a five-dimensional system, so only one dimension is left, and the wrench in it is a couple about the direction the plate translates along. The mechanism gives an exact straight line and the one thing it cannot resist is being twisted about that line.

Bennett’s linkage carries three screws. Not forces, not couples — screws, with an axis and a finite pitch each. That row is the one this whole ladder is climbing towards, because there is no subgroup of the rigid displacements whose reciprocal is a set of finite-pitch screws, and so no name for what Bennett’s mechanism is doing. The essay after next is about what follows from that.

The generic seven-joint loop carries nothing. Its joint screws span the whole six-dimensional space, so the complement is empty: there is no wrench a seven-joint spatial loop resists without moving. It is the case Kutzbach’s formula gets right, and here is the reason stated in a different vocabulary — nothing is being constrained twice, because nothing is being constrained at all beyond what the joint count already accounts for.

What Sarrus carries. The mechanism at 35°, with the wrench system reciprocal to its joint screws drawn on it. It carries one couple: a force is drawn as its line of action, because that is all a force of zero pitch is, and a couple as a ring about its direction, because a couple has no line of action at all and acts the same about every point. Everything here comes from the 5-dimensional screw system the joints span; the wrenches are its orthogonal complement under the reciprocal product.
Fig. 4 The Sarrus linkage, whose two three-joint chains lie in perpendicular planes. Five of the six dimensions of screw space are spanned by its joints, so one wrench is left reciprocal to all of them, and it is a couple about the direction the plate travels in. A mechanism that produces an exact straight line by pin joints alone, and the single thing it does not resist is a twist about that line.

The check that the complement is a complement

An assertion that a computed subspace is the reciprocal system has to test reciprocity rather than dimension, because the dimension is right by construction and would stay right if the vectors were wrong.

assertReciprocalSystemIsReciprocal takes every basis wrench and every joint screw and forms the product: the worst is 1.6 × 10⁻¹⁶ on Bennett’s linkage and exactly zero on the mechanisms whose arithmetic happens to be exact. It also requires the order to be 6r6 - r against the independently computed rr, which catches the different failure of a complement that is reciprocal to everything it was given because it is too small.

Both halves are needed and neither is interesting on its own. A basis of the zero subspace is reciprocal to everything.

What Bennett carries. The mechanism at 60°, with the wrench system reciprocal to its joint screws drawn on it. It carries three screws: a force is drawn as its line of action, because that is all a force of zero pitch is, and a couple as a ring about its direction, because a couple has no line of action at all and acts the same about every point. Everything here comes from the 3-dimensional screw system the joints span; the wrenches are its orthogonal complement under the reciprocal product.
Fig. 5 Bennett’s four-bar carrying three screws. The dashed lines are their axes and the small helices say what their pitches are — each is finite, so none of the three is a force and none is a couple. Every other mechanism in the hero table carries some mixture of forces and couples, which are the reciprocals of the subgroups of rigid motion. There is no subgroup whose reciprocal looks like this.

A subspace is not a basis, and comparing them is where this goes wrong

Here is the trap this field sets, and the site fell into it before climbing out.

Two orthonormal bases of the same subspace are different matrices. The eigendecomposition returns whichever basis the Jacobi sweeps happened to produce, and a small change in the input can rotate that basis arbitrarily within the subspace without the subspace moving at all. So comparing constraint systems entry by entry — at one position against another, say — compares mostly the arbitrary part.

The right instrument is principal angles. Given two orthonormal bases B1B_1 and B2B_2, the singular values of B1TB2B_1^{\mathsf T} B_2 are the cosines of the angles between the subspaces, and the smallest of them is the cosine of the largest angle any direction in one makes with the whole of the other. Zero means the same subspace, whatever bases arrived.

There is a floor on what a small answer means, and it is worth stating because the measurement in the next essay but one is a comparison against zero. The angle comes out of an arccosine near 1, where the function is flat: a cosine good to 10⁻¹⁶ gives an angle good to about 2×1016108\sqrt{2 \times 10^{-16}} \approx 10^{-8} radians, or 10⁻⁶ degrees. Measured on the four subgroup mechanisms the answers land between 1.9 × 10⁻⁶ and 3.0 × 10⁻⁶ degrees. That is the floor, not a drift, and a threshold set at zero would be a threshold on the arithmetic.

The other subspace, and why there are two

One distinction has to be drawn before the next essay can be read, because getting it wrong produces a number that looks like a measurement and refutes what it was measuring.

There are two different screw systems in play for a closed loop.

The loop’s own system is the span of every joint screw at once. Its dimension is the rank, its complement is what the loop carries, and it is the object every row of the hero figure describes.

A leg’s system is the span of the joints along one path from ground to a chosen moving link. Its complement is what that leg alone carries — and since a closed loop is two legs holding one moving link, the union of the two legs’ constraints is what actually acts on that link.

These are not the same and they do not behave the same. A leg’s constraint system depends on where that leg’s joints have got to, and it moves for every mechanism there is, subgroup or not. The loop’s does not have to.

The first version of the drift measurement in this ladder measured the union of the two legs’ constraint systems and reported 89 degrees for the planar four-bar — the one mechanism whose constraints certainly do not move. Nothing was wrong with the arithmetic. It was measuring the wrong subspace, and the answer it produced was a perfectly correct number about a quantity nobody wanted.

That is a failure worth naming because it has no symptom. The number was plausible, the code was right, the assertion it was written for would have passed against a threshold chosen after seeing it, and the essay would have contained a measured falsehood. What caught it was a prediction made before the measurement — that a planar four-bar’s constraints are the same three wrenches at every position, which the derivation above establishes on paper — and a measurement that disagreed with it.

What each loop's constraint system is made of. For each mechanism: the order of the screw system its joints span, the order of the reciprocal system — the wrenches it carries without moving, which is always six minus the first — and what those wrenches are. A planar four-bar carries one force and two couples; a mechanism whose motion lies in no subgroup carries screws of finite pitch instead, and 0 of these 5 do.
Fig. 6 The same table with the generic loops brought forward. A six-joint loop with nothing relating its axes spans the whole of screw space, so its reciprocal system is empty and there is nothing for it to carry — and nothing for it to do, since mobility is joints minus rank and six minus six is zero. The seven-joint loop is the same at one joint more, and it moves. Between the two rows sits the whole of the rest of this field: the loops that span less than they should.

The two dimensions sum to six, always

There is an accounting statement underneath the whole rung that is worth writing on its own, because it says the two halves are one quantity and it is what makes the reciprocal system worth computing rather than merely correct.

A freedom system and its reciprocal system are orthogonal complements in a six-dimensional space, so their dimensions add to six, at every configuration, for every mechanism. Three freedoms and three constraints; five and one; six and none. There is no mechanism anywhere with an independent pair of numbers here — the second is six minus the first, and computing either settles both.

That collapses two questions a designer asks separately. What motions does this connection permit and what loads does it carry without moving are the same question, asked from opposite ends, and an answer to one is an answer to the other. A planar loop permits three motions and carries a force out of plane and two couples in it, and those two sentences are the same sentence.

The useful consequence is that a designer may work from whichever end has the shorter description. A serial arm has six freedoms and no constraints, so describing it by its motions is the whole story and its reciprocal system is empty. A parallel platform has three freedoms and three constraints, and its constraints are usually the more informative half — which is why parallel mechanisms are classified by what they forbid, and why a delta’s behaviour is derived from six couples rather than from any statement about translation.

The same accounting is what makes overconstraint visible in the first place. A loop’s joint screws span some order rr; the freedoms are 6r6 - r if nothing repeats and more than that if something does, and the discrepancy shows up in both halves at once. So a mechanism that moves when the count says it should not is a mechanism whose reciprocal system is larger than the count predicts, and the two anomalies are the same anomaly seen from the two sides.

And it explains why the eigendecomposition was worth writing rather than reusing the rank. A rank returns one of the two numbers and discards both subspaces; the decomposition returns both subspaces and the numbers come free. Given that the answer is one object rather than two, the routine that returns the object is the right one and the routine that returns half of a number is not.

What is next

The two legs’ constraint systems are worth having despite that, because their overlap is a quantity nothing else gives. Each leg imposes some constraints; together they impose fewer than the sum, because some are imposed twice; and the difference is the number of redundant constraints.

That number is what repairs Kutzbach’s count, on every mechanism this site builds. It is also not in the joint graph, which is the interesting part, and the next rung is about what that means for a formula that was supposed to be a shortcut past the geometry.

What this makes readable

Essays that name this one as a prerequisite.

About the same objects

Not linked from either essay — found by the objects both name.

What links here

The 8 of 14 essays linking to this one that name the most of the same objects.

The objects this essay names

Each one links to every other essay that touches it.

ConstraintJacobianMobilityRankReciprocal screwScrewScrew systemThresholdWrench