wolfhece.pyvertexvectors._models ================================ .. py:module:: wolfhece.pyvertexvectors._models .. autoapi-nested-parse:: Model-only base classes for PyVertexvectors (no wx, no OpenGL dependency). Author: HECE - University of Liege, Pierre Archambeau Date: 2024-2026 Copyright (c) 2024 University of Liege. All rights reserved. This script and its content are protected by copyright law. Unauthorized copying or distribution of this file, via any medium, is strictly prohibited. Provides -------- - :class:`TriangulationModel` — triangulation geometry, I/O, transformations. - :class:`vectorpropertiesModel` — visual property storage, I/O, color helpers. GUI/OpenGL subclasses live in :mod:`wolfhece.PyVertexvectors`. Module Contents --------------- .. py:class:: VectorOGLRenderer(*args, **kwds) Bases: :py:obj:`enum.Enum` .. autoapi-inheritance-diagram:: wolfhece.pyvertexvectors._models.VectorOGLRenderer :parts: 1 :private-bases: Rendering backend for vector objects. .. py:attribute:: LIST :value: 0 .. py:attribute:: SHADER :value: 1 .. py:class:: TriangulationModel(fn: str = '', pts=None, tri=None, idx: str = '') Pure-data triangulation: vertices, triangles, I/O, transforms. Holds arrays of points and triangle indices and provides geometry operations, file reading/writing, and coordinate transformations without any OpenGL or wx dependency. The GUI subclass :class:`~wolfhece.PyVertexvectors.Triangulation` adds ``Element_To_Draw`` integration, OpenGL display lists, and matplotlib plotting helpers. .. py:attribute:: filename :value: '' .. py:attribute:: idx :value: '' .. py:attribute:: tri :value: None .. py:attribute:: pts :value: None .. py:attribute:: _used_tri .. py:attribute:: _move_start :value: None .. py:attribute:: _move_step :value: None .. py:attribute:: _rotation_center :value: None .. py:attribute:: _rotation_step :value: None .. py:attribute:: _cache :value: None .. py:property:: nb_tri :type: int Return the number of triangles. .. py:property:: nb_pts :type: int Return the number of points. .. py:method:: validate_format() Force *pts* and *tri* to numpy arrays. .. py:method:: as_polydata() -> pyvista.PolyData Convert the triangulation to a PyVista PolyData object. .. py:method:: from_polydata(poly: pyvista.PolyData) Populate from a PyVista PolyData object. .. py:method:: clip_surface(other: TriangulationModel, invert=True, subdivide=0) Clip the triangulation with another one. .. py:method:: get_mask(eps: float = 1e-10) Return a boolean mask where triangle area ≤ *eps*. .. py:method:: _get_polygons() -> list[shapely.geometry.Polygon] Get a list of Shapely polygons from each triangle. .. py:method:: unuse_triangles_containing_points(points: list[shapely.geometry.Point]) Mark triangles containing any of *points* as unused. .. py:method:: get_triangles_as_listwolfvertices(used_only: bool = True) -> list[list[wolfhece.PyVertex.wolfvertex]] Return triangles as lists of :class:`wolfvertex`. .. py:method:: find_minmax(force) Compute bounding box from point coordinates. :param force: if ``True``, always recompute. .. py:method:: set_cache() Snapshot current points for cached transformations. .. py:method:: clear_cache() Discard cached point snapshot. .. py:method:: move(delta_x: float, delta_y: float, use_cache: bool = True) Translate all points by *(delta_x, delta_y)*. :param delta_x: delta x [m] :param delta_y: delta y [m] .. py:method:: rotate(angle: float, center: tuple | wolfhece.PyVertex.wolfvertex, use_cache: bool = True) Rotate all points around *center*. :param angle: angle in degrees — positive for clockwise rotation. :param center: centre of rotation. .. py:method:: rotate_xy(x: float, y: float, use_cache: bool = True) Rotate around :attr:`_rotation_center` toward *(x, y)*. .. py:method:: copy() -> TriangulationModel Return a deep copy of the triangulation. .. py:method:: import_from_gltf(fn: str = '') Import a GLTF/GLB file. :param fn: path to the ``.glb`` or ``.gltf`` file (required). :raises ValueError: if *fn* is empty. .. py:method:: export_to_gltf(fn: str = '') -> str Export the triangulation to a GLTF/GLB file. :param fn: path to the output file (required). :raises ValueError: if *fn* is empty. :return: the path written to. .. py:method:: saveas(fn: str = '') Write the triangulation to a binary ``.TRI`` file. Binary layout (little-endian): - int32 number_of_points - int32 64 or 32 (float64 / float32 flag) - VEC3 points (float64 or float32) - int32 number_of_triangles - VEC3 triangle indices (uint32) .. py:method:: read(fn: str) Read a binary ``.TRI``, ``.dxf``, or ``.gltf/.glb`` file. After reading, :meth:`validate_format` and :meth:`find_minmax` are called automatically. .. py:method:: import_dxf(fn: str) Import 3DFACE entities from a DXF file. .. py:class:: vectorpropertiesModel(lines: list[str] = None, parent=None) Pure-data vector properties: colors, widths, legend, persistence. Stores all visual/styling attributes for a :class:`vector` and handles file I/O (*save* / *load*) without any wx or OpenGL dependency. The GUI subclass :class:`~wolfhece.PyVertexvectors.vectorproperties` adds ``Wolf_Param`` dialog creation, ``genericImagetexture`` management, and property-editing callbacks. .. py:attribute:: used :type: bool .. py:attribute:: color :type: int .. py:attribute:: width :type: int .. py:attribute:: style :type: int .. py:attribute:: alpha :type: int .. py:attribute:: closed :type: bool .. py:attribute:: filled :type: bool .. py:attribute:: legendvisible :type: bool .. py:attribute:: transparent :type: bool .. py:attribute:: flash :type: bool .. py:attribute:: legendtext :type: str .. py:attribute:: legendrelpos :type: int .. py:attribute:: legendx :type: float .. py:attribute:: legendy :type: float .. py:attribute:: legendbold :type: bool .. py:attribute:: legenditalic :type: bool .. py:attribute:: legendunderlined :type: bool .. py:attribute:: legendfontname :type: str .. py:attribute:: legendfontsize :type: int .. py:attribute:: legendcolor :type: int .. py:attribute:: extrude :type: bool .. py:attribute:: parent :value: None .. py:attribute:: plot_indices :value: False .. py:attribute:: plot_lengths :value: False .. py:attribute:: _values .. py:method:: add_values(values: dict) Merge a mapping of values into the internal storage. .. py:method:: set_shared_values(shared_values: dict) Attach an existing values mapping by reference. This is useful when multiple vectors must share identical attribute values (e.g. split parts of a multipart geometry). .. py:method:: value_keys() -> set Return the set of stored value keys. .. py:method:: values_dict() -> dict Return a shallow copy of stored values. .. py:method:: values_view() -> dict Return the internal values mapping for read-only access. Callers must not mutate the returned dictionary directly. .. py:method:: _parse_width_profile(raw) -> list | None Convert a width profile string to a list or ``None``. Two formats are accepted: * **Dense CSV** – ``"1.0,1.5,2.0"`` — one multiplier per vertex, stored as ``list[float]``. * **Sparse** – ``"0:1.0,10:2.0,20:0.5"`` — ``index:value`` pairs, stored as ``list[tuple[int, float]]``. Unspecified vertices are filled by linear interpolation (constant beyond the endpoints). Both formats are auto-detected from the presence of ``:`` tokens. .. py:method:: set_color_from_value(key: str, cmap: wolfhece.PyPalette.wolfpalette | str | matplotlib.colors.Colormap | matplotlib.cm.ScalarMappable, vmin: float = 0.0, vmax: float = 1.0) Derive the drawing color from a stored value and a colormap. .. py:method:: set_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) Set the drawing color from various input formats. .. py:method:: init_extra() Initialise extra properties not part of the VB6/Fortran format. .. py:method:: get_extra() -> list Return extra properties as a serialisable list. .. py:method:: set_extra(linesextra: list = None) Restore extra properties from a serialised list. .. py:method:: load_extra(lines: list[str]) -> int Load extra properties from file lines, return number consumed. .. py:method:: save_extra(f: io.TextIOWrapper) Write extra properties to an already-opened text file. .. py:method:: save(f: io.TextIOWrapper) Write properties in VB6/Fortran-compatible format. .. py:property:: image_path :type: pathlib.Path Path of the attached image. .. py:method:: _convert_fontname2int(fontname: str) -> int .. py:method:: _convert_int2fontname(id: int) -> str .. py:method:: egalize(other) Copy visual attributes from another properties object or vector. .. py:method:: update_myprops() No-op in model. GUI subclass populates the Wolf_Param dialog. .. py:method:: update_image_texture() No-op in model. GUI subclass updates texture coordinates. .. py:class:: vectorModel(lines: list = [], is2D=True, name='NoName', parentzone: zoneModel = None, fromshapely=None, fromnumpy: numpy.ndarray = None, fromlist: list = None) Pure-data vector: vertices, properties, geometry, I/O. Holds a list of :class:`wolfvertex` and a :class:`vectorpropertiesModel`, plus geometry helpers (shapely, interpolation, etc.) without any OpenGL, wx, or matplotlib dependency. GUI subclass ``vector`` in :mod:`wolfhece.PyVertexvectors` adds plotting, tree-widget integration and OpenGL display-list support. .. py:attribute:: myname :type: str .. py:attribute:: parentzone :type: zoneModel .. py:attribute:: myvertices :type: list[wolfhece.PyVertex.wolfvertex] .. py:attribute:: myprop :type: vectorpropertiesModel .. py:attribute:: xmin :type: float .. py:attribute:: ymin :type: float .. py:attribute:: xmax :type: float .. py:attribute:: ymax :type: float .. py:attribute:: is2D :value: True .. py:attribute:: _mylimits :value: None .. py:attribute:: length2D :value: None .. py:attribute:: length3D :value: None .. py:attribute:: _lengthparts2D :value: None .. py:attribute:: _lengthparts3D :value: None .. py:attribute:: _normals :value: None .. py:attribute:: _center_segments :value: None .. py:attribute:: _simplified_geometry :value: False .. py:attribute:: _cache_vertices :value: None .. py:attribute:: _move_start :value: None .. py:attribute:: _move_step :value: None .. py:attribute:: _rotation_center :value: None .. py:attribute:: _rotation_step :value: None .. py:attribute:: _linestring :value: None .. py:attribute:: _polygon :value: None .. py:attribute:: _vertex_kdtree :value: None .. py:attribute:: _vertex_kdtree_xy :value: None .. py:attribute:: zdatum :value: 0.0 .. py:attribute:: add_zdatum :value: False .. py:attribute:: sdatum :value: 0.0 .. py:attribute:: add_sdatum :value: False .. py:method:: _make_properties(*args, **kwargs) -> vectorpropertiesModel Create a properties object. GUI subclass returns ``vectorproperties``. .. py:method:: _make_vector(**kwargs) -> vectorModel Create a sibling vector. GUI subclass returns ``vector``. .. py:method:: _make_zone(**kwargs) -> zoneModel Create a sibling zone. GUI subclass returns ``zone``. .. py:method:: make_from_shapely(shapelyobj, **kwargs) -> vectorModel :classmethod: Factory method to create a vector from a Shapely geometry. .. py:method:: make_from_numpy(array: numpy.ndarray, **kwargs) -> vectorModel :classmethod: Factory method to create a vector from a NumPy array of shape (N, 2) or (N, 3). .. py:method:: make_from_list(lst: list, **kwargs) -> vectorModel :classmethod: Factory method to create a vector from a list of coordinate tuples. .. py:method:: _on_vertices_changed() Hook called when vertices are modified. Invalidates the cached Shapely geometries. The GUI subclass overrides this (calling ``super()``) to also invalidate the parent zone's OpenGL display list. .. py:property:: closed :type: bool Whether the vector is closed (first vertex == last vertex). .. py:property:: nbvertices :type: int Number of vertices in the vector. .. py:property:: used :type: bool Whether the vector is marked as used/active. .. py:property:: polygon :type: shapely.geometry.Polygon Shapely ``Polygon`` built from the vertices (lazily created). .. py:property:: linestring :type: shapely.geometry.LineString Shapely ``LineString`` built from the vertices (lazily created). .. py:property:: has_interior :type: bool Whether any vertex is flagged as *not in use*, indicating interior boundaries. .. py:property:: nb_interiors :type: int Number of interior boundaries (holes) derived from unused vertices. .. py:property:: centroid :type: shapely.geometry.Point Centroid of the polygon formed by the vertices (Shapely ``Point``). .. py:property:: surface :type: float Area of the polygon (0 if the vector is not closed). .. py:property:: area :type: float Alias for :pyattr:`surface`. .. py:property:: z :type: numpy.ndarray Z coordinates of all vertices as a 1-D array. If ``add_zdatum`` is ``True``, the ``zdatum`` offset is added. .. py:property:: x :type: numpy.ndarray X coordinates of all vertices as a 1-D array. .. py:property:: y :type: numpy.ndarray Y coordinates of all vertices as a 1-D array. .. py:property:: xy :type: numpy.ndarray XY coordinates as a ``(N, 2)`` array. .. py:property:: xz :type: numpy.ndarray XZ coordinates as a ``(N, 2)`` array. .. py:property:: xyz :type: numpy.ndarray XYZ coordinates as a ``(N, 3)`` array (respects ``zdatum``). .. py:property:: i :type: numpy.ndarray In-use flags of all vertices as a 1-D boolean array. .. py:property:: xyzi :type: numpy.ndarray XYZI coordinates as a ``(N, 4)`` array (x, y, z, in_use). .. py:property:: xyi :type: numpy.ndarray XYI coordinates as a ``(N, 3)`` array (x, y, in_use). .. py:property:: sz_curvi :type: tuple[numpy.ndarray, numpy.ndarray] Tuple ``(s, z)`` of curvilinear abscissa and altitude arrays. .. py:property:: s_curvi :type: numpy.ndarray Curvilinear abscissa (cumulative 2-D distance from first vertex). .. py:method:: add_value(key: str, value: Union[int, float, bool, str]) Store an arbitrary key/value pair in the vector properties. :param key: Property key. :param value: Property value. .. py:method:: get_value(key: str) -> Union[int, float, bool, str] Retrieve a stored property value by key. :param key: Property key. :returns: The stored value. .. py:method:: set_color_from_value(key: str, cmap: wolfhece.PyPalette.wolfpalette | matplotlib.colors.Colormap | matplotlib.cm.ScalarMappable, vmin: float = 0.0, vmax: float = 1.0) Set the vector colour from a stored property value using a colormap. :param key: Property key whose numeric value drives the colour. :param cmap: Colour map (``wolfpalette``, Matplotlib ``Colormap``, or ``ScalarMappable``). :param vmin: Minimum value for colour mapping. :param vmax: Maximum value for colour mapping. .. py:method:: set_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) Set the vector rendering colour. :param color: Colour as an integer, ``RGB`` instance, name string, or ``(r, g, b)`` tuple/list. .. py:method:: set_linewidth(linewidth: int | float) Set the rendering line width. :param linewidth: Line width in pixels. .. py:method:: set_alpha(alpha: int) Set the transparency level. :param alpha: Alpha value (0 = fully transparent, 255 = opaque). .. py:method:: set_filled(filled: bool) Enable or disable polygon filling. :param filled: ``True`` to render as a filled polygon. .. py:method:: set_props_from_other(other) Copy visual properties from another vector's properties. :param other: Source ``vectorpropertiesModel`` instance. .. py:method:: set_legend_text(text: str) .. py:method:: set_legend_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) .. py:method:: set_legend_text_from_value(key: str, visible: bool = True) Set the legend text from a stored property value. :param key: Property key whose value becomes the label. :param visible: Whether to make the legend visible. .. py:method:: set_legend_position(x: str | float, y: str | float) Set the legend display position. :param x: X position as a float or keyword (*'median'*, *'mean'*, *'min'*, *'max'*, *'first'*, *'last'*). :param y: Y position as a float or keyword (same options as *x*). .. py:method:: set_legend_to_centroid(text: str = '', visible: bool = True) Place the legend at the polygon centroid. :param text: Legend text (defaults to the vector name). :param visible: Whether to make the legend visible. .. py:method:: set_legend_visible(visible: bool = True) Show or hide the legend. :param visible: ``True`` to display the legend. .. py:method:: set_legend_position_to_centroid() Move the legend position to the polygon centroid. .. py:method:: set_glow(enabled: bool = True, width: float = 0.4, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.4) Configure line glow effect. :param enabled: Enable or disable glow. :param width: Glow width as fraction of half-width (0–1). :param color: RGB colour tuple with components in [0, 1]. :param alpha: Glow opacity in [0, 1]. .. py:method:: set_dash(enabled: bool = True, dash_length: float = 10.0, gap_length: float = 5.0) Configure dashed line rendering. :param enabled: Enable or disable dashes. :param dash_length: Dash length in world units. :param gap_length: Gap length in world units. .. py:method:: set_animation(mode: int = 1, speed: float = 1.0) Configure line animation. :param mode: Animation mode (0=none, 1=pulse, 2=marching ants). :param speed: Speed multiplier. .. py:method:: set_fill_animation(mode: int = 1, speed: float = 1.0, center_index: int = 0, start_angle: float = 90.0) Configure filled-polygon animation. :param mode: Animation mode (0=none, 1=pulse, 2=sweep, 3=ripple, 4=radial progressive, 5=clockwise clock, 6=counter-clockwise clock). :param speed: Speed multiplier. :param center_index: Vertex index used as the radial/clock centre. :param start_angle: Clock fill start angle in degrees. .. py:method:: set_fill_color(color=None) Set the independent fill colour for filled polygons. :param color: RGB tuple ``(r, g, b)`` with values in ``[0, 255]``, packed int, or ``None`` to inherit the vector's main colour. .. py:method:: set_contour_color(color=None, width: float = 1.0, enabled: bool = True) Set the contour/stroke colour for filled polygons. Activates a second polyline pass drawn on top of the filled area. Set *enabled=False* or *color=None* to disable the contour. :param color: RGB tuple ``(r, g, b)`` with values in ``[0, 255]``, packed int, or ``None`` to inherit the vector's main colour. :param width: Contour line width (same unit as the vector width). :param enabled: Whether to draw the contour pass at all. .. py:method:: set_join_style(style: int = 0, size: float = 0.5, size_mode: int = 0) Configure join rendering at polyline corners. :param style: Join style (0=miter, 1=bevel, 2=round, 3=fillet). :param size: Join size (fraction or world distance depending on *size_mode*). :param size_mode: 0=fraction (adimensional), 1=world distance (metres). .. py:method:: set_width_in_pixels(pixels: bool = True) Toggle pixel-based vs world-unit line width. :param pixels: ``True`` for pixel widths, ``False`` for world units. .. py:method:: set_text_along(text: str, enabled: bool = True, offset: float = 0.0, perp: float = 0.0, alignment: str = 'center') Configure text displayed along the polyline. :param text: Text to render along the path. :param enabled: Enable or disable text-along. :param offset: Shift start along the polyline (world units). :param perp: Perpendicular offset (world units, + left). :param alignment: Text alignment ('left', 'center', 'right'). .. py:method:: set_legend_glow(enabled: bool = True, width: float = 0.15, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.5) Configure legend text glow effect. :param enabled: Enable or disable legend glow. :param width: SDF threshold offset (e.g. 0.15). :param color: RGB colour tuple with components in [0, 1]. :param alpha: Glow opacity in [0, 1]. .. py:method:: set_legend_animation(mode: int = 1, speed: float = 1.0) Configure legend text animation. :param mode: Animation mode (0=none, 1=pulse, 2=wave, 3=typewriter). :param speed: Speed multiplier. .. py:method:: set_legend_style(smoothing: float = 1.0, alignment: str = 'left', line_spacing: float = 1.2) Fine-tune legend SDF text rendering. :param smoothing: SDF anti-aliasing multiplier. :param alignment: Text alignment ('left', 'center', 'right'). :param line_spacing: Multiline spacing multiplier. .. py:method:: highlighting(rgb=(255, 0, 0), linewidth=3) Highlight the vector with a temporary colour and line width. :param rgb: Highlight colour as ``(r, g, b)`` tuple. :param linewidth: Highlight line width. .. py:method:: withdrawal() Restore the colour and line width saved by :pymeth:`highlighting`. .. py:method:: add_vertex(addedvert: Union[list[wolfhece.PyVertex.wolfvertex], wolfhece.PyVertex.wolfvertex]) Append one or more vertices. :param addedvert: A single ``wolfvertex`` or a list of vertices to append. .. py:method:: add_vertices_from_array(xyz: numpy.ndarray) Append vertices from a NumPy array. :param xyz: ``(N, 2)`` or ``(N, 3)`` array of coordinates. .. py:method:: add_vertices_from_list(xyz: list) Append vertices from a list of coordinate tuples. :param xyz: List of ``(x, y)`` or ``(x, y, z)`` tuples. .. py:method:: import_shapelyobj(obj) Replace vertices from a Shapely ``LineString`` or ``Polygon``. :param obj: Shapely geometry object. .. py:method:: count() .. py:method:: close_force() Close the vector by appending the first vertex if needed. .. py:method:: force_to_close() Alias for :pymeth:`close_force`. .. py:method:: reverse() Reverse the order of vertices in-place. .. py:method:: reset() Remove all vertices and reset caches. .. py:method:: append(other: vectorModel, merge_type: Literal['link', 'copy'] = 'link') Append vertices from another vector. :param other: Source vector. :param merge_type: *'link'* to share vertex references, *'copy'* for deep copies. .. py:method:: _set_limits() Compute and store the bounding-box limits. .. py:method:: _nblines() .. py:method:: save(f) Write the vector definition (name, vertices, properties) to an open file. :param f: Writable text file handle. .. py:method:: set_z(new_z: numpy.ndarray) Deprecated — use the ``z`` property setter instead. .. py:method:: set_cache() Cache the current vertex coordinates and bounds for incremental transforms. .. py:method:: clear_cache() Clear the cached vertex coordinates and bounds. .. py:method:: move(deltax: float, deltay: float, use_cache: bool = True, inplace: bool = True) Translate the vector. :param deltax: Displacement along X. :param deltay: Displacement along Y. :param use_cache: Use cached coordinates for incremental moves. :param inplace: Modify in place; if ``False`` return a moved copy. :returns: The moved vector (self or a new copy). .. py:method:: rotate(angle: float, center: tuple[float, float] = (0.0, 0.0), use_cache: bool = True, inplace: bool = True) Rotate the vector around a centre point. :param angle: Rotation angle in degrees. :param center: Centre of rotation ``(x, y)``. :param use_cache: Use cached coordinates for incremental rotations. :param inplace: Modify in place; if ``False`` return a rotated copy. :returns: The rotated vector (self or a new copy). .. py:method:: rotate_xy(x: float, y: float, use_cache: bool = True, inplace: bool = True) .. py:method:: get_mapviewer() Return the parent map-viewer widget, or ``None``. .. py:method:: find_minmax(only_firstlast: bool = False) Compute the bounding box of the vertices. :param only_firstlast: If ``True``, consider only the first and last vertex. .. py:method:: update_image_texture() Synchronise the image-texture bounds with the current bounding box. .. py:method:: get_bounds(grid: float = None) Return the bounding box as ``((xmin, ymin), (xmax, ymax))``. :param grid: If given, snap bounds to the nearest grid step. .. py:method:: get_bounds_xx_yy(grid: float = None) Return the bounding box as ``((xmin, xmax), (ymin, ymax))``. :param grid: If given, snap bounds to the nearest grid step. .. py:method:: intersects_bounds(xmin: float = None, ymin: float = None, xmax: float = None, ymax: float = None) -> bool Return whether the vector bounding box intersects the given bbox. If bounds are not provided, the vector is considered intersecting. Sentinel unset bounds are treated as intersecting to avoid false negatives. .. py:method:: get_mean_vertex(asshapelyPoint=False) Return the mean position of all vertices. :param asshapelyPoint: If ``True``, return a Shapely ``Point``; otherwise a ``wolfvertex``. .. py:method:: isinside(x: float, y: float) -> bool Test whether the point ``(x, y)`` is inside the polygon. :param x: X coordinate. :param y: Y coordinate. .. py:method:: contains(x: float, y: float) -> bool Alias for :pymeth:`isinside`. .. py:method:: _invalidate_spatial_index() Drop cached spatial indices built from the current vertices. .. py:method:: _get_vertex_kdtree() Return the lazy-built KDTree used for nearest-vertex queries. .. py:method:: _get_nearest_search_geometry() Return the geometry used for nearest-geometry queries. .. py:method:: distance_to_geometry(x: float, y: float) -> float Return the distance from ``(x, y)`` to the vector geometry. .. py:method:: find_nearest_vertex(x, y) -> wolfhece.PyVertex.wolfvertex Return the vertex nearest to ``(x, y)``. :param x: X coordinate. :param y: Y coordinate. .. py:method:: insert_nearest_vert(x, y) -> wolfhece.PyVertex.wolfvertex Insert a new vertex at ``(x, y)`` between the two nearest existing vertices. :param x: X coordinate of the new vertex. :param y: Y coordinate of the new vertex. :returns: The inserted ``wolfvertex``. .. py:method:: insert_vertex_at_s(s: float, z: float = None, tolerance: float = 0.001) -> wolfhece.PyVertex.wolfvertex Insert a vertex at curvilinear abscissa *s*. :param s: Distance along the linestring. :param z: Optional Z value for the new vertex. :param tolerance: Distance threshold to reuse an existing vertex. :returns: The inserted (or reused) vertex. .. py:method:: project_vertex_onto_vector_and_insert(xy: shapely.geometry.Point | wolfhece.PyVertex.wolfvertex, tolerance: float = 0.001) -> wolfhece.PyVertex.wolfvertex Project a point onto the linestring and insert a new vertex there. :param xy: Point to project (Shapely ``Point`` or ``wolfvertex``). :param tolerance: Distance threshold to reuse an existing vertex. :returns: The inserted (or reused) vertex. .. py:method:: get_normal_segments(update: bool = False) -> numpy.ndarray Return outward unit normals for each segment as a ``(N-1, 2)`` array. :param update: Force recomputation even if cached. .. py:method:: get_center_segments(update: bool = False) -> numpy.ndarray Return segment mid-points as a ``(N-1, 2)`` array. :param update: Force recomputation even if cached. .. py:method:: select_points_inside(xy: wolfhece.PyVertex.cloud_vertices | numpy.ndarray) -> list[bool] Return a list of booleans indicating which points are inside the polygon. :param xy: ``cloud_vertices`` or ``(N, 2)`` array of XY coordinates. .. py:method:: get_first_point_inside(xy: wolfhece.PyVertex.cloud_vertices | numpy.ndarray) Return the first point that lies inside the polygon. :param xy: ``cloud_vertices`` or ``(N, 2)`` array of XY coordinates. :returns: ``(x, y)`` tuple or ``None``. .. py:method:: split_cloud(cloud_to_split: wolfhece.PyVertex.cloud_vertices) Split a point cloud into *inside* and *outside* subsets. :param cloud_to_split: Point cloud to partition. :returns: ``(cloud_inside, cloud_outside)`` tuple. .. py:method:: check_if_closed() -> bool Return ``True`` if the vector is geometrically closed. .. py:method:: check_if_open() -> bool Return ``True`` if the vector is open; also updates ``self.closed``. .. py:method:: check_if_interior_exists() Detect repeated XY coordinates and flag them as interior (``in_use = False``). .. py:method:: asshapely_pol() -> shapely.geometry.Polygon Convert vertex list to a Shapely 2-D ``Polygon``. .. py:method:: asshapely_pol3D() -> shapely.geometry.Polygon Convert vertex list to a Shapely 3-D ``Polygon``. .. py:method:: asshapely_ls3d() -> shapely.geometry.LineString Convert vertex list to a Shapely 3-D ``LineString``. .. py:method:: asshapely_ls() -> shapely.geometry.LineString Convert vertex list to a Shapely 3-D ``LineString`` (returns empty if < 2 vertices). .. py:method:: asshapely_mp() -> shapely.geometry.MultiPoint Convert vertex list to a Shapely ``MultiPoint``. .. py:method:: asnparray() -> numpy.ndarray Return vertices as a ``(N, 2)`` NumPy array of ``(x, y)``. .. py:method:: asnparray3d() -> numpy.ndarray Return vertices as a ``(N, 3)`` NumPy array of ``(x, y, z)`` (respects ``zdatum``). .. py:method:: prepare_shapely(prepare_shapely: bool = True, linestring: bool = True, polygon: bool = True) Build and optionally prepare Shapely linestring and/or polygon geometries. :param prepare_shapely: Whether to call Shapely ``prepare()`` for faster operations. :param linestring: Build the linestring geometry. :param polygon: Build the polygon geometry. .. py:method:: reset_linestring() Destroy cached Shapely linestring and polygon (with prepared versions). .. py:method:: intersection(vec2: vectorModel = None, eval_dist=False, norm=False, force_single=False) Compute the intersection with another vector. :param vec2: Other vector to intersect with. :param eval_dist: Also return projected distance(s) on this linestring. :param norm: Normalise distances to ``[0, 1]``. :param force_single: If multi-result, keep only the first geometry. :returns: Intersection geometry, or ``(geom, dist)`` when *eval_dist* is ``True``. .. py:method:: intersects(x: float, y: float) -> bool Test whether the linestring intersects the point ``(x, y)``. :param x: X coordinate. :param y: Y coordinate. .. py:method:: aligned_with(x: float, y: float, tolerance: float = 1e-06) -> bool Test whether the point ``(x, y)`` lies on the linestring within *tolerance*. :param x: X coordinate. :param y: Y coordinate. :param tolerance: Distance tolerance. .. py:method:: buffer(distance: float, resolution: int = 16, inplace: bool = True) -> vectorModel Return the buffered polygon. :param distance: Buffer distance. :param resolution: Number of segments to approximate a quarter-circle. :param inplace: Modify this vector; if ``False`` return a new one. .. py:method:: projectontrace(trace: vectorModel) -> vectorModel Project each vertex onto a trace and return a new 2-D vector ``(s, z)``. :param trace: Reference trace vector. :returns: New vector with ``(s, z)`` coordinates. .. py:method:: parallel_offset(distance=5.0, side: Literal['left', 'right'] = 'left') -> vectorModel | None Create a parallel offset of the linestring. :param distance: Offset distance. :param side: Side of the offset (*'left'* or *'right'*). :returns: New vector or ``None`` on failure. .. py:method:: verify_s_ascending() -> tuple[bool, list[int]] Check and fix non-ascending curvilinear abscissae by swapping vertices. :returns: ``(correction_applied, list_of_corrected_indices)``. .. py:method:: get_s2d() -> numpy.ndarray Return cumulative 2-D curvilinear distances from the first vertex. .. py:method:: get_s3d() -> numpy.ndarray Return cumulative 3-D curvilinear distances from the first vertex. .. py:method:: get_sz(cumul=True) -> tuple[numpy.ndarray, numpy.ndarray] Return ``(s, z)`` arrays of curvilinear abscissa and altitude. :param cumul: If ``True``, cumulative inter-vertex distance; otherwise direct distance from the first vertex. .. py:method:: update_lengths() Recompute 2-D and 3-D segment lengths and total lengths. .. py:method:: get_segment(s, is3D, adim=True, frombegin=True) Find the segment containing the curvilinear abscissa *s*. :param s: Curvilinear abscissa. :param is3D: Use 3-D lengths. :param adim: If ``True``, *s* is normalised to ``[0, 1]``. :param frombegin: Search from the beginning; if ``False``, from the end. :returns: ``(segment_index, cumulative_s, lengthparts)``. .. py:method:: interpolate(s: float, is3D: bool = True, adim: bool = True, frombegin: bool = True) -> wolfhece.PyVertex.wolfvertex Interpolate a point along the polyline at curvilinear abscissa *s*. :param s: Curvilinear abscissa. :param is3D: Use 3-D lengths. :param adim: If ``True``, *s* is normalised to ``[0, 1]``. :param frombegin: Search from the beginning. :returns: An interpolated ``wolfvertex``. .. py:method:: tangent_at_s(s: float, is3D: bool = True, adim: bool = True, frombegin: bool = True) -> wolfhece.PyVertex.wolfvertex Return the unit tangent vector at curvilinear abscissa *s*. :param s: Curvilinear abscissa. :param is3D: Use 3-D lengths. :param adim: Normalised abscissa. :param frombegin: Search direction. .. py:method:: normal_at_s(s: float, is3D: bool = True, adim: bool = True, frombegin: bool = True, counterclockwise=True) -> wolfhece.PyVertex.wolfvertex Return the unit normal vector at curvilinear abscissa *s*. :param s: Curvilinear abscissa. :param is3D: Use 3-D lengths. :param adim: Normalised abscissa. :param frombegin: Search direction. :param counterclockwise: Normal orientation. .. py:method:: _refine2D(ds) Refine the polyline in 2-D with a target spacing *ds*. :param ds: Maximum distance between interpolated points. :returns: List of Shapely ``Point`` objects. .. py:method:: substring(s1: float, s2: float, is3D: bool = True, adim: bool = True, eps: float = 0.01) -> vectorModel Extract a sub-vector between curvilinear abscissae *s1* and *s2*. :param s1: Start curvilinear abscissa. :param s2: End curvilinear abscissa. :param is3D: Use 3-D lengths. :param adim: Normalised abscissae. :param eps: Minimum length offset when *s1* == *s2*. :returns: New sub-vector. .. py:method:: split(ds, new=True) Split the vector by inserting vertices at regular 3-D spacing *ds*. :param ds: Target 3-D spacing. :param new: If ``True``, add the new vector to the parent zone; otherwise replace vertices in place. .. py:method:: cut(s: float, is3D: bool = True, adim: bool = True, frombegin: bool = True) -> vectorModel Cut the vector at curvilinear abscissa *s* and return the detached part. :param s: Curvilinear abscissa of the cut. :param is3D: Use 3-D lengths. :param adim: Normalised abscissa. :param frombegin: Cut direction. :returns: New vector containing the cut-off portion. .. py:method:: simplify(tolerance: float = 1.0, preserve_topology: bool = True) -> vectorModel Simplify the geometry using Shapely's Douglas-Peucker algorithm. :param tolerance: Distance tolerance for simplification. :param preserve_topology: Prevent self-intersections. :returns: New simplified vector. .. py:method:: deepcopy_vector(name: str = None, parentzone=None) -> vectorModel Return a deep copy of this vector. :param name: Name for the copy (defaults to ``_copy``). :param parentzone: Optional parent zone for the copy. .. py:method:: deepcopy(name: str = None, parentzone=None) -> vectorModel Alias for :pymeth:`deepcopy_vector`. .. py:property:: _parts :type: zoneModel Split the vector into sub-parts based on in-use flags. Vertices flagged as *not in use* act as separators between parts. The first part is always closed. .. py:method:: get_subpolygons() -> list[list[wolfhece.PyVertex.wolfvertex]] Return triangulated sub-polygons for rendering, handling interiors. :returns: List of vertex lists, each forming a triangle or polygon. .. py:method:: _fillet_polyline(xs: numpy.ndarray, ys: numpy.ndarray, ws: numpy.ndarray, join_size: float, join_size_mode: int, is_closed: bool, n_subdiv: int = 8) -> tuple[numpy.ndarray, numpy.ndarray, numpy.ndarray] :staticmethod: Replace sharp corners with quadratic Bézier fillets. For each interior corner, the original vertex is replaced by a smooth curve starting/ending at a controlled distance along the adjacent segments. :param xs, ys: coordinate arrays (float64). :param ws: width multiplier array (float32). :param join_size: Fraction (mode 0) or world distance (mode 1). In fraction mode, 0 = sharp corner, 1 = fillet eats half of each adjacent segment (clamped so adjacent fillets don't overlap). :param join_size_mode: 0 = fraction (adimensional), 1 = world. :param is_closed: whether the polyline is closed. :param n_subdiv: number of Bézier subdivision points per corner. :returns: (new_xs, new_ys, new_ws) with inserted fillet points. .. py:method:: _expand_width_profile(profile: list, n: int) -> numpy.ndarray :staticmethod: Expand a raw width profile to exactly *n* per-vertex multipliers. Supports two storage formats: * **Dense** – a plain ``list[float]``, one value per vertex. If the length differs from *n* (e.g. a phantom closing vertex was appended by :meth:`get_subpolygons`), the values are resampled with linear interpolation so the profile always spans the full polyline. * **Sparse** – a ``list`` of ``(int, float)`` tuples ``[(index, multiplier), ...]``. Unspecified vertices are filled by linear interpolation between adjacent control points; extrapolation uses the nearest endpoint value (constant fill). A single control point produces a uniform profile at that multiplier value. :param profile: Dense or sparse width profile (as returned by :meth:`~vectorproperties._parse_width_profile`). :param n: Number of vertices the result must cover. :returns: float32 array of length *n*, all values ≥ 0. .. py:method:: build_shader_vbo_data() -> tuple[numpy.ndarray, int] Build VBO data for shader rendering of this vector. Each sub-polyline (from :meth:`get_subpolygons` in non-filled mode) is converted to ``GL_LINES_ADJACENCY`` segments: four vertices per segment (prev, start, end, next), each carrying ``(x, y, curvilinear_distance, width_multiplier)``. :returns: ``(vbo_data, vertex_count)`` — contiguous float32 array and total number of vertices emitted. .. py:method:: get_values_linked_polygon(linked_arrays: list, getxy=False) -> dict Extract values from arrays inside this polygon. :param linked_arrays: List of arrays to query. :param getxy: Also return XY coordinates. :returns: Dict mapping array index to extracted values. .. py:method:: get_all_values_linked_polygon(linked_arrays, getxy=False) -> dict Extract all values from arrays inside this polygon. :param linked_arrays: Arrays to query. :param getxy: Also return XY coordinates. :returns: Dict mapping array index to all extracted values. .. py:method:: get_all_values_linked_polyline(linked_arrays, getxy=True) -> dict Extract values from arrays under this polyline. :param linked_arrays: Arrays to query. :param getxy: Also return XY coordinates. :returns: Dict mapping array index to extracted values. .. py:method:: get_values_on_vertices(curarray) Sample a raster array at each vertex position and store as Z. :param curarray: Array from which to sample values. .. py:method:: get_values_linked(linked_arrays: dict, refine=True, filter_null=False) Extract values from linked arrays along the polyline. :param linked_arrays: Dict of ``{label: array}`` to query. :param refine: Refine the polyline to the array resolution before sampling. :param filter_null: Exclude null values (``-99999``) from results. :returns: A ``zoneModel`` containing one vector per array. .. py:method:: interpolate_coordinates() Linearly interpolate Z values at vertices where Z is invalid ``(-99999, 99999, NaN)``. .. py:method:: create_cs(wa) -> vectorModel Create a cross-section profile by sampling a raster array. :param wa: ``WolfArray`` to sample. :returns: A refined vector with Z values from the array, or ``None``. .. py:method:: keep_only_trace() Reduce the vector to only two vertices: first and last, with Z = 0. .. py:method:: extend_along_trace(distance: float | str) Extend the trace (first/last vertices) by *distance* in both directions. :param distance: Extension distance in metres, or a percentage string (e.g. ``'10%'``). .. py:class:: zoneModel(lines: list[str] = [], name: str = 'NoName', parent=None, is2D: bool = True, fromshapely: Union[shapely.geometry.LineString, shapely.geometry.Polygon, shapely.geometry.MultiLineString, shapely.geometry.MultiPolygon] = None) Pure-data zone: a list of vectorModel instances plus geometry helpers. GUI subclass ``zone`` in :mod:`wolfhece.PyVertexvectors` adds plotting, OpenGL display-list support and wx integration. .. py:attribute:: myname :type: str .. py:attribute:: myvectors :type: list[vectorModel] .. py:attribute:: xmin :type: float .. py:attribute:: ymin :type: float .. py:attribute:: xmax :type: float .. py:attribute:: ymax :type: float .. py:attribute:: myprops :value: None .. py:attribute:: active_vector :value: None .. py:attribute:: parent :value: None .. py:attribute:: has_legend :value: False .. py:attribute:: has_image :value: False .. py:attribute:: _move_start :value: None .. py:attribute:: _move_step :value: None .. py:attribute:: _rotation_center :value: None .. py:attribute:: _rotation_step :value: None .. py:attribute:: selected_vectors :value: [] .. py:attribute:: multils :type: shapely.geometry.MultiLineString :value: None .. py:attribute:: used :value: True .. py:method:: _make_vector(**kwargs) -> vectorModel Create a sibling vector. GUI subclass returns ``vector``. .. py:method:: _make_zone(**kwargs) -> zoneModel Create a sibling zone. GUI subclass returns ``zone``. .. py:method:: _make_triangulation(**kwargs) -> TriangulationModel Create a triangulation. GUI subclass returns ``Triangulation``. .. py:method:: reset_listogl() No-op in model. GUI subclass deletes gl list and sets idgllist=-99999. .. py:method:: _fill_structure() No-op in model. GUI subclass calls parent.fill_structure(). .. py:property:: nbvectors :type: int Number of vectors in the zone. .. py:property:: area :type: float Total area of all vectors in the zone. .. py:property:: areas :type: list[float] List of individual vector areas. .. py:property:: vector_names :type: list[str] List of vector names in the zone. .. py:method:: add_vector(addedvect: vectorModel, index=-99999, forceparent=False, update_struct=False) Add a vector to the zone. :param addedvect: Vector to add. :param index: Insertion position (``-99999`` or > count appends). :param forceparent: Set this zone as the vector's parent. :param update_struct: Trigger GUI structure update. .. py:method:: get_vector(keyvector: Union[int, str]) -> vectorModel Return a vector by index or name. :param keyvector: Integer index or string name. :returns: The matching ``vectorModel``, or ``None``. .. py:method:: count() No-op placeholder (kept for backward compatibility). .. py:method:: import_shapelyobj(obj) Import a Shapely geometry (LineString, Polygon, Multi…) as vector(s). :param obj: Shapely geometry object. .. py:method:: check_if_interior_exists() Check all vectors for interior boundaries. .. py:method:: add_values(key: str, values: numpy.ndarray) Assign a value to each vector. :param key: Property key. :param values: 1-D array with one value per vector. .. py:method:: get_values(key: str) -> numpy.ndarray Retrieve values for a given key from all vectors. :param key: Property key. .. py:method:: set_colors_from_value(key: str, cmap: wolfhece.PyPalette.wolfpalette | matplotlib.colors.Colormap | matplotlib.cm.ScalarMappable, vmin: float = 0.0, vmax: float = 1.0) Colour all vectors according to a stored value and a colormap. :param key: Property key. :param cmap: Colour map. :param vmin: Minimum value for mapping. :param vmax: Maximum value for mapping. .. py:method:: set_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) Set the same colour on all vectors. :param color: Colour specification. .. py:method:: set_linewidth(linewidth: int | float) Set the line width for all vectors. :param linewidth: Line width in pixels. .. py:method:: set_alpha(alpha: int) Set the transparency for all vectors. :param alpha: Alpha value (0–255). .. py:method:: set_filled(filled: bool) Enable or disable polygon filling for all vectors. :param filled: ``True`` to fill. .. py:method:: check_if_open() Check all vectors for open/closed state. .. py:method:: set_legend_text(text: str) Set legend text for all vectors. :param text: Legend text. .. py:method:: set_legend_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) Set legend colour for all vectors. :param color: Colour specification. .. py:method:: set_legend_text_from_values(key: str) Set legend text from stored values for all vectors. :param key: Property key. .. py:method:: set_legend_position(x, y) Set legend position for all vectors. :param x: X position (float or keyword string). :param y: Y position (float or keyword string). .. py:method:: set_legend_to_centroid() Place legends at each vector's centroid. .. py:method:: set_legend_visible(visible: bool = True) Show or hide legends for all vectors. :param visible: ``True`` to display. .. py:method:: keep_only_trace() Reduce all vectors to their trace (first and last vertices). .. py:method:: extend_along_trace(distance: float | str) Extend all vectors along their trace. :param distance: Extension distance or percentage string. .. py:method:: set_glow(enabled: bool = True, width: float = 0.4, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.4) Configure line glow for all vectors. :param enabled: Enable or disable glow. :param width: Glow width as fraction of half-width (0–1). :param color: RGB colour tuple [0, 1]. :param alpha: Glow opacity [0, 1]. .. py:method:: set_dash(enabled: bool = True, dash_length: float = 10.0, gap_length: float = 5.0) Configure dashed lines for all vectors. :param enabled: Enable or disable dashes. :param dash_length: Dash length in world units. :param gap_length: Gap length in world units. .. py:method:: set_animation(mode: int = 1, speed: float = 1.0) Configure line animation for all vectors. :param mode: 0=none, 1=pulse, 2=marching ants. :param speed: Speed multiplier. .. py:method:: set_fill_animation(mode: int = 1, speed: float = 1.0, center_index: int = 0, start_angle: float = 90.0) Configure filled-polygon animation for all vectors. :param mode: 0=none, 1=pulse, 2=sweep, 3=ripple, 4=radial progressive, 5=clockwise clock, 6=counter-clockwise clock. :param speed: Speed multiplier. :param center_index: Vertex index used as the radial/clock centre. :param start_angle: Clock fill start angle in degrees. .. py:method:: set_fill_color(color=None) Set independent fill colour for all vectors. :param color: RGB tuple, packed int, or None to inherit main colour. .. py:method:: set_contour_color(color=None, width: float = 1.0, enabled: bool = True) Set contour colour/width for all vectors. :param color: RGB tuple, packed int, or None to inherit main colour. :param width: Contour line width. :param enabled: Whether to draw the contour pass. .. py:method:: set_join_style(style: int = 0, size: float = 0.5, size_mode: int = 0) Configure join rendering for all vectors. :param style: 0=miter, 1=bevel, 2=round, 3=fillet. :param size: Join size. :param size_mode: 0=fraction, 1=world distance. .. py:method:: set_width_in_pixels(pixels: bool = True) Toggle pixel vs world-unit line width for all vectors. :param pixels: ``True`` for pixel widths. .. py:method:: set_text_along(text: str, enabled: bool = True, offset: float = 0.0, perp: float = 0.0, alignment: str = 'center') Configure text along polyline for all vectors. :param text: Text to display. :param enabled: Enable or disable. :param offset: Shift start along polyline (world units). :param perp: Perpendicular offset (world units). :param alignment: 'left', 'center', 'right'. .. py:method:: set_legend_glow(enabled: bool = True, width: float = 0.15, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.5) Configure legend glow for all vectors. :param enabled: Enable or disable legend glow. :param width: SDF threshold offset. :param color: RGB colour tuple [0, 1]. :param alpha: Glow opacity [0, 1]. .. py:method:: set_legend_animation(mode: int = 1, speed: float = 1.0) Configure legend animation for all vectors. :param mode: 0=none, 1=pulse, 2=wave, 3=typewriter. :param speed: Speed multiplier. .. py:method:: set_legend_style(smoothing: float = 1.0, alignment: str = 'left', line_spacing: float = 1.2) Configure legend SDF text style for all vectors. :param smoothing: SDF AA multiplier. :param alignment: 'left', 'center', 'right'. :param line_spacing: Multiline spacing multiplier. .. py:method:: set_cache() Cache coordinates and bounds for all vectors. .. py:method:: clear_cache() Clear cached data for all vectors and reset transform state. .. py:method:: move(dx: float, dy: float, use_cache: bool = True, inplace: bool = True) Translate all vectors in the zone. :param dx: Displacement along X. :param dy: Displacement along Y. :param use_cache: Use cached coordinates. :param inplace: Modify in place; if ``False`` return a moved copy. .. py:method:: rotate(angle: float, center: tuple[float, float], use_cache: bool = True, inplace: bool = True) Rotate all vectors around a centre point. :param angle: Rotation angle in degrees. :param center: Centre of rotation ``(x, y)``. :param use_cache: Use cached coordinates. :param inplace: Modify in place or return a copy. .. py:method:: rotate_xy(x: float, y: float, use_cache: bool = True, inplace: bool = True) .. py:method:: use() Mark all vectors and the zone as used/active. .. py:method:: unuse() Mark all vectors and the zone as unused/inactive. .. py:method:: get_mapviewer() Return the parent map-viewer widget. .. py:method:: find_minmax(update=False, only_firstlast: bool = False) Compute the bounding box across all vectors. :param update: Recompute individual vector bounds first. :param only_firstlast: Consider only first/last vertices. .. py:method:: find_nearest_vertex(x: float, y: float) -> wolfhece.PyVertex.wolfvertex | None Return the nearest vertex across all vectors in the zone. .. py:method:: find_nearest_vector(x: float, y: float) -> vectorModel | None Return the vector whose geometry is nearest to ``(x, y)``. .. py:method:: select_vectors_from_point(x: float, y: float, inside=True) Select vectors containing or nearest to the point ``(x, y)``. :param x: X coordinate. :param y: Y coordinate. :param inside: If ``True``, select vectors whose polygon contains the point; otherwise select the nearest vector. .. py:method:: get_selected_vectors(all=False) .. py:method:: asshapely_ls() -> shapely.geometry.MultiLineString Return all vectors as a Shapely ``MultiLineString``. .. py:method:: prepare_shapely() Build a Shapely ``MultiLineString`` for the zone. .. py:method:: _nblines() -> int Return the number of lines required when saving this zone. .. py:method:: save(f: io.TextIOWrapper) Write the zone definition to an open file. :param f: Writable text file handle. .. py:method:: save_extra(f: io.TextIOWrapper) Write extra properties for each vector. :param f: Writable text file handle. .. py:method:: load_extra(lines: list[str]) -> int .. py:method:: export_shape(fn: str = '') Export vectors as an ESRI Shapefile (Lambert 72 / EPSG:31370). :param fn: Output file path. .. py:method:: buffer(distance: float, resolution: int = 16, inplace: bool = False) -> zoneModel Buffer all vectors in the zone. :param distance: Buffer distance. :param resolution: Segments per quarter-circle. :param inplace: Modify in place or return a new zone. .. py:method:: reverse(inplace: bool = True) -> zoneModel Reverse vertex order in all vectors. :param inplace: Modify in place or return a copy. .. py:method:: add_parallel(distance) Add a parallel offset of the active vector to the zone. :param distance: Offset distance (positive = right, negative = left). .. py:method:: parallel_active(distance) Replace zone contents with the active vector plus left and right offsets. :param distance: Offset distance. .. py:method:: create_cs(wa) -> zoneModel Create cross-section profiles for each vector by sampling a raster. :param wa: ``WolfArray`` to sample. :returns: New zone containing the cross-section vectors. .. py:method:: deepcopy_zone(name: str = None, parent=None) -> zoneModel Return a deep copy of this zone. :param name: Name for the copy (defaults to ``_copy``). :param parent: Optional parent for the copy. .. py:method:: deepcopy(name: str = None, parent=None) -> zoneModel Alias for :pymeth:`deepcopy_zone`. .. py:method:: create_multibin(nb: int = None, nb2: int = 0) -> TriangulationModel Create a multi-bin triangulation between the zone's vectors. :param nb: Number of interpolation points per vector. :param nb2: Number of intermediate vectors between each pair. :returns: ``TriangulationModel`` or ``None`` on error. .. py:method:: create_constrainedDelaunay(nb: int = None) -> TriangulationModel Create a constrained Delaunay triangulation from the zone's vectors. :param nb: Number of interpolation points per vector (0 = no resampling). :returns: ``TriangulationModel`` or ``None`` on error. .. py:method:: createmultibin_proj(nb: int = None, nb2: int = 0) -> TriangulationModel Create a projected multi-bin triangulation using a support line. :param nb: Number of interpolation points per vector. :param nb2: Number of intermediate vectors between each pair. :returns: ``TriangulationModel`` or ``None`` on error. .. py:method:: create_polygon_from_parallel(ds: float, howmanypoly=1) -> None Create polygons between left, centre, and right vectors. The zone must contain exactly 3 vectors. :param ds: Spacing along the trace. :param howmanypoly: Number of polygons. .. py:method:: create_sliding_polygon_from_parallel(poly_length: float, ds_sliding: float, farthest_parallel: float, interval_parallel: float = None, intersect=None, howmanypoly=1, eps_offset: float = 0.25) Create sliding polygons along a trace with parallel offsets. :param poly_length: Length of each polygon along the trace. :param ds_sliding: Sliding step between successive polygons. :param farthest_parallel: Maximum offset distance. :param interval_parallel: Interval between parallel offsets. :param intersect: Optional intersecting vector to limit the trace. :param howmanypoly: Number of polygons per position. :param eps_offset: Small offset applied at the starting position. .. py:method:: get_values_linked_polygons(linked_arrays, stats=True) -> dict Extract raster values inside each vector's polygon. :param linked_arrays: Arrays to query. :param stats: Compute statistics on the results. .. py:method:: get_all_values_linked_polygon(linked_arrays, stats=True, key_idx_names: Literal['idx', 'name'] = 'idx', getxy=False) -> dict Extract all raster values inside each vector's polygon. :param linked_arrays: Arrays to query. :param stats: Compute statistics. :param key_idx_names: Key type for result dict (*'idx'* or *'name'*). :param getxy: Also return XY coordinates. .. py:method:: _stats_values(vals: dict) Compute median, mean, min, max, p5, p95 statistics on extracted values. :param vals: Dict of ``{polygon_id: {values: ...}}``. .. py:class:: ZonesModel(filename: str | pathlib.Path = '', ox: float = 0.0, oy: float = 0.0, tx: float = 0.0, ty: float = 0.0, is2D: bool = True, idx: str = '', colname: str = None, bbox: shapely.geometry.Polygon = None, find_minmax_init: bool = True, colors: dict = None) Pure-data Zones: a list of zoneModel instances plus I/O and geometry helpers. GUI subclass ``Zones`` in :mod:`wolfhece.PyVertexvectors` adds wx.Frame, OpenGL display-list support, tree-list UI and wx integration. .. py:attribute:: tx :type: float .. py:attribute:: ty :type: float .. py:attribute:: myzones :type: list[zoneModel] .. py:attribute:: wx_exists :value: False .. py:attribute:: plotted :value: True .. py:attribute:: mapviewer :value: None .. py:attribute:: _myprops :value: None .. py:attribute:: loaded :value: True .. py:attribute:: active_vector :value: None .. py:attribute:: active_zone :value: None .. py:attribute:: last_active :value: None .. py:attribute:: force3D :value: False .. py:attribute:: is2D :value: True .. py:attribute:: filename :value: '' .. py:attribute:: init_struct :value: True .. py:attribute:: xmin :value: 0.0 .. py:attribute:: ymin :value: 0.0 .. py:attribute:: xmax :value: -99999.0 .. py:attribute:: ymax :value: -99999.0 .. py:attribute:: _first_find_minmax :type: bool :value: True .. py:attribute:: _move_start :value: None .. py:attribute:: _move_step :value: None .. py:attribute:: _rotation_center :value: None .. py:attribute:: _rotation_step :value: None .. py:method:: prep_listogl() No-op in the model; GUI override prepares OpenGL display lists. .. py:method:: reset_listogl() No-op in the model; GUI override resets OpenGL display lists. .. py:method:: _make_zone(**kwargs) Factory: create a zoneModel. GUI override returns ``zone``. .. py:method:: _make_zones(**kwargs) Factory: create a ZonesModel. GUI override returns ``Zones``. .. py:method:: _make_vector(**kwargs) Factory: create a vectorModel. GUI override returns ``vector``. .. py:property:: mynames :type: list[str] Return the names of all zones .. py:method:: check_if_interior_exists() Check if the zone has at least one vector with interior points .. py:method:: add_values(key: str, values: numpy.ndarray | dict) Add values to the zones. :param key: Value identifier. :param values: Either a dict ``{zone_name: ndarray}`` or an ndarray whose first axis length must match :pyattr:`nbzones`. .. py:method:: get_values(key: str) -> numpy.ndarray Get values from the zones. :param key: Value identifier. :return: Array of values, one element per zone. .. py:method:: set_colors_from_value(key: str, cmap: wolfhece.PyPalette.wolfpalette | str | matplotlib.colors.Colormap | matplotlib.cm.ScalarMappable, vmin: float = 0.0, vmax: float = 1.0) Set colours for all zones based on stored values. :param key: Value identifier used to look up per-zone data. :param cmap: Colour map (palette, name, Colormap or ScalarMappable). :param vmin: Lower bound of the value range. :param vmax: Upper bound of the value range. .. py:method:: set_color(color: int | wolfhece.color_constants.RGB | str | list | tuple) Set a uniform colour for all zones. :param color: Colour specification (integer, RGB, name, or list/tuple). .. py:method:: set_linewidth(linewidth: int | float) Set line width for all zones. :param linewidth: Width in pixels. .. py:method:: set_alpha(alpha: int) Set transparency for all zones. :param alpha: Alpha value (0–255). .. py:method:: set_filled(filled: bool) Set filled rendering for all zones. :param filled: Whether polygons should be drawn filled. .. py:method:: check_if_open() Check if the vectors in the zone are open .. py:method:: concatenate_all_vectors() -> list[vectorModel] Concatenate all vectors in the zones .. py:method:: prepare_shapely() Prepare shapely objects for all vectors in zones .. py:method:: filter_contains(others: list[vectorModel]) -> ZonesModel Create a new ZonesModel with vectors from *others* contained in the zones. :param others: List of vectors or a ZonesModel to filter. :return: A new ``ZonesModel`` with the contained vectors. .. py:property:: areas List of areas of all zones .. py:method:: buffer(distance: float, resolution: int = 16, inplace: bool = True) Buffer all zones. :param distance: Buffer distance in world units. :param resolution: Number of segments to approximate a quarter circle. :param inplace: If True, modify in place; otherwise return a new object. .. py:method:: set_cache() Set cache for all zones .. py:method:: clear_cache() Clear cache for all zones .. py:method:: move(dx: float, dy: float, use_cache: bool = True, inplace: bool = True) Move all zones. :param dx: Translation along X. :param dy: Translation along Y. :param use_cache: If True, move relative to cached positions. :param inplace: If True, modify in place; otherwise return a deep copy. .. py:method:: rotate(angle: float, center: shapely.geometry.Point = None, use_cache: bool = True, inplace: bool = True) Rotate all zones. :param angle: Rotation angle in radians. :param center: Centre of rotation (default: origin). :param use_cache: If True, rotate from cached positions. :param inplace: If True, modify in place; otherwise return a deep copy. .. py:method:: rotate_xy(angle: float, center: shapely.geometry.Point = None, use_cache: bool = True, inplace: bool = True) Rotate all zones (XY plane only). :param angle: Rotation angle in radians. :param center: Centre of rotation (default: origin). :param use_cache: If True, rotate from cached positions. :param inplace: If True, modify in place; otherwise return a deep copy. .. py:method:: force_unique_zone_name() Check if all zones have a unique id If not, the id will be set to the index of the zone in the list .. py:method:: set_legend_visible(visible: bool = True) Set the visibility of the legend for all zones. :param visible: Whether the legend should be visible. .. py:method:: set_legend_text(text: str) Set the legend text for all zones. :param text: Legend text string. .. py:method:: set_legend_color(color: str | int | tuple | list | wolfhece.color_constants.RGB) Set the legend colour for all zones. :param color: Colour specification. .. py:method:: set_legend(x: float | str, y: float | str, text: str, visible: bool = True) Set legend position, text and visibility for all zones. :param x: X-coordinate of the legend. :param y: Y-coordinate of the legend. :param text: Legend text string. :param visible: Whether the legend should be visible. .. py:method:: set_legend_text_from_values(key: str) Set legend text for all zones from stored values. :param key: Value identifier. .. py:method:: set_legend_to_centroid() Set the legend to the centroid of the zones .. py:method:: set_legend_position(x, y) Set legend position for all zones. :param x: X-coordinate. :param y: Y-coordinate. .. py:method:: set_glow(enabled: bool = True, width: float = 0.4, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.4) Configure line glow for all zones. :param enabled: Enable or disable glow. :param width: Glow width as fraction of half-width (0–1). :param color: RGB colour tuple [0, 1]. :param alpha: Glow opacity [0, 1]. .. py:method:: set_dash(enabled: bool = True, dash_length: float = 10.0, gap_length: float = 5.0) Configure dashed lines for all zones. :param enabled: Enable or disable dashes. :param dash_length: Dash length in world units. :param gap_length: Gap length in world units. .. py:method:: set_animation(mode: int = 1, speed: float = 1.0) Configure line animation for all zones. :param mode: 0=none, 1=pulse, 2=marching ants. :param speed: Speed multiplier. .. py:method:: set_fill_animation(mode: int = 1, speed: float = 1.0, center_index: int = 0, start_angle: float = 90.0) Configure filled-polygon animation for all zones. :param mode: 0=none, 1=pulse, 2=sweep, 3=ripple, 4=radial progressive, 5=clockwise clock, 6=counter-clockwise clock. :param speed: Speed multiplier. :param center_index: Vertex index used as the radial/clock centre. :param start_angle: Clock fill start angle in degrees. .. py:method:: set_fill_color(color=None) Set independent fill colour for all zones. :param color: RGB tuple, packed int, or None to inherit main colour. .. py:method:: set_contour_color(color=None, width: float = 1.0, enabled: bool = True) Set contour colour/width for all zones. :param color: RGB tuple, packed int, or None to inherit main colour. :param width: Contour line width. :param enabled: Whether to draw the contour pass. .. py:method:: set_join_style(style: int = 0, size: float = 0.5, size_mode: int = 0) Configure join rendering for all zones. :param style: 0=miter, 1=bevel, 2=round, 3=fillet. :param size: Join size. :param size_mode: 0=fraction, 1=world distance. .. py:method:: set_width_in_pixels(pixels: bool = True) Toggle pixel vs world-unit line width for all zones. :param pixels: ``True`` for pixel widths. .. py:method:: set_text_along(text: str, enabled: bool = True, offset: float = 0.0, perp: float = 0.0, alignment: str = 'center') Configure text along polyline for all zones. :param text: Text to display. :param enabled: Enable or disable. :param offset: Shift start along polyline (world units). :param perp: Perpendicular offset (world units). :param alignment: 'left', 'center', 'right'. .. py:method:: set_legend_glow(enabled: bool = True, width: float = 0.15, color: tuple = (1.0, 1.0, 1.0), alpha: float = 0.5) Configure legend glow for all zones. :param enabled: Enable or disable legend glow. :param width: SDF threshold offset. :param color: RGB colour tuple [0, 1]. :param alpha: Glow opacity [0, 1]. .. py:method:: set_legend_animation(mode: int = 1, speed: float = 1.0) Configure legend animation for all zones. :param mode: 0=none, 1=pulse, 2=wave, 3=typewriter. :param speed: Speed multiplier. .. py:method:: set_legend_style(smoothing: float = 1.0, alignment: str = 'left', line_spacing: float = 1.2) Configure legend SDF text style for all zones. :param smoothing: SDF AA multiplier. :param alignment: 'left', 'center', 'right'. :param line_spacing: Multiline spacing multiplier. .. py:property:: nbzones Number of zones in the collection. .. py:method:: import_shapefile(fn: str, bbox: shapely.geometry.Polygon = None, colname: str = None, value_columns: str | list[str] | tuple[str, Ellipsis] | None = None, share_multipart_values: bool = False) Import a shapefile using geopandas. The entire shapefile is loaded as a single zone. :param fn: Path to the shapefile. :param bbox: Optional bounding box to filter features. :param colname: Column name used to build zone names. :param value_columns: Columns to store into vector properties. - ``None``: do not import attribute values (default). - ``'all'``: import all non-geometry columns. - list/tuple: import selected columns. :param share_multipart_values: If True, multipart geometries share the same underlying ``_values`` dictionary across split vectors. .. py:method:: import_GeoDataFrame(content: geopandas.GeoDataFrame, bbox: shapely.geometry.Polygon = None, colname: str = None, value_columns: str | list[str] | tuple[str, Ellipsis] | None = None, share_multipart_values: bool = False) Import a GeoDataFrame. :param content: GeoDataFrame to import. :param bbox: Optional bounding box to filter features. :param colname: Column name used to build zone names. :param value_columns: Columns to store into vector properties. - ``None``: do not import attribute values (default). - ``'all'``: import all non-geometry columns. - list/tuple: import selected columns. :param share_multipart_values: If True, multipart geometries share the same underlying ``_values`` dictionary across split vectors. .. py:method:: export_GeoDataFrame(as_multipart: bool = False) -> geopandas.GeoDataFrame Export to a GeoDataFrame :param as_multipart: If True, export one row per zone with Multi* geometries when possible. Default False keeps legacy behavior. .. py:method:: _vector_geometry_for_export(curvect: vectorModel) Return the most suitable shapely geometry for a vector export. .. py:method:: _zone_multipart_geometry_for_export(curzone: zoneModel) Return a Multi* geometry for a zone when possible. If a zone mixes closed and open vectors, multipart export is ambiguous; in that case ``None`` is returned and a warning is emitted. .. py:method:: export_GeoDataFrame_with_values(value_columns: str | list[str] | tuple[str, Ellipsis] = 'common', missing_value=np.nan, include_vector_meta: bool = True, as_multipart: bool = False) -> geopandas.GeoDataFrame Export vectors to a temporary GeoDataFrame including property values. By default, one row is written per vector. With ``as_multipart=True``, one row is written per zone with a Multi* geometry. Property keys can be selected with: - ``'common'``: keys present in every exported vector. - ``'union'``: all keys found on at least one vector. - list/tuple: explicit key selection. :param value_columns: Column-selection mode. :param missing_value: Fill value for missing keys. :param include_vector_meta: Include helper metadata columns. :param as_multipart: Export one Multi* geometry per zone. :returns: A GeoDataFrame ready to be written with GeoPandas. .. py:method:: export_to_shapefile(filename: str, include_values: bool = False, value_columns: str | list[str] | tuple[str, Ellipsis] = 'common', missing_value=np.nan, include_vector_meta: bool = True, as_multipart: bool = False) Export to shapefile. The first vector of each zone will be exported. Use ``export_shape`` on the zone object to export all vectors. :param filename: Output shapefile path. :param include_values: If True, export per-vector property values. :param value_columns: Property-key selection mode used when ``include_values=True``. :param missing_value: Fill value for missing keys. :param include_vector_meta: Include helper metadata columns. :param as_multipart: If True, export one row per zone as Multi*. .. py:method:: export_to_geopackage(filename: str, layer: str = 'zones', include_values: bool = True, value_columns: str | list[str] | tuple[str, Ellipsis] = 'common', missing_value=np.nan, include_vector_meta: bool = True, as_multipart: bool = False) Export to GeoPackage using GeoPandas. :param filename: Output GeoPackage path. :param layer: Layer name inside the GeoPackage. :param include_values: If True, export per-vector property values. :param value_columns: Property-key selection mode used when ``include_values=True``. :param missing_value: Fill value for missing keys. :param include_vector_meta: Include helper metadata columns. :param as_multipart: If True, export one row per zone as Multi*. .. py:method:: export_active_zone_to_shapefile(filename: str) Export the active zone to a shapefile. :param filename: Output shapefile path. .. py:method:: import_gdb(fn: str, bbox: shapely.geometry.Polygon = None, layers: list[str] = None, colname: str = None, value_columns: str | list[str] | tuple[str, Ellipsis] | None = None, share_multipart_values: bool = False) Import a GDB file using geopandas and Fiona. :param fn: Path to the GDB file. :param bbox: Optional bounding box to filter features. :param layers: List of layer names to import (default: all). :param colname: Column name used to build zone names. :param value_columns: Columns to store into vector properties. :param share_multipart_values: If True, multipart geometries share the same underlying ``_values`` dictionary across split vectors. .. py:method:: import_gpkg(fn: str, bbox: shapely.geometry.Polygon = None, layers: list[str] = None, colname: str = None, value_columns: str | list[str] | tuple[str, Ellipsis] | None = None, share_multipart_values: bool = False) Import a GeoPackage file using geopandas and Fiona. :param fn: Path to the GPKG file. :param bbox: Optional bounding box to filter features. :param layers: List of layer names to import (default: all). :param colname: Column name used to build zone names. :param value_columns: Columns to store into vector properties. :param share_multipart_values: If True, multipart geometries share the same underlying ``_values`` dictionary across split vectors. .. py:method:: colorize_data(colors: dict[str:list[int]], filled: bool = False) -> None Colorize zones based on a dictionary of colours. Zone names must match the dictionary keys. :param colors: Mapping ``{zone_name: [R, G, B]}``. :param filled: Whether polygons should be drawn filled. .. py:method:: set_width(width: int) -> None Set line width for all vectors in all zones. :param width: Width in pixels. .. py:method:: get_zone(keyzone: Union[int, str]) -> zoneModel Retrieve a zone by name or index. If multiple zones share the same name, only the first is returned. :param keyzone: Zone index (int) or zone name (str). :return: The matching zone, or *None* if not found. .. py:property:: zone_names :type: list[str] Return the list of zone names .. py:method:: import_dxf(fn, imported_elts=['POLYLINE', 'LWPOLYLINE', 'LINE']) Import of a DXF file as a 'Zones'. The DXF file is read and the elements are stored in zones based on their layers. The supported elements are POLYLINE, LWPOLYLINE and LINE. If you want to import other elements, you must upgrade this routine `import_dxf`. :param fn: name of the DXF file to import :param imported_elts: list of DXF elements to import. Default is ['POLYLINE','LWPOLYLINE','LINE']. :return: None .. py:method:: find_nearest_vertex(x: float, y: float) -> wolfhece.PyVertex.wolfvertex | None Find the nearest vertex across all zones. .. py:method:: find_nearest_vector(x: float, y: float) -> vectorModel Find the vector whose geometry is closest to a coordinate. :param x: X-coordinate. :param y: Y-coordinate. :return: The nearest vector. .. py:method:: find_vector_containing_point(x: float, y: float) -> vectorModel Find the first vector whose polygon contains the point. :param x: X-coordinate. :param y: Y-coordinate. :return: The containing vector, or *None*. .. py:method:: check_plot() L'objet doit être affiché Fonction principalement utile pour l'objet WolfMapViewer et le GUI .. py:method:: uncheck_plot(unload=True) Mark the object as not plotted. :param unload: Reserved for GUI subclasses. .. py:method:: save() Sauvegarde sur disque, sans remise en cause du nom de fichier .. py:method:: saveas(filename: str = '') Save to disk, optionally under a new filename. :param filename: New path; if empty, uses the current ``self.filename``. .. py:method:: add_zone(addedzone: zoneModel, forceparent=False) Add a zone to the collection. :param addedzone: The zone to add. :param forceparent: If True, set this object as the zone's parent. .. py:method:: create_zone(name: str = '') -> zoneModel Create a new zone and add it to the collection. :param name: Name of the new zone. :return: The newly created zone. .. py:method:: find_minmax(update=False, only_firstlast: bool = False) Trouve les bornes des vertices pour toutes les zones et tous les vecteurs :param update : si True, force la MAJ des minmax dans chaque zone; si False, compile les minmax déjà présents :param only_firstlast : si True, ne prend en compte que le premier et le dernier vertex de chaque vecteur .. py:method:: plot(sx=None, sy=None, xmin=None, ymin=None, xmax=None, ymax=None, size=None) Draw all zones. :param sx: Scale factor along X. :param sy: Scale factor along Y. :param xmin: Minimum X of the viewport. :param ymin: Minimum Y of the viewport. :param xmax: Maximum X of the viewport. :param ymax: Maximum Y of the viewport. :param size: Reference size for rendering. .. py:method:: get_bounds(force_to_update: bool = True) -> tuple[tuple[float, float], tuple[float, float]] Return the bounds of all zones. :param force_to_update: If True, recompute bounds before returning. :return: ``((xmin, xmax), (ymin, ymax))``. .. py:method:: select_vectors_from_point(x: float, y: float, inside=True) Select vectors in each zone from a coordinate. Fills the ``selected_vectors`` list of each zone. :param x: X-coordinate. :param y: Y-coordinate. :param inside: If True, select by containment; if False, select the nearest vector. .. py:method:: create_cs(wa) -> ZonesModel Create cross-section zones from the active zone. :param wa: Active WolfArray used to extract cross-section elevations. :return: A new ZonesModel containing the cross-sections, or *None*. .. py:method:: update_from_sz_direction(xy1: numpy.ndarray, xy2: numpy.ndarray, sz: numpy.ndarray) Update the active vector from curvilinear s-z values along a direction. :param xy1: Start point ``[x, y]`` of the direction. :param xy2: End point ``[x, y]`` of the direction. :param sz: Array of shape ``(n, 2)`` with columns ``[s, z]``. .. py:method:: get_selected_vectors(all=False) Return selected vectors from all zones. :param all: If True, return all selected vectors as a list; if False, return only the nearest selected vector. .. py:method:: unuse() Rend inutilisé l'ensemble des zones .. py:method:: use() Rend utilisé l'ensemble des zones .. py:method:: _callback_destroy_props() Callback invoked when the properties dialog is destroyed. .. py:method:: deepcopy_zones(name: str = None) -> ZonesModel Return a deep copy of this object. :param name: Optional name for the copy. :return: A new ``ZonesModel`` instance. .. py:method:: deepcopy(name: str = None) -> ZonesModel Return a deep copy of this object (alias for :meth:`deepcopy_zones`). :param name: Optional name for the copy. :return: A new ``ZonesModel`` instance. .. py:method:: keep_only_trace() Keep only the trace (first and last vertices) of all vectors for all zones in this Zones. .. py:method:: deepcopy_only_trace(name: str = None) -> ZonesModel Return a deep copy keeping only trace vertices (first and last). :param name: Optional name for the copy. :return: A new ``ZonesModel`` instance with trace-only vectors. .. py:method:: extend_along_trace(distance: float | str) Extend all vectors along their trace by the given distance. :param distance: Distance to extend (float) or 'auto' to extend by 10% of the vector length. .. py:class:: GridModel(size: float = 1000.0, ox: float = 0.0, oy: float = 0.0, ex: float = 1000.0, ey: float = 1000.0) Bases: :py:obj:`ZonesModel` .. autoapi-inheritance-diagram:: wolfhece.pyvertexvectors._models.GridModel :parts: 1 :private-bases: Pure-data Grid: one zone with gridx, gridy and contour vectors. GUI subclass ``Grid`` in :mod:`wolfhece.PyVertexvectors` inherits from this and adds wx/OpenGL support via ``Zones``. .. py:method:: creategrid(size: float = 100.0, ox: float = 0.0, oy: float = 0.0, ex: float = 1000.0, ey: float = 1000.0) (Re)create the grid lines and contour. Resets the gridx, gridy and contour vectors and rebuilds them as a regular rectangular grid. :param size: Grid cell size in world units. :param ox: X-coordinate of the grid origin (lower-left). :param oy: Y-coordinate of the grid origin (lower-left). :param ex: X-coordinate of the grid extent (upper-right). :param ey: Y-coordinate of the grid extent (upper-right).