hazy-frames 0.1.0__tar.gz → 0.2.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- hazy_frames-0.2.0/.github/workflows/ci.yml +57 -0
- hazy_frames-0.2.0/.github/workflows/release.yml +32 -0
- hazy_frames-0.2.0/.pre-commit-config.yaml +35 -0
- hazy_frames-0.2.0/.readthedocs.yaml +16 -0
- hazy_frames-0.2.0/CHANGELOG.md +131 -0
- hazy_frames-0.2.0/CLAUDE.md +452 -0
- hazy_frames-0.2.0/CONTRIBUTING.md +117 -0
- hazy_frames-0.2.0/PKG-INFO +123 -0
- hazy_frames-0.2.0/README.md +88 -0
- hazy_frames-0.2.0/docs/Makefile +12 -0
- hazy_frames-0.2.0/docs/README.md +33 -0
- hazy_frames-0.2.0/docs/api/frame.rst +14 -0
- hazy_frames-0.2.0/docs/api/geometric_primitives.rst +18 -0
- hazy_frames-0.2.0/docs/api/index.rst +9 -0
- hazy_frames-0.2.0/docs/api/utils.rst +16 -0
- hazy_frames-0.2.0/docs/conf.py +78 -0
- hazy_frames-0.2.0/docs/examples/.gitignore +1 -0
- hazy_frames-0.2.0/docs/examples/01-surface_intersections.ipynb +475 -0
- hazy_frames-0.2.0/docs/examples/02-frame-hierarchies.ipynb +185 -0
- hazy_frames-0.2.0/docs/examples/03-simple-robot-arm.ipynb +383 -0
- hazy_frames-0.2.0/docs/examples/04-simple-raytracing.ipynb +914 -0
- hazy_frames-0.2.0/docs/examples/index.rst +12 -0
- hazy_frames-0.2.0/docs/index.rst +61 -0
- hazy_frames-0.2.0/docs/installation.rst +51 -0
- hazy_frames-0.2.0/docs/quickstart.rst +87 -0
- hazy_frames-0.2.0/examples/01-surface_intersections.ipynb +475 -0
- hazy_frames-0.2.0/examples/02-frame-hierarchies.ipynb +185 -0
- hazy_frames-0.2.0/examples/03-simple-robot-arm.ipynb +383 -0
- hazy_frames-0.2.0/examples/04-simple-raytracing.ipynb +855 -0
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/pyproject.toml +34 -6
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/src/hazy/__init__.py +5 -2
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/src/hazy/constants.py +5 -0
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/src/hazy/frame.py +338 -111
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/src/hazy/primitives.py +619 -60
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/src/hazy/utils.py +9 -4
- hazy_frames-0.2.0/tests/conftest.py +121 -0
- hazy_frames-0.2.0/tests/test_frame.py +1435 -0
- hazy_frames-0.2.0/tests/test_integration.py +767 -0
- hazy_frames-0.2.0/tests/test_numpy_integration.py +549 -0
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/tests/test_primitives.py +4 -27
- hazy_frames-0.2.0/tests/test_utils.py +40 -0
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/uv.lock +870 -541
- hazy_frames-0.1.0/.github/badges/coverage.svg +0 -21
- hazy_frames-0.1.0/PKG-INFO +0 -253
- hazy_frames-0.1.0/README.md +0 -228
- hazy_frames-0.1.0/tests/test_frame.py +0 -747
- hazy_frames-0.1.0/tests/test_integration.py +0 -392
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/.gitignore +0 -0
- {hazy_frames-0.1.0 → hazy_frames-0.2.0}/LICENSE +0 -0
- /hazy_frames-0.1.0/tests/conftest.py → /hazy_frames-0.2.0/tests/__init__.py +0 -0
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
on:
|
|
3
|
+
push:
|
|
4
|
+
branches: ["main", "feat/**"]
|
|
5
|
+
pull_request:
|
|
6
|
+
branches: ["main"]
|
|
7
|
+
permissions:
|
|
8
|
+
contents: read
|
|
9
|
+
jobs:
|
|
10
|
+
lint:
|
|
11
|
+
runs-on: ubuntu-latest
|
|
12
|
+
steps:
|
|
13
|
+
- uses: actions/checkout@v4
|
|
14
|
+
|
|
15
|
+
- name: Install uv
|
|
16
|
+
uses: astral-sh/setup-uv@v4
|
|
17
|
+
|
|
18
|
+
- name: Set up Python
|
|
19
|
+
run: uv python install 3.12
|
|
20
|
+
|
|
21
|
+
- name: Install dependencies
|
|
22
|
+
run: uv sync --group dev
|
|
23
|
+
|
|
24
|
+
- name: Run ruff format check
|
|
25
|
+
run: uv run ruff format --check .
|
|
26
|
+
|
|
27
|
+
- name: Run ruff lint
|
|
28
|
+
run: uv run ruff check .
|
|
29
|
+
|
|
30
|
+
test:
|
|
31
|
+
runs-on: ubuntu-latest
|
|
32
|
+
strategy:
|
|
33
|
+
fail-fast: true
|
|
34
|
+
matrix:
|
|
35
|
+
python-version: ["3.12", "3.13"]
|
|
36
|
+
|
|
37
|
+
steps:
|
|
38
|
+
- uses: actions/checkout@v4
|
|
39
|
+
|
|
40
|
+
- name: Install uv
|
|
41
|
+
uses: astral-sh/setup-uv@v4
|
|
42
|
+
|
|
43
|
+
- name: Set up Python ${{ matrix.python-version }}
|
|
44
|
+
run: uv python install ${{ matrix.python-version }}
|
|
45
|
+
|
|
46
|
+
- name: Install dependencies
|
|
47
|
+
run: uv sync --group dev
|
|
48
|
+
|
|
49
|
+
- name: Run tests
|
|
50
|
+
run: uv run pytest --cov=src/hazy --cov-report=term --cov-report=xml
|
|
51
|
+
|
|
52
|
+
- name: Upload coverage
|
|
53
|
+
uses: codecov/codecov-action@v4
|
|
54
|
+
if: matrix.python-version == '3.12'
|
|
55
|
+
with:
|
|
56
|
+
file: ./coverage.xml
|
|
57
|
+
token: ${{ secrets.CODECOV_TOKEN }}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
name: Release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags:
|
|
6
|
+
- "v*"
|
|
7
|
+
|
|
8
|
+
permissions:
|
|
9
|
+
contents: write
|
|
10
|
+
|
|
11
|
+
jobs:
|
|
12
|
+
release:
|
|
13
|
+
runs-on: ubuntu-latest
|
|
14
|
+
steps:
|
|
15
|
+
- uses: actions/checkout@v4
|
|
16
|
+
|
|
17
|
+
- name: Install uv
|
|
18
|
+
uses: astral-sh/setup-uv@v4
|
|
19
|
+
|
|
20
|
+
- name: Set up Python
|
|
21
|
+
run: uv python install 3.12
|
|
22
|
+
|
|
23
|
+
- name: Build package
|
|
24
|
+
run: uv build
|
|
25
|
+
|
|
26
|
+
- name: Create GitHub Release
|
|
27
|
+
uses: softprops/action-gh-release@v2
|
|
28
|
+
with:
|
|
29
|
+
files: dist/*
|
|
30
|
+
draft: false
|
|
31
|
+
prerelease: false
|
|
32
|
+
body_path: CHANGELOG.md
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# Pre-commit hooks configuration
|
|
2
|
+
# See https://pre-commit.com for more information
|
|
3
|
+
|
|
4
|
+
repos:
|
|
5
|
+
# Ruff - fast Python linter and formatter
|
|
6
|
+
- repo: https://github.com/astral-sh/ruff-pre-commit
|
|
7
|
+
rev: v0.8.4
|
|
8
|
+
hooks:
|
|
9
|
+
# Run the linter
|
|
10
|
+
- id: ruff
|
|
11
|
+
args: [--fix]
|
|
12
|
+
language: system
|
|
13
|
+
# Run the formatter
|
|
14
|
+
- id: ruff-format
|
|
15
|
+
language: system
|
|
16
|
+
|
|
17
|
+
# Strip output from Jupyter notebooks
|
|
18
|
+
- repo: https://github.com/kynan/nbstripout
|
|
19
|
+
rev: 0.8.1
|
|
20
|
+
hooks:
|
|
21
|
+
- id: nbstripout
|
|
22
|
+
language: system
|
|
23
|
+
|
|
24
|
+
# General file cleaning hooks
|
|
25
|
+
- repo: https://github.com/pre-commit/pre-commit-hooks
|
|
26
|
+
rev: v5.0.0
|
|
27
|
+
hooks:
|
|
28
|
+
# Remove trailing whitespace
|
|
29
|
+
- id: trailing-whitespace
|
|
30
|
+
# Ensure files end with a newline
|
|
31
|
+
- id: end-of-file-fixer
|
|
32
|
+
# Check for files that would conflict on case-insensitive filesystems
|
|
33
|
+
- id: check-case-conflict
|
|
34
|
+
# Check for merge conflicts
|
|
35
|
+
- id: check-merge-conflict
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## [Unreleased]
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
|
|
12
|
+
- **Transformation Clear Methods**: New methods to reset transformations
|
|
13
|
+
- `Frame.clear_rotations()` - Reset all rotations to identity
|
|
14
|
+
- `Frame.clear_translations()` - Reset all translations to zero
|
|
15
|
+
- `Frame.clear_scalings()` - Reset all scalings to identity
|
|
16
|
+
- `Frame.clear_all_transforms()` - Reset all transformations at once
|
|
17
|
+
|
|
18
|
+
- **Array Input Support**: Enhanced NumPy integration for transformation methods
|
|
19
|
+
- `Frame.translate()` now accepts array input: `translate([x, y, z])`
|
|
20
|
+
- `Frame.scale()` now accepts array input: `scale([x, y, z])`
|
|
21
|
+
- Maintains backward compatibility with existing APIs
|
|
22
|
+
|
|
23
|
+
- **Examples**: New advanced optical raytracing example
|
|
24
|
+
- `03-simple-robot-arm.ipynb`: Robot arm kinematics with hierarchical frames and animation
|
|
25
|
+
- `04-simple-raytracing.ipynb`: Optical raytracing through lens surfaces
|
|
26
|
+
- Demonstrates frame transformations simplifying optical system design
|
|
27
|
+
- Implements meridional plane reduction for axisymmetric surfaces
|
|
28
|
+
- Shows spherical and hyperbolic lens profiles with aberration visualization
|
|
29
|
+
- Features immutable Ray class with Snell's law vector refraction
|
|
30
|
+
|
|
31
|
+
### Changed
|
|
32
|
+
|
|
33
|
+
- **Improved Error Messages**: Better validation and error messages for transformation methods
|
|
34
|
+
- `Frame.scale()` provides clearer guidance when mixing scalar and per-axis arguments
|
|
35
|
+
- Validates array shapes and provides helpful error messages
|
|
36
|
+
|
|
37
|
+
## [0.2.0] - 2025-11-15
|
|
38
|
+
|
|
39
|
+
### Added
|
|
40
|
+
|
|
41
|
+
- **Comprehensive NumPy Integration**: Native support for NumPy arrays and batch operations
|
|
42
|
+
- `from_array()` factory methods for `Point` and `Vector` classes
|
|
43
|
+
- `list_from_array()` for batch creation from NumPy arrays
|
|
44
|
+
- Support for array-like inputs in `Frame.point()` and `Frame.vector()`
|
|
45
|
+
- NumPy stack operations (`np.stack()`, `np.hstack()`, `np.vstack()`) for primitives
|
|
46
|
+
- Compatibility with NumPy scalar types (`np.float64`, `np.int32`, etc.)
|
|
47
|
+
- Dedicated test suite for NumPy integration (`tests/test_numpy_integration.py`)
|
|
48
|
+
|
|
49
|
+
- **Custom Formatters**: `__format__()` method for `GeometricPrimitive` with multiple output styles
|
|
50
|
+
- Standard format specifiers (e.g., `:6.2f`, `:.3f`, `:10.4e`) format all three components
|
|
51
|
+
- `'a'`: Array-only format without class name or frame info
|
|
52
|
+
- `'n'`: No-frame format showing only class name and coordinates
|
|
53
|
+
- Default: Full format with class name and frame
|
|
54
|
+
|
|
55
|
+
- **Multi-Index Support**: `__getitem__()` now supports advanced NumPy indexing
|
|
56
|
+
- Integer indexing: `primitive[0]` returns float
|
|
57
|
+
- Slicing: `primitive[0:2]` returns NDArray
|
|
58
|
+
- Fancy indexing: `primitive[[0, 2]]` returns NDArray
|
|
59
|
+
|
|
60
|
+
- **Quaternion Rotation Support**: `Frame.rotate_quat()` method for quaternion-based rotations
|
|
61
|
+
|
|
62
|
+
- **Child Frame Creation**: `Frame.make_child()` method to create child frames directly
|
|
63
|
+
|
|
64
|
+
- **Batch Transformations**: Explicit methods for batch operations
|
|
65
|
+
- `batch_transform_points()` for transforming multiple points
|
|
66
|
+
- `batch_transform_vectors()` for transforming multiple vectors
|
|
67
|
+
|
|
68
|
+
- **Parent-Child Tracking**: Frames now maintain bidirectional parent-child relationships
|
|
69
|
+
- Each frame tracks its direct children
|
|
70
|
+
- Cache invalidation propagates recursively through the hierarchy
|
|
71
|
+
|
|
72
|
+
- **Documentation**: Complete Sphinx documentation with ReadTheDocs integration
|
|
73
|
+
- Installation guide, quick start tutorial, and API reference
|
|
74
|
+
- Jupyter notebook examples integrated via nbsphinx
|
|
75
|
+
- Available at [hazy-frames.readthedocs.io](https://hazy-frames.readthedocs.io/)
|
|
76
|
+
|
|
77
|
+
- **Examples**: Two interactive Jupyter notebooks demonstrating core concepts
|
|
78
|
+
- `01-surface_intersections.ipynb`: Ray-plane intersection with coordinate transformations
|
|
79
|
+
- `02-frame-hierarchies.ipynb`: Parent-child relationships and dynamic transformations
|
|
80
|
+
|
|
81
|
+
- **CI/CD**: GitHub Actions workflow with pytest, ruff linting, and codecov integration
|
|
82
|
+
|
|
83
|
+
- **Pre-commit Hooks**: Automated code quality checks with ruff linter and formatter
|
|
84
|
+
|
|
85
|
+
### Changed
|
|
86
|
+
|
|
87
|
+
- **API Naming Improvements**: More consistent and pythonic naming conventions
|
|
88
|
+
- Removed `coords` property (use `np.array(primitive)` instead)
|
|
89
|
+
- Renamed `unit_x/y/z` to `axis_x/y/z` for frame axes
|
|
90
|
+
- Removed `make_` prefix from `Frame.point()` and `Frame.vector()` methods
|
|
91
|
+
- Simplified `Frame.scale()` API: uniform scaling with single argument, per-axis with three
|
|
92
|
+
|
|
93
|
+
- **Root Frame Handling**: Removed implicit singleton pattern
|
|
94
|
+
- Frames can now be orphans (no parent) instead of defaulting to global singleton
|
|
95
|
+
- More explicit frame hierarchy management
|
|
96
|
+
|
|
97
|
+
- **API Documentation**: Comprehensive docstrings with examples for all public methods
|
|
98
|
+
|
|
99
|
+
### Fixed
|
|
100
|
+
|
|
101
|
+
- **Cache Invalidation**: Parent frame modifications now properly invalidate child frame caches
|
|
102
|
+
- Previously, modifying a parent would cause stale transformations in child frames
|
|
103
|
+
- Cache invalidation now propagates recursively through the entire hierarchy
|
|
104
|
+
|
|
105
|
+
- **Vector Batch Transform**: Fixed critical bug in `batch_transform_vectors_global()` using incorrect homogeneous coordinate (was `w=1`, now correctly `w=0`)
|
|
106
|
+
|
|
107
|
+
- **Parent Immutability**: Frame parent is now immutable after creation to maintain hierarchy consistency
|
|
108
|
+
|
|
109
|
+
### Removed
|
|
110
|
+
|
|
111
|
+
- **Legacy Methods**: Removed redundant `Vector.unit_x/y/z()` methods (use `frame.axis_x/y/z` instead)
|
|
112
|
+
|
|
113
|
+
## [0.1.0] - 2025-11-09
|
|
114
|
+
|
|
115
|
+
Initial release of hazy-frames.
|
|
116
|
+
|
|
117
|
+
### Added
|
|
118
|
+
|
|
119
|
+
- Hierarchical frame system with parent-child relationships
|
|
120
|
+
- Frame-aware geometric primitives (`Point` and `Vector`)
|
|
121
|
+
- Automatic coordinate transformations between frames
|
|
122
|
+
- Transformation caching for performance
|
|
123
|
+
- Type-safe geometric arithmetic (e.g., Point - Point = Vector)
|
|
124
|
+
- Support for rotation (Euler angles), translation, and scaling
|
|
125
|
+
- NumPy array conversion via `__array__()` protocol
|
|
126
|
+
- Comprehensive test suite with pytest
|
|
127
|
+
- MIT License
|
|
128
|
+
|
|
129
|
+
[Unreleased]: https://github.com/Littie28/hazy-frames/compare/v0.2.0...HEAD
|
|
130
|
+
[0.2.0]: https://github.com/Littie28/hazy-frames/compare/v0.1.0...v0.2.0
|
|
131
|
+
[0.1.0]: https://github.com/Littie28/hazy-frames/releases/tag/v0.1.0
|