circlepack#
Implements a fast, dependency-free algorithm for packing circles with prescribed tangencies. Used internally in KnotPy for layout of graph structures.
Functions
|
Angle at x between y and z using circle geometry. |
|
Compute a circle packing layout given prescribed tangencies. |
|
Sum of angles at center formed with its neighboring cycle. |
|
Invert packing so that circle k surrounds the others. |
|
Invert all circles in the packing around a given complex point. |
|
Normalize the packing so that a given circle has radius target. |
|
Recursively place neighbors of a given center based on geometry. |
|
Yield candidate centers and their resulting smallest radius after inversion and normalization. |
- circle_pack(internal, external)#
Compute a circle packing layout given prescribed tangencies.
Internal circles are surrounded by a cycle of other circles; external circles have fixed radii.
- Parameters:
internal (dict[str, list[str]]) – Mapping of internal keys to cyclic list of neighbor keys.
external (dict[str, float]) – Mapping of external keys to fixed radii.
- Returns:
A dictionary mapping each key to a (center, radius) pair.
- Raises:
ValueError – If keys are not disjoint or external radii are non-positive.
- Return type:
dict[str, tuple[complex, float]]
Example
>>> internal = {'A': ['B', 'C', 'D']} >>> external = {'B': 1.0, 'C': 1.0, 'D': 1.0} >>> packing = circle_pack(internal, external) >>> len(packing) 4
- invert_packing(packing, center)#
Invert all circles in the packing around a given complex point.
- Parameters:
packing (dict[str, tuple[complex, float]]) – Dictionary mapping keys to (center, radius) pairs.
center (complex) – Complex point to invert around.
- Returns:
A new packing where all circles are inverted.
- Return type:
dict[str, tuple[complex, float]]
Example
>>> inverted = invert_packing(packing, 0j)
- normalize_packing(packing, k=None, target=1.0)#
Normalize the packing so that a given circle has radius target.
- Parameters:
packing (dict[str, tuple[complex, float]]) – Mapping from keys to (center, radius).
k (str) – Optional key of the circle to normalize. If None, uses the smallest.
target (float) – Desired radius for the selected circle.
- Returns:
New packing with all circles scaled accordingly.
- Return type:
dict[str, tuple[complex, float]]
- invert_around(packing, k, smallCircles=None)#
Invert packing so that circle k surrounds the others.
This finds a Möbius transform (via inversion) that places circle k large enough to contain the others, based on a grid search.
- Parameters:
packing (dict[str, tuple[complex, float]]) – The circle packing to invert.
k (str) – Key of the desired outer circle.
smallCircles (list[str] | None) – Optional list of keys to consider in optimization.
- Returns:
A new packing with optimized inversion.
- Return type:
dict[str, tuple[complex, float]]