Geometry

class Line3(v=None, w=None, check=True)[source]

Bases: BasePoseList

classmethod Alloc(n=1)

Construct an instance with N default values (BasePoseList superclass method)

Parameters:

n (int, optional) – Number of values, defaults to 1

Return type:

Self

Returns:

pose instance with n default values

X.Alloc(N) creates an instance of the pose class X with N default values, ie. len(X) will be N.

X can be considered a vector of pose objects, and those elements can be referenced X[i] or assigned to X[i] = ....

Note

The default value depends on the pose class and is the result of the empty constructor. For SO2, SE2, SO3, SE3 it is an identity matrix, for a twist class Twist2 or Twist3 it is a zero vector, for a UnitQuaternion or Quaternion it is a zero vector.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10

where X is any of the SMTB classes.

classmethod Empty()

Construct an empty instance (BasePoseList superclass method)

Return type:

Self

Returns:

pose instance with zero values

Example:

>>> x = X.Empty()
>>> len(x)
0

where X is any of the SMTB classes.

classmethod IntersectingPlanes(pi1, pi2)[source]
Return type:

Self

classmethod Join(P, Q)[source]

Create 3D line from two 3D points

Parameters:
  • P (array_like(3)) – First 3D point

  • Q (array_like(3)) – Second 3D point

Returns:

3D line

Return type:

Line3 instance

Line3.Join(P, Q) create a Line3 object that represents the line joining the 3D points P (3,) and Q (3,). The direction is from Q to P.

Seealso:

IntersectingPlanes() PointDir()

classmethod PointDir(point, dir)[source]

Create 3D line from a point and direction

Parameters:
  • point (array_like(3)) – A 3D point

  • dir (array_like(3)) – Direction vector

Returns:

3D line

Return type:

Line3 instance

Line3.PointDir(P, W) is a Line3` object that represents the line containing the point P and parallel to the direction vector W.

Seealso:

Join() IntersectingPlanes()

classmethod TwoPlanes(pi1, pi2)[source]

Create 3D line from intersection of two planes

Parameters:
  • pi1 (array_like(4), or Plane) – First plane

  • pi2 (array_like(4), or Plane) – Second plane

Returns:

3D line

Return type:

Line3 instance

L = Line3.TwoPlanes(π1, π2) is a Line3 object that represents the line formed by the intersection of two planes π1 and π3.

Planes are represented by the 4-vector \([a, b, c, d]\) which describes the plane \(\pi: ax + by + cz + d=0\).

Seealso:

Join() PointDir()

__eq__(l2)[source]

Test if two lines are equivalent

Parameters:

l2 (Line3) – Second line

Returns:

lines are equivalent

Return type:

bool

L1 == L2 is True if the Line3 objects describe the same line in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Note

There is a hardwired tolerance of 10eps.

Seealso:

isequal() __ne__()

__init__(v=None, w=None, check=True)[source]

Create a Line3 object

Parameters:
  • v (array_like(6) or array_like(3)) – Plucker coordinate vector, or Plucker moment vector

  • w (array_like(3), optional) – Plucker direction vector, optional

  • check (bool) – check that the parameters are valid, defaults to True

Raises:

ValueError – bad arguments

Returns:

3D line

Return type:

Line3 instance

A representation of a 3D line using Plucker coordinates.

  • Line3(p) creates a 3D line from a Plucker coordinate vector p=[v, w]

    where v (3,) is the moment and w (3,) is the line direction.

  • Line3(v, w) as above but the components v and w are provided separately.

  • Line3(L) creates a copy of the Line3 object L.

Notes:
  • The Line3 object inherits from collections.UserList and has list-like behaviours.

  • A single Line3 object contains a 1D-array of Plucker coordinates.

  • The elements of the array are guaranteed to be Plucker coordinates.

  • The number of elements is given by len(L)

  • The elements can be accessed using index and slice notation, eg. L[1] or L[2:3]

  • The Line3 instance can be used as an iterator in a for loop or list comprehension.

  • Some methods support operations on the internal list.

Seealso:

Join() TwoPlanes() PointDir()

__mul__(right)[source]

Reciprocal product

Parameters:
  • left (Line3) – Left operand

  • right (Line3) – Right operand

Returns:

reciprocal product

Return type:

float

left * right is the scalar reciprocal product \(\hat{w}_L \dot m_R + \hat{w}_R \dot m_R\).

Note

  • Multiplication or composition of lines is not defined.

  • Pre-multiplication by an SE3 object is supported, see __rmul__.

Seealso:

__rmul__()

__ne__(l2)[source]

Test if two lines are not equivalent

Parameters:

l2 (Line3) – Second line

Returns:

lines are not equivalent

Return type:

bool

L1 != L2 is True if the Line3 objects describe different lines in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Note

There is a hardwired tolerance of 10eps.

Seealso:

__ne__()

__or__(l2)[source]

Overloaded | operator tests for parallelism

Parameters:

l2 (Line3) – Second line

Returns:

lines are parallel

Return type:

bool

l1 | l2 is an operator which is true if the two lines are parallel.

Note

The | operator has low precendence.

Note

There is a hardwired tolerance of 10eps.

Seealso:

isparallel() __xor__()

__rmul__(left)[source]

Rigid-body transformation of 3D line

Parameters:
  • left (SE3) – Rigid-body transform

  • right (Line) – 3D line

Returns:

transformed 3D line

Return type:

Line3 instance

T * line is the line transformed by the rigid body transformation T.

Seealso:

__mul__()

__xor__(l2)[source]

Overloaded ^ operator tests for intersection

Parameters:

l2 (Line3) – Second line

Returns:

lines intersect

Return type:

bool

l1 ^ l2 is an operator which is true if the two lines intersect.

Note

  • The ^ operator has low precendence.

  • Is False if the lines are equivalent since they would intersect at an infinite number of points.

Note

There is a hardwired tolerance of 10eps.

Seealso:

intersects() isparallel() isintersecting()

append(x)[source]

Append a line

Parameters:

x (Line3) – line object

Raises:

ValueError – Attempt to append a non Plucker object

Returns:

Line3 object with new line appended

Return type:

Line3 instance

arghandler(arg, convertfrom=(), check=True)

Standard constructor support (BasePoseList superclass method)

Parameters:
  • arg (Any) – initial value

  • convertfrom (Tuple) – list of classes to accept and convert from

  • check (bool) – check value is valid, defaults to True

Type:

tuple of typles

Raises:

ValueError – bad type passed

Return type:

bool

The value arg can be any of:

  1. None, an identity value is created

  2. a numpy.ndarray of the appropriate shape and value which is valid for the subclass

  3. a list whose elements all meet the criteria above

  4. an instance of the subclass

  5. a list whose elements are all singelton instances of the subclass

For cases 2 and 3, a NumPy array or a list of NumPy array is passed. Each NumPyarray is tested for validity (if check is False a cursory check of shape is made, if check is True the numerical value is inspected) and converted to the required internal format by the _import method. The default _import method calls the isvalid method for checking. This mechanism allows equivalent forms to be passed, ie. 6x1 or 4x4 for an se(3).

If self is an instance of class A, and an instance of class B is passed and B is an element of the convertfrom argument, then B.A() will be invoked to perform the type conversion.

Examples:

SE3()
SE3(np.identity(4))
SE3([np.identity(4), np.identity(4)])
SE3(SE3())
SE3([SE3(), SE3()])
Twist3(SE3())
binop(right, op, op2=None, list1=True)

Perform binary operation

Parameters:
  • left (BasePoseList subclass) – left operand

  • right (BasePoseList subclass, scalar or array) – right operand

  • op (callable) – binary operation

  • op2 (callable) – binary operation

  • list1 (bool) – return single array as a list, default True

Raises:

ValueError – arguments are not compatible

Returns:

list of values

Return type:

list

The is a helper method for implementing binary operation with overloaded operators such as X * Y where X and Y are both subclasses of BasePoseList. Each operand has a list of one or more values and this methods computes a list of result values according to:

Inputs

Output

len(left)

len(right)

len

operation

1

1

1

ret = op(left, right)

1

M

M

ret[i] = op(left, right[i])

M

1

M

ret[i] = op(left[i], right)

M

M

M

ret[i] = op(left[i], right[i])

The arguments to op are the internal numeric values, ie. as returned by the ._A property.

The result is always a list, except for the first case above and list1 is False.

If the right operand is not a BasePoseList subclass, but is a numeric scalar or array then then op2 is invoked

For example:

X._binop(Y, lambda x, y: x + y)

Input

Output

len(left)

len

operation

1

1

ret = op2(left, right)

M

M

ret[i] = op2(left[i], right)

There is no check on the shape of right if it is an array. The result is always a list, except for the first case above and list1 is False.

clear() None -- remove all items from S
closest_to_line(l2)[source]

Closest point between lines

Parameters:

l2 (Line3) – second line

Returns:

nearest points and distance between lines at those points

Return type:

ndarray(3,N), ndarray(N)

There are four cases:

  • len(self) == len(other) == 1 find the point on the first line closest to the second line, as well as the minimum distance between the lines.

  • len(self) == 1, len(other) == N find the point of intersection between the first line and the N other lines, returning N intersection points and distances.

  • len(self) == N, len(other) == 1 find the point of intersection between the N first lines and the other line, returning N intersection points and distances.

  • len(self) == N, len(other) == M for each of the N first lines find the closest intersection with each of the M other lines, returning N intersection points and distances.

** this last one should be an option, default behavior would be to test self[i] against line[i] ** maybe different function

For two sets of lines, of equal size, return an array of closest points and distances.

Example:

.. runblock:: pycon

    >>> from spatialmath import Line3
    >>> line1 = Line3.Join([1, 1, 0], [1, 1, 1])
    >>> line2 = Line3.Join([0, 0, 0], [2, 3, 5])
    >>> line1.closest_to_line(line2)
Reference:

Plucker coordinates

Seealso:

distance()

closest_to_point(x)[source]

Point on line closest to given point

Parameters:

x (array_like(3)) – An arbitrary 3D point

Returns:

Point on the line and distance to line

Return type:

ndarray(3), float

Find the point on the line closest to x as well as the distance at that closest point.

Example:

>>> from spatialmath import Line3
>>> line1 = Line3.Join([0, 0, 0], [2, 2, 3])
>>> line1.closest_to_point([1, 1, 1])
(array([0.8235, 0.8235, 1.2353]), 0.3429971702850176)
Seealso:

meth:point

commonperp(l2)[source]

Common perpendicular to two lines

Parameters:

l2 (Line3) – Second line

Returns:

Perpendicular line

Return type:

Line3 instance or None

l1.commonperp(l2) is the common perpendicular line between the two lines. Returns None if the lines are parallel.

Seealso:

intersect()

contains(x, tol=20)[source]

Test if points are on the line

Parameters:
  • x (3-element array_like, or ndarray(3,N)) – 3D point

  • tol (float, optional) – Tolerance in units of eps, defaults to 20

Raises:

ValueError – Bad argument

Returns:

Whether point is on the line

Return type:

bool or numpy.ndarray(N) of bool

line.contains(X) is true if the point X lies on the line defined by the Line3 object self.

If X is an array with 3 rows, the test is performed on every column and an array of booleans is returned.

copy()
count(value) integer -- return number of occurrences of value
distance(l2, tol=20)[source]

Minimum distance between lines

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

Closest distance between lines

Return type:

float

``l1.distance(l2) is the minimum distance between two lines.

Note

Works for parallel, skew and intersecting lines.

Seealso:

closest_to_line()

extend(iterable)

Extend sequence of values in an instance (BasePoseList superclass method)

Parameters:

x (instance of same type) – the value to extend

Raises:

ValueError – incorrect type of appended object

Return type:

None

Appends the argument’s values to the object’s internal list of values.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> x.append(X.Alloc(5))   # extend the list
>>> len(x)
15

where X is any of the SMTB classes.

index(value[, start[, stop]]) integer -- return first index of value.

Raises ValueError if the value is not present.

Supporting start and stop arguments is optional, but recommended.

insert(i, item)

Insert a value to an instance (BasePoseList superclass method)

Parameters:
  • i (int) – element to insert value before

  • item (instance of same type) – the value to insert

Raises:

ValueError – incorrect type of inserted value

Return type:

None

Inserts the argument into the object’s internal list of values.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> x.insert(0, X())   # insert at start of list
>>> len(x)
11
>>> x.insert(10, X())   # append to the list
>>> len(x)
11

where X is any of the SMTB classes.

Note

If i is beyond the end of the list, the item is appended to the list

intersect_plane(plane, tol=20)[source]

Line intersection with a plane

Parameters:
  • plane (array_like(4) or Plane3) – A plane

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

Intersection point, λ

Return type:

ndarray(3), float

  • P, λ = line.intersect_plane(plane) is the point where the line intersects the plane, and the corresponding λ value. Return None, None if no intersection.

The plane can be specified as:

  • a 4-vector \([a, b, c, d]\) which describes the plane \(\pi: ax + by + cz + d=0\).

  • a Plane object

The return value is a named tuple with elements:

  • .p for the point on the line as a numpy.ndarray, shape=(3,)

  • .lam the lambda value for the point on the line.

Sealso:

point() Plane

intersect_volume(bounds)[source]

Line intersection with a volume

Parameters:

bounds (Union[List, Tuple[float, float, float, float, float, float], ndarray[Any, dtype[TypeVar(ScalarType, bound= generic, covariant=True)]]]) – Bounds of an axis-aligned rectangular cuboid

Returns:

Intersection point, λ value

Return type:

ndarray(3,N), ndarray(N)

P, λ = line.intersect_volume(bounds) is a matrix (3xN) with columns that indicate where the line intersects the faces of the volume and the corresponding λ values.

The volume is specified by bounds = [xmin xmax ymin ymax zmin zmax].

The number of columns N is either:

  • 0, when the line is outside the plot volume or,

  • 2 when the line pierces the bounding volume.

See also plot() point()

intersects(l2)[source]

Intersection point of two lines

Parameters:

l2 (Line3) – Second line

Returns:

3D intersection point

Return type:

ndarray(3) or None

l1.intersects(l2) is the point of intersection of the two lines, or None if the lines do not intersect or are equivalent.

Seealso:

commonperp :meth:`eq() __xor__()

isequal(l2, tol=20)[source]

Test if two lines are equivalent

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines are equivalent

Return type:

bool

L1 == L2 is True if the Line3 objects describe the same line in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Seealso:

__eq__()

isintersecting(l2, tol=20)[source]

Test if lines are intersecting

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines intersect

Return type:

bool

l1.isintersecting(l2) is true if the two lines intersect.

Note

Is False if the lines are equivalent since they would intersect at an infinite number of points.

Seealso:

__xor__() intersects() isparallel()

isparallel(l2, tol=20)[source]

Test if lines are parallel

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines are parallel

Return type:

bool

l1.isparallel(l2) is true if the two lines are parallel.

l1 | l2 as above but in binary operator form

Seealso:

__or__() intersects()

static isvalid(x, check=False)[source]

A decorator indicating abstract staticmethods.

Deprecated, use ‘staticmethod’ with ‘abstractmethod’ instead.

Return type:

bool

lam(point)[source]

Parametric distance from principal point

Parameters:

point (array_like(3)) – 3D point

Returns:

parametric distance λ

Return type:

float

line.lam(P) is the value of \(\lambda\) such that \(Q = P_p + \lambda \hat{d}\) is closest to P.

Seealso:

point()

plot(*pos, bounds=None, ax=None, **kwargs)[source]

Plot a line

Parameters:
  • bounds (Union[float, List[float], Tuple[float, ...], ndarray[Any, dtype[TypeVar(ScalarType, bound= generic, covariant=True)]], None]) – Bounds of an axis-aligned rectangular cuboid as [xmin xmax ymin ymax zmin zmax], optional

  • **kwargs

    Extra arguents passed to Line2D

Returns:

Plotted line

Return type:

Matplotlib artists

  • line.plot(bounds) adds a line segment to the current axes, and the handle of the line is returned. The line segment is defined by the intersection of the line and the given rectangular cuboid. If the line does not intersect the plotting volume None is returned.

  • line.plot() as above but the bounds are taken from the axis limits of the current axes.

The line color or style is specified by:

  • a MATLAB-style linestyle like ‘k–’

  • additional arguments passed to Line2D

Seealso:

intersect_volume()

point(lam)[source]

Generate point on line

Parameters:

lam (float) – Scalar distance from principal point

Returns:

Distance from principal point to the origin

Return type:

float

line.point(λ) is a point on the line, where λ is the parametric distance along the line from the principal point of the line such that \(P = P_p + \lambda \hat{d}\) and \(\hat{d}\) is the line direction given by line.uw.

Seealso:

pp() closest() uw() lam()

pop(i=-1)

Pop value from an instance (BasePoseList superclass method)

Parameters:

i (int) – item in the list to pop, default is last

Returns:

the popped value

Return type:

instance of same type

Raises:

IndexError – if there are no values to pop

Removes a value from the value list and returns it. The original instance is modified.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> y = x.pop()  # pop the last value x[9]
>>> len(x)
9
>>> y = x.pop(0)  # pop the first value x[0]
>>> len(x)
8

where X is any of the SMTB classes.

remove(item)

S.remove(value) – remove first occurrence of value. Raise ValueError if the value is not present.

reverse()

S.reverse() – reverse IN PLACE

side(other)[source]

Plucker side operator

Parameters:

other (Line3) – second line

Returns:

permuted dot product

Return type:

float

This permuted dot product operator is zero whenever the lines intersect or are parallel.

skew()[source]

Line as a Plucker skew-symmetric matrix

Returns:

Skew-symmetric matrix form of Plucker coordinates

Return type:

ndarray(4,4)

line.skew() is the Plucker matrix, a 4x4 skew-symmetric matrix representation of the line whose six unique elements are the Plucker coordinates of the line.

\[\begin{split}\sk{L} = \begin{bmatrix} 0 & v_z & -v_y & \omega_x \\ -v_z & 0 & v_x & \omega_y \\ v_y & -v_x & 0 & \omega_z \\ -\omega_x & -\omega_y & -\omega_z & 0 \end{bmatrix}\end{split}\]

Note

  • For two homogeneous points P and Q on the line, \(PQ^T-QP^T\) is

also skew symmetric. - The projection of Plucker line by a perspective camera is a homogeneous line (3x1) given by \(\vee C M C^T\) where \(C \in \mathbf{R}^{3 \times 4}\) is the camera matrix.

sort(*args, **kwds)
unop(op, matrix=False)

Perform unary operation

Parameters:
  • self (BasePoseList subclass) – operand

  • op (callable) – unnary operation

  • matrix (bool) – return array instead of list, default False

Returns:

operation results

Return type:

list or NumPy array

The is a helper method for implementing unary operations where the operand has multiple value. This method computes the value of the operation for all input values and returns the result as either a list or as a matrix which vertically stacks the results.

Input

Output

len(self)

len

operation

1

1

ret = op(self)

M

M

ret[i] = op(self[i])

M

M

ret[i,;] = op(self[i])

The result is:

  • a list of values if matrix==False, or

  • a 2D NumPy stack of values if matrix==True, it is assumed that the value is a 1D array.

property A: ndarray[Any, dtype[floating]]

Array value of an instance (BasePoseList superclass method)

Returns:

NumPy array value of this instance

Return type:

ndarray

  • X.A is a NumPy array that represents the value of this instance, and has a shape given by X.shape.

Note

This assumes that len(X) == 1, ie. it is a single-valued instance.

property pp: ndarray[Any, dtype[floating]]

Principal point of the 3D line

Returns:

Principal point of the line

Return type:

ndarray(3)

line.pp is the point on the line that is closest to the origin.

Notes:

  • Same as Plucker.point(0)

Seealso:

ppd() :meth`point`

property ppd: float

Distance from principal point to the origin

Returns:

Distance from principal point to the origin

Return type:

float

line.ppd is the distance from the principal point to the origin. This is the smallest distance of any point on the line to the origin.

Seealso:

pp()

property shape: Tuple[int]
property uw: ndarray[Any, dtype[floating]]

Line direction as a unit vector

Returns:

Line direction as a unit vector

Return type:

ndarray(3,)

line.uw is a unit-vector parallel to the line.

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

w()

property v: ndarray[Any, dtype[floating]]

Moment vector

Returns:

the moment vector

Return type:

ndarray(3)

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

w()

property vec: ndarray[Any, dtype[floating]]

Line as a Plucker coordinate vector

Returns:

Plucker coordinate vector

Return type:

ndarray(6,)

line.vec is the Plucker coordinate vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

property w: ndarray[Any, dtype[floating]]

Direction vector

Returns:

the direction vector

Return type:

ndarray(3)

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

v() uw()

class Plane3(c)[source]

Bases: object

Create a plane object from linear coefficients

Parameters:

c (array_like(4)) – Plane coefficients

Returns:

a Plane object

Return type:

Plane

Planes are represented by the 4-vector \([a, b, c, d]\) which describes the plane \(\pi: ax + by + cz + d=0\).

classmethod LinePoint(l, p)[source]

Create a plane object from a line and point

Parameters:
  • l (Line3) – 3D line

  • p (ndarray(3)) – Points in the plane

Returns:

a Plane object

Return type:

Plane

Seealso:

PointNormal() ThreePoints()

classmethod PointNormal(p, n)[source]

Create a plane object from point and normal

Parameters:
  • p (array_like(3)) – Point in the plane

  • n (array_like(3)) – Normal vector to the plane

Returns:

a Plane object

Return type:

Plane

Seealso:

ThreePoints() LinePoint()

classmethod ThreePoints(p)[source]

Create a plane object from three points

Parameters:

p (ndarray(3,3)) – Three points in the plane

Returns:

a Plane object

Return type:

Plane

The points in p are arranged as columns.

Seealso:

PointNormal() LinePoint()

classmethod TwoLines(l1, l2)[source]

Create a plane object from two line

Parameters:
Returns:

a Plane object

Return type:

Plane

Warning

This algorithm fails if the lines are parallel.

Seealso:

LinePoint() PointNormal() ThreePoints()

__init__(c)[source]
contains(p, tol=20)[source]

Test if point in plane

Parameters:
  • p (array_like(3)) – A 3D point

  • tol (float) – tolerance in units of eps, defaults to 20

Returns:

if the point is in the plane

Return type:

bool

static intersection(pi1, pi2, pi3)[source]

Intersection point of three planes

Parameters:
  • pi1 (Plane) – plane 1

  • pi2 (Plane) – plane 2

  • pi3 (Plane) – plane 3

Returns:

coordinates of intersection point

Return type:

ndarray(3)

This static method computes the intersection point of the three planes given as arguments.

Warning

This algorithm fails if the planes do not intersect, or intersect along a line.

Seealso:

Plane()

plot(bounds=None, ax=None, **kwargs)[source]

Plot plane

Parameters:
  • bounds (array_like(2|4|6), optional) – bounds of plot volume, defaults to None

  • ax (Axes, optional) – 3D axes to plot into, defaults to None

  • kwargs – optional arguments passed to plot_surface

The bounds of the 3D plot volume is [xmin, xmax, ymin, ymax, zmin, zmax] and a 3D plot is created if not already existing. If bounds is not provided it is taken from current 3D axes.

The plane is drawn using plot_surface.

Seealso:

axes_logic()

property d: float

Plane offset

Returns:

Offset of the plane

Return type:

float

For a plane \(\pi: ax + by + cz + d=0\) this is the scalar \(d\).

Seealso:

n()

property n: ndarray[Any, dtype[floating]]

Normal to the plane

Returns:

Normal to the plane

Return type:

ndarray(3)

For a plane \(\pi: ax + by + cz + d=0\) this is the vector \([a,b,c]\).

Seealso:

d()

class Plucker(v=None, w=None)[source]

Bases: Line3

classmethod Alloc(n=1)

Construct an instance with N default values (BasePoseList superclass method)

Parameters:

n (int, optional) – Number of values, defaults to 1

Return type:

Self

Returns:

pose instance with n default values

X.Alloc(N) creates an instance of the pose class X with N default values, ie. len(X) will be N.

X can be considered a vector of pose objects, and those elements can be referenced X[i] or assigned to X[i] = ....

Note

The default value depends on the pose class and is the result of the empty constructor. For SO2, SE2, SO3, SE3 it is an identity matrix, for a twist class Twist2 or Twist3 it is a zero vector, for a UnitQuaternion or Quaternion it is a zero vector.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10

where X is any of the SMTB classes.

classmethod Empty()

Construct an empty instance (BasePoseList superclass method)

Return type:

Self

Returns:

pose instance with zero values

Example:

>>> x = X.Empty()
>>> len(x)
0

where X is any of the SMTB classes.

classmethod IntersectingPlanes(pi1, pi2)
Return type:

Self

classmethod Join(P, Q)

Create 3D line from two 3D points

Parameters:
  • P (array_like(3)) – First 3D point

  • Q (array_like(3)) – Second 3D point

Returns:

3D line

Return type:

Line3 instance

Line3.Join(P, Q) create a Line3 object that represents the line joining the 3D points P (3,) and Q (3,). The direction is from Q to P.

Seealso:

IntersectingPlanes() PointDir()

classmethod PointDir(point, dir)

Create 3D line from a point and direction

Parameters:
  • point (array_like(3)) – A 3D point

  • dir (array_like(3)) – Direction vector

Returns:

3D line

Return type:

Line3 instance

Line3.PointDir(P, W) is a Line3` object that represents the line containing the point P and parallel to the direction vector W.

Seealso:

Join() IntersectingPlanes()

classmethod TwoPlanes(pi1, pi2)

Create 3D line from intersection of two planes

Parameters:
  • pi1 (array_like(4), or Plane) – First plane

  • pi2 (array_like(4), or Plane) – Second plane

Returns:

3D line

Return type:

Line3 instance

L = Line3.TwoPlanes(π1, π2) is a Line3 object that represents the line formed by the intersection of two planes π1 and π3.

Planes are represented by the 4-vector \([a, b, c, d]\) which describes the plane \(\pi: ax + by + cz + d=0\).

Seealso:

Join() PointDir()

__eq__(l2)

Test if two lines are equivalent

Parameters:

l2 (Line3) – Second line

Returns:

lines are equivalent

Return type:

bool

L1 == L2 is True if the Line3 objects describe the same line in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Note

There is a hardwired tolerance of 10eps.

Seealso:

isequal() __ne__()

__init__(v=None, w=None)[source]

Create a Line3 object

Parameters:
  • v (array_like(6) or array_like(3)) – Plucker coordinate vector, or Plucker moment vector

  • w (array_like(3), optional) – Plucker direction vector, optional

  • check (bool) – check that the parameters are valid, defaults to True

Raises:

ValueError – bad arguments

Returns:

3D line

Return type:

Line3 instance

A representation of a 3D line using Plucker coordinates.

  • Line3(p) creates a 3D line from a Plucker coordinate vector p=[v, w]

    where v (3,) is the moment and w (3,) is the line direction.

  • Line3(v, w) as above but the components v and w are provided separately.

  • Line3(L) creates a copy of the Line3 object L.

Notes:
  • The Line3 object inherits from collections.UserList and has list-like behaviours.

  • A single Line3 object contains a 1D-array of Plucker coordinates.

  • The elements of the array are guaranteed to be Plucker coordinates.

  • The number of elements is given by len(L)

  • The elements can be accessed using index and slice notation, eg. L[1] or L[2:3]

  • The Line3 instance can be used as an iterator in a for loop or list comprehension.

  • Some methods support operations on the internal list.

Seealso:

Join() TwoPlanes() PointDir()

__mul__(right)

Reciprocal product

Parameters:
  • left (Line3) – Left operand

  • right (Line3) – Right operand

Returns:

reciprocal product

Return type:

float

left * right is the scalar reciprocal product \(\hat{w}_L \dot m_R + \hat{w}_R \dot m_R\).

Note

  • Multiplication or composition of lines is not defined.

  • Pre-multiplication by an SE3 object is supported, see __rmul__.

Seealso:

__rmul__()

__ne__(l2)

Test if two lines are not equivalent

Parameters:

l2 (Line3) – Second line

Returns:

lines are not equivalent

Return type:

bool

L1 != L2 is True if the Line3 objects describe different lines in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Note

There is a hardwired tolerance of 10eps.

Seealso:

__ne__()

__or__(l2)

Overloaded | operator tests for parallelism

Parameters:

l2 (Line3) – Second line

Returns:

lines are parallel

Return type:

bool

l1 | l2 is an operator which is true if the two lines are parallel.

Note

The | operator has low precendence.

Note

There is a hardwired tolerance of 10eps.

Seealso:

isparallel() __xor__()

__rmul__(left)

Rigid-body transformation of 3D line

Parameters:
  • left (SE3) – Rigid-body transform

  • right (Line) – 3D line

Returns:

transformed 3D line

Return type:

Line3 instance

T * line is the line transformed by the rigid body transformation T.

Seealso:

__mul__()

__xor__(l2)

Overloaded ^ operator tests for intersection

Parameters:

l2 (Line3) – Second line

Returns:

lines intersect

Return type:

bool

l1 ^ l2 is an operator which is true if the two lines intersect.

Note

  • The ^ operator has low precendence.

  • Is False if the lines are equivalent since they would intersect at an infinite number of points.

Note

There is a hardwired tolerance of 10eps.

Seealso:

intersects() isparallel() isintersecting()

append(x)

Append a line

Parameters:

x (Line3) – line object

Raises:

ValueError – Attempt to append a non Plucker object

Returns:

Line3 object with new line appended

Return type:

Line3 instance

arghandler(arg, convertfrom=(), check=True)

Standard constructor support (BasePoseList superclass method)

Parameters:
  • arg (Any) – initial value

  • convertfrom (Tuple) – list of classes to accept and convert from

  • check (bool) – check value is valid, defaults to True

Type:

tuple of typles

Raises:

ValueError – bad type passed

Return type:

bool

The value arg can be any of:

  1. None, an identity value is created

  2. a numpy.ndarray of the appropriate shape and value which is valid for the subclass

  3. a list whose elements all meet the criteria above

  4. an instance of the subclass

  5. a list whose elements are all singelton instances of the subclass

For cases 2 and 3, a NumPy array or a list of NumPy array is passed. Each NumPyarray is tested for validity (if check is False a cursory check of shape is made, if check is True the numerical value is inspected) and converted to the required internal format by the _import method. The default _import method calls the isvalid method for checking. This mechanism allows equivalent forms to be passed, ie. 6x1 or 4x4 for an se(3).

If self is an instance of class A, and an instance of class B is passed and B is an element of the convertfrom argument, then B.A() will be invoked to perform the type conversion.

Examples:

SE3()
SE3(np.identity(4))
SE3([np.identity(4), np.identity(4)])
SE3(SE3())
SE3([SE3(), SE3()])
Twist3(SE3())
binop(right, op, op2=None, list1=True)

Perform binary operation

Parameters:
  • left (BasePoseList subclass) – left operand

  • right (BasePoseList subclass, scalar or array) – right operand

  • op (callable) – binary operation

  • op2 (callable) – binary operation

  • list1 (bool) – return single array as a list, default True

Raises:

ValueError – arguments are not compatible

Returns:

list of values

Return type:

list

The is a helper method for implementing binary operation with overloaded operators such as X * Y where X and Y are both subclasses of BasePoseList. Each operand has a list of one or more values and this methods computes a list of result values according to:

Inputs

Output

len(left)

len(right)

len

operation

1

1

1

ret = op(left, right)

1

M

M

ret[i] = op(left, right[i])

M

1

M

ret[i] = op(left[i], right)

M

M

M

ret[i] = op(left[i], right[i])

The arguments to op are the internal numeric values, ie. as returned by the ._A property.

The result is always a list, except for the first case above and list1 is False.

If the right operand is not a BasePoseList subclass, but is a numeric scalar or array then then op2 is invoked

For example:

X._binop(Y, lambda x, y: x + y)

Input

Output

len(left)

len

operation

1

1

ret = op2(left, right)

M

M

ret[i] = op2(left[i], right)

There is no check on the shape of right if it is an array. The result is always a list, except for the first case above and list1 is False.

clear() None -- remove all items from S
closest_to_line(l2)

Closest point between lines

Parameters:

l2 (Line3) – second line

Returns:

nearest points and distance between lines at those points

Return type:

ndarray(3,N), ndarray(N)

There are four cases:

  • len(self) == len(other) == 1 find the point on the first line closest to the second line, as well as the minimum distance between the lines.

  • len(self) == 1, len(other) == N find the point of intersection between the first line and the N other lines, returning N intersection points and distances.

  • len(self) == N, len(other) == 1 find the point of intersection between the N first lines and the other line, returning N intersection points and distances.

  • len(self) == N, len(other) == M for each of the N first lines find the closest intersection with each of the M other lines, returning N intersection points and distances.

** this last one should be an option, default behavior would be to test self[i] against line[i] ** maybe different function

For two sets of lines, of equal size, return an array of closest points and distances.

Example:

.. runblock:: pycon

    >>> from spatialmath import Line3
    >>> line1 = Line3.Join([1, 1, 0], [1, 1, 1])
    >>> line2 = Line3.Join([0, 0, 0], [2, 3, 5])
    >>> line1.closest_to_line(line2)
Reference:

Plucker coordinates

Seealso:

distance()

closest_to_point(x)

Point on line closest to given point

Parameters:

x (array_like(3)) – An arbitrary 3D point

Returns:

Point on the line and distance to line

Return type:

ndarray(3), float

Find the point on the line closest to x as well as the distance at that closest point.

Example:

>>> from spatialmath import Line3
>>> line1 = Line3.Join([0, 0, 0], [2, 2, 3])
>>> line1.closest_to_point([1, 1, 1])
(array([0.8235, 0.8235, 1.2353]), 0.3429971702850176)
Seealso:

meth:point

commonperp(l2)

Common perpendicular to two lines

Parameters:

l2 (Line3) – Second line

Returns:

Perpendicular line

Return type:

Line3 instance or None

l1.commonperp(l2) is the common perpendicular line between the two lines. Returns None if the lines are parallel.

Seealso:

intersect()

contains(x, tol=20)

Test if points are on the line

Parameters:
  • x (3-element array_like, or ndarray(3,N)) – 3D point

  • tol (float, optional) – Tolerance in units of eps, defaults to 20

Raises:

ValueError – Bad argument

Returns:

Whether point is on the line

Return type:

bool or numpy.ndarray(N) of bool

line.contains(X) is true if the point X lies on the line defined by the Line3 object self.

If X is an array with 3 rows, the test is performed on every column and an array of booleans is returned.

copy()
count(value) integer -- return number of occurrences of value
distance(l2, tol=20)

Minimum distance between lines

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

Closest distance between lines

Return type:

float

``l1.distance(l2) is the minimum distance between two lines.

Note

Works for parallel, skew and intersecting lines.

Seealso:

closest_to_line()

extend(iterable)

Extend sequence of values in an instance (BasePoseList superclass method)

Parameters:

x (instance of same type) – the value to extend

Raises:

ValueError – incorrect type of appended object

Return type:

None

Appends the argument’s values to the object’s internal list of values.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> x.append(X.Alloc(5))   # extend the list
>>> len(x)
15

where X is any of the SMTB classes.

index(value[, start[, stop]]) integer -- return first index of value.

Raises ValueError if the value is not present.

Supporting start and stop arguments is optional, but recommended.

insert(i, item)

Insert a value to an instance (BasePoseList superclass method)

Parameters:
  • i (int) – element to insert value before

  • item (instance of same type) – the value to insert

Raises:

ValueError – incorrect type of inserted value

Return type:

None

Inserts the argument into the object’s internal list of values.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> x.insert(0, X())   # insert at start of list
>>> len(x)
11
>>> x.insert(10, X())   # append to the list
>>> len(x)
11

where X is any of the SMTB classes.

Note

If i is beyond the end of the list, the item is appended to the list

intersect_plane(plane, tol=20)

Line intersection with a plane

Parameters:
  • plane (array_like(4) or Plane3) – A plane

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

Intersection point, λ

Return type:

ndarray(3), float

  • P, λ = line.intersect_plane(plane) is the point where the line intersects the plane, and the corresponding λ value. Return None, None if no intersection.

The plane can be specified as:

  • a 4-vector \([a, b, c, d]\) which describes the plane \(\pi: ax + by + cz + d=0\).

  • a Plane object

The return value is a named tuple with elements:

  • .p for the point on the line as a numpy.ndarray, shape=(3,)

  • .lam the lambda value for the point on the line.

Sealso:

point() Plane

intersect_volume(bounds)

Line intersection with a volume

Parameters:

bounds (Union[List, Tuple[float, float, float, float, float, float], ndarray[Any, dtype[TypeVar(ScalarType, bound= generic, covariant=True)]]]) – Bounds of an axis-aligned rectangular cuboid

Returns:

Intersection point, λ value

Return type:

ndarray(3,N), ndarray(N)

P, λ = line.intersect_volume(bounds) is a matrix (3xN) with columns that indicate where the line intersects the faces of the volume and the corresponding λ values.

The volume is specified by bounds = [xmin xmax ymin ymax zmin zmax].

The number of columns N is either:

  • 0, when the line is outside the plot volume or,

  • 2 when the line pierces the bounding volume.

See also plot() point()

intersects(l2)

Intersection point of two lines

Parameters:

l2 (Line3) – Second line

Returns:

3D intersection point

Return type:

ndarray(3) or None

l1.intersects(l2) is the point of intersection of the two lines, or None if the lines do not intersect or are equivalent.

Seealso:

commonperp :meth:`eq() __xor__()

isequal(l2, tol=20)

Test if two lines are equivalent

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines are equivalent

Return type:

bool

L1 == L2 is True if the Line3 objects describe the same line in space. Note that because of the over parameterization, lines can be equivalent even if their coordinate vectors are different.

Seealso:

__eq__()

isintersecting(l2, tol=20)

Test if lines are intersecting

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines intersect

Return type:

bool

l1.isintersecting(l2) is true if the two lines intersect.

Note

Is False if the lines are equivalent since they would intersect at an infinite number of points.

Seealso:

__xor__() intersects() isparallel()

isparallel(l2, tol=20)

Test if lines are parallel

Parameters:
  • l2 (Line3) – Second line

  • tol (float, optional) – Tolerance in multiples of eps, defaults to 20

Returns:

lines are parallel

Return type:

bool

l1.isparallel(l2) is true if the two lines are parallel.

l1 | l2 as above but in binary operator form

Seealso:

__or__() intersects()

static isvalid(x, check=False)

A decorator indicating abstract staticmethods.

Deprecated, use ‘staticmethod’ with ‘abstractmethod’ instead.

Return type:

bool

lam(point)

Parametric distance from principal point

Parameters:

point (array_like(3)) – 3D point

Returns:

parametric distance λ

Return type:

float

line.lam(P) is the value of \(\lambda\) such that \(Q = P_p + \lambda \hat{d}\) is closest to P.

Seealso:

point()

plot(*pos, bounds=None, ax=None, **kwargs)

Plot a line

Parameters:
  • bounds (Union[float, List[float], Tuple[float, ...], ndarray[Any, dtype[TypeVar(ScalarType, bound= generic, covariant=True)]], None]) – Bounds of an axis-aligned rectangular cuboid as [xmin xmax ymin ymax zmin zmax], optional

  • **kwargs

    Extra arguents passed to Line2D

Returns:

Plotted line

Return type:

Matplotlib artists

  • line.plot(bounds) adds a line segment to the current axes, and the handle of the line is returned. The line segment is defined by the intersection of the line and the given rectangular cuboid. If the line does not intersect the plotting volume None is returned.

  • line.plot() as above but the bounds are taken from the axis limits of the current axes.

The line color or style is specified by:

  • a MATLAB-style linestyle like ‘k–’

  • additional arguments passed to Line2D

Seealso:

intersect_volume()

point(lam)

Generate point on line

Parameters:

lam (float) – Scalar distance from principal point

Returns:

Distance from principal point to the origin

Return type:

float

line.point(λ) is a point on the line, where λ is the parametric distance along the line from the principal point of the line such that \(P = P_p + \lambda \hat{d}\) and \(\hat{d}\) is the line direction given by line.uw.

Seealso:

pp() closest() uw() lam()

pop(i=-1)

Pop value from an instance (BasePoseList superclass method)

Parameters:

i (int) – item in the list to pop, default is last

Returns:

the popped value

Return type:

instance of same type

Raises:

IndexError – if there are no values to pop

Removes a value from the value list and returns it. The original instance is modified.

Example:

>>> x = X.Alloc(10)
>>> len(x)
10
>>> y = x.pop()  # pop the last value x[9]
>>> len(x)
9
>>> y = x.pop(0)  # pop the first value x[0]
>>> len(x)
8

where X is any of the SMTB classes.

remove(item)

S.remove(value) – remove first occurrence of value. Raise ValueError if the value is not present.

reverse()

S.reverse() – reverse IN PLACE

side(other)

Plucker side operator

Parameters:

other (Line3) – second line

Returns:

permuted dot product

Return type:

float

This permuted dot product operator is zero whenever the lines intersect or are parallel.

skew()

Line as a Plucker skew-symmetric matrix

Returns:

Skew-symmetric matrix form of Plucker coordinates

Return type:

ndarray(4,4)

line.skew() is the Plucker matrix, a 4x4 skew-symmetric matrix representation of the line whose six unique elements are the Plucker coordinates of the line.

\[\begin{split}\sk{L} = \begin{bmatrix} 0 & v_z & -v_y & \omega_x \\ -v_z & 0 & v_x & \omega_y \\ v_y & -v_x & 0 & \omega_z \\ -\omega_x & -\omega_y & -\omega_z & 0 \end{bmatrix}\end{split}\]

Note

  • For two homogeneous points P and Q on the line, \(PQ^T-QP^T\) is

also skew symmetric. - The projection of Plucker line by a perspective camera is a homogeneous line (3x1) given by \(\vee C M C^T\) where \(C \in \mathbf{R}^{3 \times 4}\) is the camera matrix.

sort(*args, **kwds)
unop(op, matrix=False)

Perform unary operation

Parameters:
  • self (BasePoseList subclass) – operand

  • op (callable) – unnary operation

  • matrix (bool) – return array instead of list, default False

Returns:

operation results

Return type:

list or NumPy array

The is a helper method for implementing unary operations where the operand has multiple value. This method computes the value of the operation for all input values and returns the result as either a list or as a matrix which vertically stacks the results.

Input

Output

len(self)

len

operation

1

1

ret = op(self)

M

M

ret[i] = op(self[i])

M

M

ret[i,;] = op(self[i])

The result is:

  • a list of values if matrix==False, or

  • a 2D NumPy stack of values if matrix==True, it is assumed that the value is a 1D array.

property A: ndarray[Any, dtype[floating]]

Array value of an instance (BasePoseList superclass method)

Returns:

NumPy array value of this instance

Return type:

ndarray

  • X.A is a NumPy array that represents the value of this instance, and has a shape given by X.shape.

Note

This assumes that len(X) == 1, ie. it is a single-valued instance.

property pp: ndarray[Any, dtype[floating]]

Principal point of the 3D line

Returns:

Principal point of the line

Return type:

ndarray(3)

line.pp is the point on the line that is closest to the origin.

Notes:

  • Same as Plucker.point(0)

Seealso:

ppd() :meth`point`

property ppd: float

Distance from principal point to the origin

Returns:

Distance from principal point to the origin

Return type:

float

line.ppd is the distance from the principal point to the origin. This is the smallest distance of any point on the line to the origin.

Seealso:

pp()

property shape: Tuple[int]
property uw: ndarray[Any, dtype[floating]]

Line direction as a unit vector

Returns:

Line direction as a unit vector

Return type:

ndarray(3,)

line.uw is a unit-vector parallel to the line.

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

w()

property v: ndarray[Any, dtype[floating]]

Moment vector

Returns:

the moment vector

Return type:

ndarray(3)

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

w()

property vec: ndarray[Any, dtype[floating]]

Line as a Plucker coordinate vector

Returns:

Plucker coordinate vector

Return type:

ndarray(6,)

line.vec is the Plucker coordinate vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

property w: ndarray[Any, dtype[floating]]

Direction vector

Returns:

the direction vector

Return type:

ndarray(3)

The line is represented by a vector \((\vec{v}, \vec{w}) \in \mathbb{R}^6\).

Seealso:

v() uw()