PyOptik 3.2.0__tar.gz → 3.2.1__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.
Files changed (106) hide show
  1. pyoptik-3.2.1/.github/workflows/deploy_documentation.yml +56 -0
  2. {pyoptik-3.2.0 → pyoptik-3.2.1}/PKG-INFO +1 -1
  3. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/_version.py +3 -3
  4. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/catalog.py +5 -6
  5. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material/dataset.py +0 -1
  6. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/thin_film.py +0 -1
  7. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/tui.py +0 -1
  8. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/PKG-INFO +1 -1
  9. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/SOURCES.txt +3 -0
  10. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/scm_file_list.json +3 -0
  11. pyoptik-3.2.1/PyOptik.egg-info/scm_version.json +8 -0
  12. pyoptik-3.2.1/docs/images/logo.svg +22 -0
  13. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/_static/default.css +18 -1
  14. pyoptik-3.2.1/docs/source/_static/favicon.png +0 -0
  15. pyoptik-3.2.1/docs/source/_static/favicon.svg +18 -0
  16. pyoptik-3.2.1/docs/source/_static/logo-dark.svg +22 -0
  17. pyoptik-3.2.1/docs/source/_static/logo.svg +22 -0
  18. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/conf.py +6 -2
  19. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/index.rst +1 -21
  20. pyoptik-3.2.1/docs/source/user_guide.rst +35 -0
  21. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_catalog.py +26 -0
  22. pyoptik-3.2.0/.github/workflows/deploy_documentation.yml +0 -23
  23. pyoptik-3.2.0/PyOptik.egg-info/scm_version.json +0 -8
  24. pyoptik-3.2.0/docs/images/logo.svg +0 -1
  25. pyoptik-3.2.0/docs/source/_static/favicon.png +0 -0
  26. pyoptik-3.2.0/docs/source/_static/logo.svg +0 -1
  27. {pyoptik-3.2.0 → pyoptik-3.2.1}/.coveragerc +0 -0
  28. {pyoptik-3.2.0 → pyoptik-3.2.1}/.flake8 +0 -0
  29. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/dependabot.yml +0 -0
  30. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/workflows/deploy_PyPi.yml +0 -0
  31. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/workflows/deploy_anaconda.yml +0 -0
  32. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/workflows/deploy_coverage.yml +0 -0
  33. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/workflows/quality.yml +0 -0
  34. {pyoptik-3.2.0 → pyoptik-3.2.1}/.github/workflows/tests.yml +0 -0
  35. {pyoptik-3.2.0 → pyoptik-3.2.1}/.gitignore +0 -0
  36. {pyoptik-3.2.0 → pyoptik-3.2.1}/.pre-commit-config.yaml +0 -0
  37. {pyoptik-3.2.0 → pyoptik-3.2.1}/CHANGELOG.md +0 -0
  38. {pyoptik-3.2.0 → pyoptik-3.2.1}/CONTRIBUTING.md +0 -0
  39. {pyoptik-3.2.0 → pyoptik-3.2.1}/LICENSE +0 -0
  40. {pyoptik-3.2.0 → pyoptik-3.2.1}/Makefile +0 -0
  41. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/__init__.py +0 -0
  42. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/__main__.py +0 -0
  43. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/directories.py +0 -0
  44. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material/__init__.py +0 -0
  45. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material/base_class.py +0 -0
  46. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material/sellmeier_class.py +0 -0
  47. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material/tabulated_class.py +0 -0
  48. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/material_type.py +0 -0
  49. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik/utils.py +0 -0
  50. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/dependency_links.txt +0 -0
  51. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/entry_points.txt +0 -0
  52. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/requires.txt +0 -0
  53. {pyoptik-3.2.0 → pyoptik-3.2.1}/PyOptik.egg-info/top_level.txt +0 -0
  54. {pyoptik-3.2.0 → pyoptik-3.2.1}/README.rst +0 -0
  55. {pyoptik-3.2.0 → pyoptik-3.2.1}/conda.recipe/meta.yaml +0 -0
  56. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/Makefile +0 -0
  57. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/README.rst +0 -0
  58. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/catalog/README.rst +0 -0
  59. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/catalog/plot_catalog_search.py +0 -0
  60. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/custom_materials/README.rst +0 -0
  61. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/custom_materials/plot_measured_material.py +0 -0
  62. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/group_properties/README.rst +0 -0
  63. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/group_properties/plot_group_properties.py +0 -0
  64. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/interfaces/README.rst +0 -0
  65. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/interfaces/plot_fresnel_angles.py +0 -0
  66. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/sellmeier/README.rst +0 -0
  67. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/sellmeier/plot_bk7.py +0 -0
  68. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/sellmeier/plot_compare_glasses.py +0 -0
  69. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/sellmeier/plot_silica.py +0 -0
  70. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/sellmeier/plot_water.py +0 -0
  71. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/tabulated/README.rst +0 -0
  72. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/tabulated/plot_polyethylene.py +0 -0
  73. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/tabulated/plot_silicon_nk.py +0 -0
  74. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/tabulated/plot_silver.py +0 -0
  75. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/thin_films/README.rst +0 -0
  76. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/thin_films/plot_antireflection_coating.py +0 -0
  77. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/examples/thin_films/plot_bragg_mirror.py +0 -0
  78. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/images/example_bk7.png +0 -0
  79. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/make.bat +0 -0
  80. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/_static/thumbnail.png +0 -0
  81. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/catalog_browser.rst +0 -0
  82. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/code.rst +0 -0
  83. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/conventions.rst +0 -0
  84. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/custom_materials.rst +0 -0
  85. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/examples.rst +0 -0
  86. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/getting_started.rst +0 -0
  87. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/materials_and_catalog.rst +0 -0
  88. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/references.rst +0 -0
  89. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/sg_execution_times.rst +0 -0
  90. {pyoptik-3.2.0 → pyoptik-3.2.1}/docs/source/thin_films.rst +0 -0
  91. {pyoptik-3.2.0 → pyoptik-3.2.1}/pyproject.toml +0 -0
  92. {pyoptik-3.2.0 → pyoptik-3.2.1}/pytest.ini +0 -0
  93. {pyoptik-3.2.0 → pyoptik-3.2.1}/setup.cfg +0 -0
  94. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/__init__.py +0 -0
  95. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/conftest.py +0 -0
  96. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_base_material_decorator.py +0 -0
  97. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_datasets_and_custom_materials.py +0 -0
  98. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_docstrings.py +0 -0
  99. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_main_cli.py +0 -0
  100. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_material_models.py +0 -0
  101. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_thin_film.py +0 -0
  102. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_tui.py +0 -0
  103. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_utils_extra.py +0 -0
  104. {pyoptik-3.2.0 → pyoptik-3.2.1}/tests/test_validation_and_logging.py +0 -0
  105. {pyoptik-3.2.0 → pyoptik-3.2.1}/tools/next_release_version.py +0 -0
  106. {pyoptik-3.2.0 → pyoptik-3.2.1}/tools/release_tag.py +0 -0
@@ -0,0 +1,56 @@
1
+ # Simple workflow for deploying static content to GitHub Pages
2
+ name: Documentation
3
+
4
+ on:
5
+ push:
6
+ branches: [ "master" ]
7
+ tags: [ "v*" ]
8
+ pull_request:
9
+ branches: [ "master" ]
10
+
11
+ concurrency:
12
+ group: documentation-build-${{ github.repository }}-${{ github.ref }}
13
+ cancel-in-progress: true
14
+
15
+ permissions:
16
+ contents: write
17
+ pages: write
18
+ id-token: write
19
+
20
+ jobs:
21
+ ManyLinux_x86_64:
22
+ uses: MartinPdeS/MPSActions/.github/workflows/publish_documentation.yml@v5
23
+ with:
24
+ python-version: "3.11"
25
+ package-name: "PyOptik"
26
+ apt-package: xvfb jq
27
+ deploy-pages: ${{ github.event_name == 'push' && (github.ref == 'refs/heads/master' || startsWith(github.ref, 'refs/tags/v')) }}
28
+
29
+ deploy_pages:
30
+ needs: ManyLinux_x86_64
31
+ if: ${{ github.event_name == 'push' && (github.ref == 'refs/heads/master' || startsWith(github.ref, 'refs/tags/v')) }}
32
+ runs-on: ubuntu-latest
33
+ permissions:
34
+ contents: read
35
+ pages: write
36
+ id-token: write
37
+ environment:
38
+ name: github-pages
39
+ url: ${{ steps.deployment.outputs.page_url }}
40
+ steps:
41
+ - name: Checkout generated documentation
42
+ uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09
43
+ with:
44
+ ref: documentation_page
45
+
46
+ - name: Configure GitHub Pages
47
+ uses: actions/configure-pages@v5
48
+
49
+ - name: Upload GitHub Pages artifact
50
+ uses: actions/upload-pages-artifact@v3
51
+ with:
52
+ path: .
53
+
54
+ - name: Deploy GitHub Pages
55
+ id: deployment
56
+ uses: actions/deploy-pages@v4
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: PyOptik
3
- Version: 3.2.0
3
+ Version: 3.2.1
4
4
  Summary: A package for refractive index values.
5
5
  Author-email: Martin Poinsinet de Sivry-Houle <martin.poinsinet.de.sivry@gmail.com>
6
6
  License: MIT License
@@ -18,7 +18,7 @@ version_tuple: tuple[int | str, ...]
18
18
  commit_id: str | None
19
19
  __commit_id__: str | None
20
20
 
21
- __version__ = version = '3.2.0'
22
- __version_tuple__ = version_tuple = (3, 2, 0)
21
+ __version__ = version = '3.2.1'
22
+ __version_tuple__ = version_tuple = (3, 2, 1)
23
23
 
24
- __commit_id__ = commit_id = 'g7c8410160'
24
+ __commit_id__ = commit_id = 'g6f0650682'
@@ -1,6 +1,5 @@
1
1
  """Catalog and upstream-identity support for optical material data."""
2
2
 
3
- from __future__ import annotations
4
3
 
5
4
  from dataclasses import dataclass
6
5
  from pathlib import Path
@@ -78,7 +77,7 @@ class MaterialPage:
78
77
  if not self.available:
79
78
  return None
80
79
  try:
81
- with self.local_path.open("r") as stream:
80
+ with self.local_path.open("r", encoding="utf-8") as stream:
82
81
  reference = (yaml.safe_load(stream) or {}).get("REFERENCES")
83
82
  return str(reference) if reference is not None else None
84
83
  except (OSError, yaml.YAMLError):
@@ -286,7 +285,7 @@ class MaterialCatalog:
286
285
  existing_manifest = None
287
286
  if catalog_file.exists() and not force:
288
287
  try:
289
- with (root / "manifest.json").open("r") as stream:
288
+ with (root / "manifest.json").open("r", encoding="utf-8") as stream:
290
289
  existing_manifest = json.load(stream)
291
290
  except (FileNotFoundError, json.JSONDecodeError):
292
291
  existing_manifest = None
@@ -381,7 +380,7 @@ class MaterialCatalog:
381
380
  def load_catalog(self, catalog_file: Path | str) -> None:
382
381
  """Load an upstream ``catalog-nk.yml`` file."""
383
382
  catalog_file = Path(catalog_file)
384
- with catalog_file.open("r") as stream:
383
+ with catalog_file.open("r", encoding="utf-8") as stream:
385
384
  document = yaml.safe_load(stream) or []
386
385
  self._pages.clear()
387
386
 
@@ -529,7 +528,7 @@ class MaterialCatalog:
529
528
  if not self.manifest_path.exists():
530
529
  return {"catalog": {}, "pages": {}}
531
530
  try:
532
- with self.manifest_path.open("r") as stream:
531
+ with self.manifest_path.open("r", encoding="utf-8") as stream:
533
532
  manifest = json.load(stream)
534
533
  manifest.setdefault("catalog", {})
535
534
  manifest.setdefault("pages", {})
@@ -542,7 +541,7 @@ class MaterialCatalog:
542
541
  """Atomically write the download manifest after a page completes."""
543
542
  self.data_root.mkdir(parents=True, exist_ok=True)
544
543
  temporary = self.manifest_path.with_suffix(".json.tmp")
545
- with temporary.open("w") as stream:
544
+ with temporary.open("w", encoding="utf-8") as stream:
546
545
  json.dump(manifest, stream, indent=2, sort_keys=True)
547
546
  stream.write("\n")
548
547
  temporary.replace(self.manifest_path)
@@ -1,6 +1,5 @@
1
1
  """Typed, validated representations of PyOptik material datasets."""
2
2
 
3
- from __future__ import annotations
4
3
 
5
4
  from dataclasses import dataclass, field
6
5
  from pathlib import Path
@@ -1,6 +1,5 @@
1
1
  """Fresnel interfaces and coherent thin-film transfer-matrix calculations."""
2
2
 
3
- from __future__ import annotations
4
3
 
5
4
  from dataclasses import dataclass
6
5
  from typing import Any, Iterable
@@ -1,6 +1,5 @@
1
1
  """Optional Textual terminal interface for browsing the material catalog."""
2
2
 
3
- from __future__ import annotations
4
3
 
5
4
  from pathlib import Path
6
5
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: PyOptik
3
- Version: 3.2.0
3
+ Version: 3.2.1
4
4
  Summary: A package for refractive index values.
5
5
  Author-email: Martin Poinsinet de Sivry-Houle <martin.poinsinet.de.sivry@gmail.com>
6
6
  License: MIT License
@@ -76,8 +76,11 @@ docs/source/materials_and_catalog.rst
76
76
  docs/source/references.rst
77
77
  docs/source/sg_execution_times.rst
78
78
  docs/source/thin_films.rst
79
+ docs/source/user_guide.rst
79
80
  docs/source/_static/default.css
80
81
  docs/source/_static/favicon.png
82
+ docs/source/_static/favicon.svg
83
+ docs/source/_static/logo-dark.svg
81
84
  docs/source/_static/logo.svg
82
85
  docs/source/_static/thumbnail.png
83
86
  tests/__init__.py
@@ -58,6 +58,8 @@
58
58
  "docs/make.bat",
59
59
  "docs/source/_static/default.css",
60
60
  "docs/source/_static/favicon.png",
61
+ "docs/source/_static/favicon.svg",
62
+ "docs/source/_static/logo-dark.svg",
61
63
  "docs/source/_static/logo.svg",
62
64
  "docs/source/_static/thumbnail.png",
63
65
  "docs/source/catalog_browser.rst",
@@ -72,6 +74,7 @@
72
74
  "docs/source/references.rst",
73
75
  "docs/source/sg_execution_times.rst",
74
76
  "docs/source/thin_films.rst",
77
+ "docs/source/user_guide.rst",
75
78
  "pyproject.toml",
76
79
  "pytest.ini",
77
80
  "tests/__init__.py",
@@ -0,0 +1,8 @@
1
+ {
2
+ "tag": "3.2.1",
3
+ "distance": 0,
4
+ "node": "g6f0650682bb62d97e4d26a7dad770bdd207d0f42",
5
+ "dirty": true,
6
+ "branch": "HEAD",
7
+ "node_date": "2026-09-21"
8
+ }
@@ -0,0 +1,22 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 920 240" role="img" aria-labelledby="title description">
2
+ <title id="title">PyOptik</title>
3
+ <desc id="description">A beam of light passing through a prism and separating into three colors.</desc>
4
+ <defs>
5
+ <linearGradient id="prism" x1="0" y1="0" x2="1" y2="1">
6
+ <stop offset="0" stop-color="#1d73be"/>
7
+ <stop offset="1" stop-color="#0b2c4d"/>
8
+ </linearGradient>
9
+ </defs>
10
+ <g fill="none" stroke-linecap="round" stroke-linejoin="round">
11
+ <path d="M122 20 222 210H22Z" fill="url(#prism)" stroke="#45c2e6" stroke-width="6"/>
12
+ <path d="M0 133 105 116" stroke="#0e7490" stroke-width="10"/>
13
+ <path d="M105 116 146 111" stroke="#eaf8ff" stroke-width="10"/>
14
+ <path d="M146 111 250 65" stroke="#40c7ee" stroke-width="9"/>
15
+ <path d="M146 111 258 111" stroke="#32c69a" stroke-width="9"/>
16
+ <path d="M146 111 250 157" stroke="#f2b84b" stroke-width="9"/>
17
+ </g>
18
+ <g font-family="Inter, Avenir Next, Segoe UI, Arial, sans-serif">
19
+ <text x="290" y="126" fill="#102f52" font-size="92" font-weight="700" letter-spacing="-3">PyOptik</text>
20
+ <text x="296" y="174" fill="#39759e" font-size="24" font-weight="650" letter-spacing="5">OPTICAL MATERIALS</text>
21
+ </g>
22
+ </svg>
@@ -16,4 +16,21 @@ div.highlight a {
16
16
  /* Stack components in footer vertically. */
17
17
  .bd-footer .footer-items__end, .bd-footer .footer-items__start {
18
18
  flex-direction: row;
19
- }
19
+ }
20
+
21
+ /* Give the responsive wordmark a predictable footprint in the header. */
22
+ .navbar-brand.logo img {
23
+ width: 12.5rem;
24
+ max-height: 3.25rem;
25
+ }
26
+
27
+ /* Keep the compact primary navigation on one line at desktop widths. */
28
+ @media (min-width: 960px) {
29
+ .bd-header .navbar-nav {
30
+ flex-wrap: nowrap;
31
+ }
32
+
33
+ .bd-header .nav-link {
34
+ white-space: nowrap;
35
+ }
36
+ }
@@ -0,0 +1,18 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 240 240" role="img" aria-labelledby="title">
2
+ <title id="title">PyOptik prism</title>
3
+ <defs>
4
+ <linearGradient id="prism" x1="0" y1="0" x2="1" y2="1">
5
+ <stop offset="0" stop-color="#278bd5"/>
6
+ <stop offset="1" stop-color="#0b2c4d"/>
7
+ </linearGradient>
8
+ </defs>
9
+ <rect width="240" height="240" rx="42" fill="#101923"/>
10
+ <g fill="none" stroke-linecap="round" stroke-linejoin="round">
11
+ <path d="M108 28 181 190H35Z" fill="url(#prism)" stroke="#62d5f2" stroke-width="6"/>
12
+ <path d="M8 125 94 110" stroke="#eaf8ff" stroke-width="10"/>
13
+ <path d="M94 110 125 106" stroke="#ffffff" stroke-width="10"/>
14
+ <path d="M125 106 224 70" stroke="#50d7f6" stroke-width="9"/>
15
+ <path d="M125 106 230 111" stroke="#48d8aa" stroke-width="9"/>
16
+ <path d="M125 106 221 151" stroke="#ffc95c" stroke-width="9"/>
17
+ </g>
18
+ </svg>
@@ -0,0 +1,22 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 920 240" role="img" aria-labelledby="title description">
2
+ <title id="title">PyOptik</title>
3
+ <desc id="description">A beam of light passing through a prism and separating into three colors.</desc>
4
+ <defs>
5
+ <linearGradient id="prism" x1="0" y1="0" x2="1" y2="1">
6
+ <stop offset="0" stop-color="#278bd5"/>
7
+ <stop offset="1" stop-color="#12395f"/>
8
+ </linearGradient>
9
+ </defs>
10
+ <g fill="none" stroke-linecap="round" stroke-linejoin="round">
11
+ <path d="M122 20 222 210H22Z" fill="url(#prism)" stroke="#62d5f2" stroke-width="6"/>
12
+ <path d="M0 133 105 116" stroke="#d9f5ff" stroke-width="10"/>
13
+ <path d="M105 116 146 111" stroke="#ffffff" stroke-width="10"/>
14
+ <path d="M146 111 250 65" stroke="#50d7f6" stroke-width="9"/>
15
+ <path d="M146 111 258 111" stroke="#48d8aa" stroke-width="9"/>
16
+ <path d="M146 111 250 157" stroke="#ffc95c" stroke-width="9"/>
17
+ </g>
18
+ <g font-family="Inter, Avenir Next, Segoe UI, Arial, sans-serif">
19
+ <text x="290" y="126" fill="#f3f8fc" font-size="92" font-weight="700" letter-spacing="-3">PyOptik</text>
20
+ <text x="296" y="174" fill="#9cc9e5" font-size="24" font-weight="650" letter-spacing="5">OPTICAL MATERIALS</text>
21
+ </g>
22
+ </svg>
@@ -0,0 +1,22 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 920 240" role="img" aria-labelledby="title description">
2
+ <title id="title">PyOptik</title>
3
+ <desc id="description">A beam of light passing through a prism and separating into three colors.</desc>
4
+ <defs>
5
+ <linearGradient id="prism" x1="0" y1="0" x2="1" y2="1">
6
+ <stop offset="0" stop-color="#1d73be"/>
7
+ <stop offset="1" stop-color="#0b2c4d"/>
8
+ </linearGradient>
9
+ </defs>
10
+ <g fill="none" stroke-linecap="round" stroke-linejoin="round">
11
+ <path d="M122 20 222 210H22Z" fill="url(#prism)" stroke="#45c2e6" stroke-width="6"/>
12
+ <path d="M0 133 105 116" stroke="#0e7490" stroke-width="10"/>
13
+ <path d="M105 116 146 111" stroke="#eaf8ff" stroke-width="10"/>
14
+ <path d="M146 111 250 65" stroke="#40c7ee" stroke-width="9"/>
15
+ <path d="M146 111 258 111" stroke="#32c69a" stroke-width="9"/>
16
+ <path d="M146 111 250 157" stroke="#f2b84b" stroke-width="9"/>
17
+ </g>
18
+ <g font-family="Inter, Avenir Next, Segoe UI, Arial, sans-serif">
19
+ <text x="290" y="126" fill="#102f52" font-size="92" font-weight="700" letter-spacing="-3">PyOptik</text>
20
+ <text x="296" y="174" fill="#39759e" font-size="24" font-weight="650" letter-spacing="5">OPTICAL MATERIALS</text>
21
+ </g>
22
+ </svg>
@@ -46,7 +46,7 @@ napoleon_google_docstring = False
46
46
  napoleon_numpy_docstring = True
47
47
 
48
48
  html_logo = "_static/logo.svg"
49
- html_favicon = "_static/favicon.png"
49
+ html_favicon = "_static/favicon.svg"
50
50
 
51
51
 
52
52
  examples_files = [
@@ -106,7 +106,11 @@ binder_branch = f"v{major}.{minor}.x"
106
106
 
107
107
  html_theme_options = dict()
108
108
 
109
- html_theme_options['logo'] = dict(text=package_name, image="_static/logo.svg")
109
+ html_theme_options['logo'] = dict(
110
+ text="",
111
+ image_light="_static/logo.svg",
112
+ image_dark="_static/logo-dark.svg",
113
+ )
110
114
  html_theme_options["show_nav_level"] = 0
111
115
 
112
116
  html_theme_options.update({
@@ -41,30 +41,10 @@ Quick example
41
41
  print(interface.reflectance)
42
42
 
43
43
  .. toctree::
44
- :caption: Start here
45
44
  :maxdepth: 2
46
45
 
47
46
  getting_started
48
-
49
- .. toctree::
50
- :caption: User guide
51
- :maxdepth: 2
52
-
53
- materials_and_catalog
54
- custom_materials
55
- thin_films
56
- catalog_browser
57
-
58
- .. toctree::
59
- :caption: Learn by example
60
- :maxdepth: 2
61
-
47
+ user_guide
62
48
  examples
63
-
64
- .. toctree::
65
- :caption: Reference
66
- :maxdepth: 2
67
-
68
- conventions
69
49
  code
70
50
  references
@@ -0,0 +1,35 @@
1
+ User guide
2
+ ==========
3
+
4
+ Use these guides to move from material discovery to complete optical
5
+ calculations.
6
+
7
+ .. list-table::
8
+ :widths: 28 72
9
+
10
+ * - :doc:`Materials and catalog <materials_and_catalog>`
11
+ - Choose a material model, search the RefractiveIndex.INFO catalog, and
12
+ preserve provenance.
13
+ * - :doc:`Custom materials <custom_materials>`
14
+ - Import arrays or CSV data, define formula coefficients, validate data,
15
+ and export YAML.
16
+ * - :doc:`Interfaces and thin films <thin_films>`
17
+ - Calculate Fresnel coefficients, characteristic angles, and coherent
18
+ multilayer spectra.
19
+ * - :doc:`Catalog browser <catalog_browser>`
20
+ - Search and inspect the downloaded database from an interactive terminal
21
+ interface.
22
+ * - :doc:`Physical conventions <conventions>`
23
+ - Review wavelength, sign, interpolation, power, and provenance
24
+ conventions.
25
+
26
+ .. toctree::
27
+ :hidden:
28
+ :maxdepth: 2
29
+
30
+ materials_and_catalog
31
+ custom_materials
32
+ thin_films
33
+ catalog_browser
34
+ conventions
35
+
@@ -1,5 +1,6 @@
1
1
  import io
2
2
  import zipfile
3
+ from pathlib import Path
3
4
 
4
5
  import yaml
5
6
 
@@ -39,6 +40,31 @@ def test_catalog_reads_upstream_hierarchy(tmp_path):
39
40
  assert matches[0].provenance()["available"] is False
40
41
 
41
42
 
43
+ def test_catalog_opens_unicode_yaml_as_utf8(tmp_path, monkeypatch):
44
+ catalog_file = tmp_path / "catalog-nk.yml"
45
+ catalog_file.write_text(
46
+ "- SHELF: main\n"
47
+ " content:\n"
48
+ " - BOOK: Au\n"
49
+ " content:\n"
50
+ " - PAGE: Test\n"
51
+ " name: Gold – thin film\n"
52
+ " data: main/Au/nk/Test.yml\n",
53
+ encoding="utf-8",
54
+ )
55
+ original_open = Path.open
56
+
57
+ def checked_open(path, *args, **kwargs):
58
+ if path == catalog_file:
59
+ assert kwargs.get("encoding") == "utf-8"
60
+ return original_open(path, *args, **kwargs)
61
+
62
+ monkeypatch.setattr(Path, "open", checked_open)
63
+
64
+ catalog = MaterialCatalog(catalog_file=catalog_file, data_root=tmp_path / "rii")
65
+ assert catalog.get("main/Au/Test").description == "Gold – thin film"
66
+
67
+
42
68
  def test_catalog_loads_local_page(tmp_path):
43
69
  data_root = tmp_path / "rii"
44
70
  data_file = data_root / "main/Si/nk/Test.yml"
@@ -1,23 +0,0 @@
1
- # Simple workflow for deploying static content to GitHub Pages
2
- name: Documentation
3
-
4
- on:
5
- push:
6
- branches: [ "master" ]
7
- tags: '*'
8
- pull_request:
9
- branches: [ "master" ]
10
-
11
- # Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages
12
- permissions:
13
- contents: write
14
- pages: write
15
- id-token: write
16
-
17
- jobs:
18
- ManyLinux_x86_64:
19
- uses: MartinPdeS/MPSActions/.github/workflows/publish_documentation.yml@v5
20
- with:
21
- python-version: "3.11"
22
- package-name: "PyOptik"
23
- apt-package: xvfb jq
@@ -1,8 +0,0 @@
1
- {
2
- "tag": "3.2.0",
3
- "distance": 0,
4
- "node": "g7c8410160ff259451a9478f2f563f8a1188e1ed7",
5
- "dirty": true,
6
- "branch": "HEAD",
7
- "node_date": "2026-09-16"
8
- }
@@ -1 +0,0 @@
1
- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1500 420"><g transform="translate(35 45)"><path d="M165 25 300 280H30Z" fill="#123b75"/><path d="M165 25 165 280 30 280Z" fill="#2371c7"/><path d="M-10 194 165 164" stroke="#f4fbff" stroke-width="17"/><path d="M165 164 340 105M165 164 350 164M165 164 340 223" stroke-linecap="round" fill="none" stroke-width="13"/><path d="M165 164 340 105" stroke="#16bfe4" stroke-width="13"/><path d="M165 164 350 164" stroke="#23c99e" stroke-width="13"/><path d="M165 164 340 223" stroke="#f2ae3a" stroke-width="13"/></g><text x="430" y="190" font-family="Avenir Next,Arial,sans-serif" font-size="150" font-weight="700" fill="#102d5c">PyOptik</text><text x="437" y="264" font-family="Avenir Next,Arial,sans-serif" font-size="36" font-weight="600" letter-spacing="8" fill="#35669c">REFRACTIVE INDEX LIBRARY</text></svg>
@@ -1 +0,0 @@
1
- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1500 420"><g transform="translate(35 45)"><path d="M165 25 300 280H30Z" fill="#123b75"/><path d="M165 25 165 280 30 280Z" fill="#2371c7"/><path d="M-10 194 165 164" stroke="#f4fbff" stroke-width="17"/><path d="M165 164 340 105M165 164 350 164M165 164 340 223" stroke-linecap="round" fill="none" stroke-width="13"/><path d="M165 164 340 105" stroke="#16bfe4" stroke-width="13"/><path d="M165 164 350 164" stroke="#23c99e" stroke-width="13"/><path d="M165 164 340 223" stroke="#f2ae3a" stroke-width="13"/></g><text x="430" y="190" font-family="Avenir Next,Arial,sans-serif" font-size="150" font-weight="700" fill="#102d5c">PyOptik</text><text x="437" y="264" font-family="Avenir Next,Arial,sans-serif" font-size="36" font-weight="600" letter-spacing="8" fill="#35669c">REFRACTIVE INDEX LIBRARY</text></svg>
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes