Lens Picture

This notebook demonstrates the simulation and optimization of an optical system using the diffinytrace package.
It was run in Google Colab to take advantage of GPU acceleration and Google Drive integration for saving results.
[1]:
%pip install diffinytrace.zip
Processing ./diffinytrace.zip
  Preparing metadata (setup.py) ... done
Requirement already satisfied: colour-science==0.4.7 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (0.4.7)
Requirement already satisfied: matplotlib==3.10.8 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (3.10.8)
Requirement already satisfied: numpy==2.3.5 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (2.3.5)
Requirement already satisfied: pandas==3.0.1 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (3.0.1)
Requirement already satisfied: Pillow==12.0.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (12.0.0)
Requirement already satisfied: plotly==6.6.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (6.6.0)
Requirement already satisfied: pvlib==0.15.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (0.15.0)
Requirement already satisfied: scikit_learn==1.8.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (1.8.0)
Requirement already satisfied: scipy==1.17.1 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (1.17.1)
Requirement already satisfied: tqdm==4.67.3 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (4.67.3)
Requirement already satisfied: nbformat==5.1.3 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (5.1.3)
Requirement already satisfied: ipykernel==7.2.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (7.2.0)
Requirement already satisfied: cadquery==2.7.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (2.7.0)
Requirement already satisfied: torchmetrics==1.9.0 in /usr/local/lib/python3.12/dist-packages (from diffinytrace==2.1) (1.9.0)
Requirement already satisfied: cadquery-ocp<7.9,>=7.8.1 in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (7.8.1.1.post1)
Requirement already satisfied: ezdxf>=1.3.0 in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (1.4.3)
Requirement already satisfied: multimethod<2.0,>=1.11 in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (1.12)
Requirement already satisfied: nlopt<3.0,>=2.9.0 in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (2.10.0)
Requirement already satisfied: runtype in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (0.5.3)
Requirement already satisfied: casadi in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (3.7.2)
Requirement already satisfied: path in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (17.1.1)
Requirement already satisfied: trame in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (3.12.0)
Requirement already satisfied: trame-vtk in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (2.11.7)
Requirement already satisfied: trame-components in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (2.5.0)
Requirement already satisfied: trame-vuetify in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (3.2.1)
Requirement already satisfied: pyparsing>=3.0.0 in /usr/local/lib/python3.12/dist-packages (from cadquery==2.7.0->diffinytrace==2.1) (3.3.2)
Requirement already satisfied: comm>=0.1.1 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (0.2.3)
Requirement already satisfied: debugpy>=1.6.5 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (1.8.15)
Requirement already satisfied: ipython>=7.23.1 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (7.34.0)
Requirement already satisfied: jupyter-client>=8.8.0 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (8.8.0)
Requirement already satisfied: jupyter-core!=6.0.*,>=5.1 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (5.9.1)
Requirement already satisfied: matplotlib-inline>=0.1 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (0.2.1)
Requirement already satisfied: nest-asyncio>=1.4 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (1.6.0)
Requirement already satisfied: packaging>=22 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (26.0)
Requirement already satisfied: psutil>=5.7 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (5.9.5)
Requirement already satisfied: pyzmq>=25 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (26.2.1)
Requirement already satisfied: tornado>=6.4.1 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (6.5.1)
Requirement already satisfied: traitlets>=5.4.0 in /usr/local/lib/python3.12/dist-packages (from ipykernel==7.2.0->diffinytrace==2.1) (5.7.1)
Requirement already satisfied: contourpy>=1.0.1 in /usr/local/lib/python3.12/dist-packages (from matplotlib==3.10.8->diffinytrace==2.1) (1.3.3)
Requirement already satisfied: cycler>=0.10 in /usr/local/lib/python3.12/dist-packages (from matplotlib==3.10.8->diffinytrace==2.1) (0.12.1)
Requirement already satisfied: fonttools>=4.22.0 in /usr/local/lib/python3.12/dist-packages (from matplotlib==3.10.8->diffinytrace==2.1) (4.62.1)
Requirement already satisfied: kiwisolver>=1.3.1 in /usr/local/lib/python3.12/dist-packages (from matplotlib==3.10.8->diffinytrace==2.1) (1.5.0)
Requirement already satisfied: python-dateutil>=2.7 in /usr/local/lib/python3.12/dist-packages (from matplotlib==3.10.8->diffinytrace==2.1) (2.9.0.post0)
Requirement already satisfied: ipython-genutils in /usr/local/lib/python3.12/dist-packages (from nbformat==5.1.3->diffinytrace==2.1) (0.2.0)
Requirement already satisfied: jsonschema!=2.5.0,>=2.4 in /usr/local/lib/python3.12/dist-packages (from nbformat==5.1.3->diffinytrace==2.1) (4.26.0)
Requirement already satisfied: narwhals>=1.15.1 in /usr/local/lib/python3.12/dist-packages (from plotly==6.6.0->diffinytrace==2.1) (2.19.0)
Requirement already satisfied: pytz in /usr/local/lib/python3.12/dist-packages (from pvlib==0.15.0->diffinytrace==2.1) (2025.2)
Requirement already satisfied: requests in /usr/local/lib/python3.12/dist-packages (from pvlib==0.15.0->diffinytrace==2.1) (2.32.4)
Requirement already satisfied: h5py in /usr/local/lib/python3.12/dist-packages (from pvlib==0.15.0->diffinytrace==2.1) (3.16.0)
Requirement already satisfied: joblib>=1.3.0 in /usr/local/lib/python3.12/dist-packages (from scikit_learn==1.8.0->diffinytrace==2.1) (1.5.3)
Requirement already satisfied: threadpoolctl>=3.2.0 in /usr/local/lib/python3.12/dist-packages (from scikit_learn==1.8.0->diffinytrace==2.1) (3.6.0)
Requirement already satisfied: torch>=2.0.0 in /usr/local/lib/python3.12/dist-packages (from torchmetrics==1.9.0->diffinytrace==2.1) (2.10.0+cu128)
Requirement already satisfied: lightning-utilities>=0.15.3 in /usr/local/lib/python3.12/dist-packages (from torchmetrics==1.9.0->diffinytrace==2.1) (0.15.3)
Requirement already satisfied: vtk==9.3.1 in /usr/local/lib/python3.12/dist-packages (from cadquery-ocp<7.9,>=7.8.1->cadquery==2.7.0->diffinytrace==2.1) (9.3.1)
Requirement already satisfied: typing_extensions>=4.6.0 in /usr/local/lib/python3.12/dist-packages (from ezdxf>=1.3.0->cadquery==2.7.0->diffinytrace==2.1) (4.15.0)
Requirement already satisfied: setuptools>=18.5 in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (75.2.0)
Requirement already satisfied: jedi>=0.16 in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.19.2)
Requirement already satisfied: decorator in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (4.4.2)
Requirement already satisfied: pickleshare in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.7.5)
Requirement already satisfied: prompt-toolkit!=3.0.0,!=3.0.1,<3.1.0,>=2.0.0 in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (3.0.52)
Requirement already satisfied: pygments in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (2.20.0)
Requirement already satisfied: backcall in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.2.0)
Requirement already satisfied: pexpect>4.3 in /usr/local/lib/python3.12/dist-packages (from ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (4.9.0)
Requirement already satisfied: attrs>=22.2.0 in /usr/local/lib/python3.12/dist-packages (from jsonschema!=2.5.0,>=2.4->nbformat==5.1.3->diffinytrace==2.1) (26.1.0)
Requirement already satisfied: jsonschema-specifications>=2023.03.6 in /usr/local/lib/python3.12/dist-packages (from jsonschema!=2.5.0,>=2.4->nbformat==5.1.3->diffinytrace==2.1) (2025.9.1)
Requirement already satisfied: referencing>=0.28.4 in /usr/local/lib/python3.12/dist-packages (from jsonschema!=2.5.0,>=2.4->nbformat==5.1.3->diffinytrace==2.1) (0.37.0)
Requirement already satisfied: rpds-py>=0.25.0 in /usr/local/lib/python3.12/dist-packages (from jsonschema!=2.5.0,>=2.4->nbformat==5.1.3->diffinytrace==2.1) (0.30.0)
Requirement already satisfied: platformdirs>=2.5 in /usr/local/lib/python3.12/dist-packages (from jupyter-core!=6.0.*,>=5.1->ipykernel==7.2.0->diffinytrace==2.1) (4.9.6)
Requirement already satisfied: six>=1.5 in /usr/local/lib/python3.12/dist-packages (from python-dateutil>=2.7->matplotlib==3.10.8->diffinytrace==2.1) (1.17.0)
Requirement already satisfied: filelock in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.25.2)
Requirement already satisfied: sympy>=1.13.3 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (1.14.0)
Requirement already satisfied: networkx>=2.5.1 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.6.1)
Requirement already satisfied: jinja2 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.1.6)
Requirement already satisfied: fsspec>=0.8.5 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (2025.3.0)
Requirement already satisfied: cuda-bindings==12.9.4 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.9.4)
Requirement already satisfied: nvidia-cuda-nvrtc-cu12==12.8.93 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.93)
Requirement already satisfied: nvidia-cuda-runtime-cu12==12.8.90 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.90)
Requirement already satisfied: nvidia-cuda-cupti-cu12==12.8.90 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.90)
Requirement already satisfied: nvidia-cudnn-cu12==9.10.2.21 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (9.10.2.21)
Requirement already satisfied: nvidia-cublas-cu12==12.8.4.1 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.4.1)
Requirement already satisfied: nvidia-cufft-cu12==11.3.3.83 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (11.3.3.83)
Requirement already satisfied: nvidia-curand-cu12==10.3.9.90 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (10.3.9.90)
Requirement already satisfied: nvidia-cusolver-cu12==11.7.3.90 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (11.7.3.90)
Requirement already satisfied: nvidia-cusparse-cu12==12.5.8.93 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.5.8.93)
Requirement already satisfied: nvidia-cusparselt-cu12==0.7.1 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (0.7.1)
Requirement already satisfied: nvidia-nccl-cu12==2.27.5 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (2.27.5)
Requirement already satisfied: nvidia-nvshmem-cu12==3.4.5 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.4.5)
Requirement already satisfied: nvidia-nvtx-cu12==12.8.90 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.90)
Requirement already satisfied: nvidia-nvjitlink-cu12==12.8.93 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (12.8.93)
Requirement already satisfied: nvidia-cufile-cu12==1.13.1.3 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (1.13.1.3)
Requirement already satisfied: triton==3.6.0 in /usr/local/lib/python3.12/dist-packages (from torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.6.0)
Requirement already satisfied: cuda-pathfinder~=1.1 in /usr/local/lib/python3.12/dist-packages (from cuda-bindings==12.9.4->torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (1.5.2)
Requirement already satisfied: charset_normalizer<4,>=2 in /usr/local/lib/python3.12/dist-packages (from requests->pvlib==0.15.0->diffinytrace==2.1) (3.4.7)
Requirement already satisfied: idna<4,>=2.5 in /usr/local/lib/python3.12/dist-packages (from requests->pvlib==0.15.0->diffinytrace==2.1) (3.11)
Requirement already satisfied: urllib3<3,>=1.21.1 in /usr/local/lib/python3.12/dist-packages (from requests->pvlib==0.15.0->diffinytrace==2.1) (2.5.0)
Requirement already satisfied: certifi>=2017.4.17 in /usr/local/lib/python3.12/dist-packages (from requests->pvlib==0.15.0->diffinytrace==2.1) (2026.2.25)
Requirement already satisfied: trame-server<4,>=3.4 in /usr/local/lib/python3.12/dist-packages (from trame->cadquery==2.7.0->diffinytrace==2.1) (3.10.0)
Requirement already satisfied: trame-client<4,>=3.10.1 in /usr/local/lib/python3.12/dist-packages (from trame->cadquery==2.7.0->diffinytrace==2.1) (3.11.4)
Requirement already satisfied: trame-common<2,>=1 in /usr/local/lib/python3.12/dist-packages (from trame->cadquery==2.7.0->diffinytrace==2.1) (1.1.3)
Requirement already satisfied: wslink>=2.3.3 in /usr/local/lib/python3.12/dist-packages (from trame->cadquery==2.7.0->diffinytrace==2.1) (2.5.6)
Requirement already satisfied: pyyaml in /usr/local/lib/python3.12/dist-packages (from trame->cadquery==2.7.0->diffinytrace==2.1) (6.0.3)
Requirement already satisfied: parso<0.9.0,>=0.8.4 in /usr/local/lib/python3.12/dist-packages (from jedi>=0.16->ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.8.6)
Requirement already satisfied: ptyprocess>=0.5 in /usr/local/lib/python3.12/dist-packages (from pexpect>4.3->ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.7.0)
Requirement already satisfied: wcwidth in /usr/local/lib/python3.12/dist-packages (from prompt-toolkit!=3.0.0,!=3.0.1,<3.1.0,>=2.0.0->ipython>=7.23.1->ipykernel==7.2.0->diffinytrace==2.1) (0.6.0)
Requirement already satisfied: mpmath<1.4,>=1.1.0 in /usr/local/lib/python3.12/dist-packages (from sympy>=1.13.3->torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (1.3.0)
Requirement already satisfied: more-itertools in /usr/local/lib/python3.12/dist-packages (from trame-server<4,>=3.4->trame->cadquery==2.7.0->diffinytrace==2.1) (10.8.0)
Requirement already satisfied: aiohttp<4 in /usr/local/lib/python3.12/dist-packages (from wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (3.13.5)
Requirement already satisfied: msgpack<2,>=1 in /usr/local/lib/python3.12/dist-packages (from wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (1.1.2)
Requirement already satisfied: MarkupSafe>=2.0 in /usr/local/lib/python3.12/dist-packages (from jinja2->torch>=2.0.0->torchmetrics==1.9.0->diffinytrace==2.1) (3.0.3)
Requirement already satisfied: aiohappyeyeballs>=2.5.0 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (2.6.1)
Requirement already satisfied: aiosignal>=1.4.0 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (1.4.0)
Requirement already satisfied: frozenlist>=1.1.1 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (1.8.0)
Requirement already satisfied: multidict<7.0,>=4.5 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (6.7.1)
Requirement already satisfied: propcache>=0.2.0 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (0.4.1)
Requirement already satisfied: yarl<2.0,>=1.17.0 in /usr/local/lib/python3.12/dist-packages (from aiohttp<4->wslink>=2.3.3->trame->cadquery==2.7.0->diffinytrace==2.1) (1.23.0)
Building wheels for collected packages: diffinytrace
  Building wheel for diffinytrace (setup.py) ... done
  Created wheel for diffinytrace: filename=diffinytrace-2.1-py3-none-any.whl size=88812 sha256=5666754bd81285164d374136a957cc67b7b9e85c51b4c1397a29a71648d504e1
  Stored in directory: /tmp/pip-ephem-wheel-cache-kw4re0m9/wheels/db/ea/21/35eb070bb05c3b3e3b9b47ff193267b4ac5b0871240da78a7c
Successfully built diffinytrace
Installing collected packages: diffinytrace
  Attempting uninstall: diffinytrace
    Found existing installation: diffinytrace 2.1
    Uninstalling diffinytrace-2.1:
      Successfully uninstalled diffinytrace-2.1
Successfully installed diffinytrace-2.1
[2]:
from google.colab import drive
drive.mount('/content/gdrive')
from os import listdir
from os.path import isfile, join
path = "gdrive/MyDrive/results_final"

Mounted at /content/gdrive
[3]:
import diffinytrace as dit
import torch
import numpy as np
torch.set_default_dtype(torch.float64)
import random

SEED = 0
np.random.seed(SEED)
torch.manual_seed(SEED)
random.seed(SEED)


from sunlight_picture import create_lens
import os
import pickle
import gc

def save_data(data, filename):
    with open(filename, 'wb') as file:
        pickle.dump(data, file)
    print(f"Data saved to {filename}")

def load_data(filename):
    with open(filename, 'rb') as file:
        data = pickle.load(file)
    print(f"Data loaded from {filename}")
    return data

def create_folder(folder_path):
    try:
        os.makedirs(folder_path, exist_ok=True)
        return f"Folder created successfully at: {folder_path}" if not os.path.exists(folder_path) else f"Folder already exists at: {folder_path}"
    except Exception as e:
        return f"An error occurred: {e}"

device = "cuda:0"
image_file_name = "img1.jpg"
results_folder_main = path+"/lens_picture/"
create_folder(results_folder_main)
sigma_final = 0.3
#theta_max_rad=5.

sigmas = None
ns_start = [4,4]
orders = [3,3]
num_refinements = 6
#num_refinements = 4
lens_thickness:float=5.

theta_max_rad = 20/1000.
detector_distance:float=60.

lens_distance:float=5.0

aperture_radius_source = 21.
image_padding = 0.2
grid_size = 256
num_rays = 2**21
#[1601,1601]
from diffinytrace import utils
#from diffinytrace.nonimaging import smoothing
aperture_radius_detector = aperture_radius_source*(1+image_padding)

print("num of conv points should probably be at least ", 2.0*aperture_radius_detector*2.0/sigma_final)

import numpy as np
import matplotlib.pyplot as plt

# Parameters
dx = (aperture_radius_detector*2.0)/grid_size
x = np.linspace(-dx*2, dx*2, 500)  # x-axis range

# Gaussian 1 centered at 0
gaussian1 = (1 / (sigma_final * np.sqrt(2 * np.pi))) * np.exp(-x**2 / (2 * sigma_final**2))

# Gaussian 2 centered at dx
gaussian2 = (1 / (sigma_final * np.sqrt(2 * np.pi))) * np.exp(-(x - dx)**2 / (2 * sigma_final**2))

# Plot
plt.figure(figsize=(8, 5))
plt.plot(x, gaussian1, label='Gaussian centered at 0')
plt.plot(x, gaussian2, label=r'Gaussian centered at $\Delta x$')
plt.title("Two 1D Gaussians")
plt.xlabel("x [mmm]")
plt.ylabel("y [1]")
plt.legend()
plt.grid()
plt.show()

gc.collect()
irr_func = utils.irradiance_importer.create_irradiance_from_image_square(image_file_name,image_padding,0.,aperture_radius_detector)

#quantity2D.plot(final_smoother.desired_smooth_irradiance.cpu().detach().numpy(),"Smoothed Desired Irr.",aperture_radius_detector,cmap="gray")
#plt.imshow(final_smoother.desired_smooth_irradiance.cpu().detach().numpy()[::-1])
#%%
def make_run(subfolder_main,use_desired_irradiance_smoothing,T_margin):
    create_folder(subfolder_main)
    subfolder = subfolder_main

    #create_folder(subfolder)
    kwargs = dict(image_file_name=image_file_name,
                lens_material=dit.materials["PMMA"],
                air_material=dit.materials["AIR"],
                device=device,
                sigma=sigma_final,
                use_desired_irradiance_smoothing=use_desired_irradiance_smoothing,
                num_rays=num_rays,
                num_refinements=num_refinements,
                grid_size=grid_size,
                theta_max_rad=theta_max_rad,
                T_margin=T_margin,
                lens_thickness=lens_thickness,
                detector_distance=detector_distance,
                lens_distance=lens_distance,
                )

    results = create_lens(**kwargs)
    save_data(results, subfolder+"/results_dict.pkl")
    del results
    gc.collect()


num of conv points should probably be at least  336.0
_images/diffinytrace_server_lens_picture_3_1.png
[4]:
from diffinytrace import (
    source, transforms, Bspline, Plane, Lens, Detector, SequentialOpticalSystem,
    utils, plotting, target_grid, render, minimize, set_unused_bspline_coeff_to_nearest,
    export, gaussian_smoother
)
import matplotlib.pyplot as plt
import diffinytrace as dit
import torch
from typing import List



aperture_radius_source:float=21.
aperture_radius_lens:float=25.
image_padding:float=0.2


lens_material=dit.materials["PMMA"]
air_material=dit.materials["AIR"]
light_transform = transforms.Offset(torch.tensor([0.0,0.0,0.0]))
light_transform.pos.requires_grad = False

light_source = None

light_source = source.VisibleSunlightSimpleMonochromatic(light_transform,aperture_radius_source,wl=0.5,total_power=1.0,theta_max_rad=theta_max_rad)
lens_transform = transforms.Distance(lens_distance,parent_transform=light_transform)

aperture_radius_detector = aperture_radius_source*(1+image_padding)

bspline_surface1 = Bspline(aperture_radius_lens,orders,ns_start)

surface1 = Plane()
lens1 = Lens(lens_transform,lens_thickness,surface1,bspline_surface1,lens_material,aperture_radius_lens,is_square=True)
lens_transform.distance.requires_grad = False
lens1.lens_thickness.requires_grad = False
detector_transform = transforms.Distance(detector_distance,parent_transform=lens1)#25.0+0.5
detector_transform.distance.requires_grad = False
plane_surface = Plane()
detector = Detector(detector_transform,plane_surface,aperture_radius_detector)
system = SequentialOpticalSystem({"source":light_source,"lens":lens1,"detector":detector},air_material)
sequence = ["source","lens","detector"]


x,weights = light_source.sample([1,5,5,5],"simpson")

#x,weights = light_source.sample(2000)

O,D,wave_len,_,RayPaths = system(x,sequence)

system.to("cpu")
offset_arrows = -(aperture_radius_lens+1)

Only sobol_pow2,sobol or monte_carlo sampling supported for VisibleSunlightSimpleMonochromatic
/usr/local/lib/python3.12/dist-packages/torch/functional.py:505: UserWarning: torch.meshgrid: in an upcoming release, it will be required to pass the indexing argument. (Triggered internally at /pytorch/aten/src/ATen/native/TensorShape.cpp:4381.)
  return _VF.meshgrid(tensors, **kwargs)  # type: ignore[attr-defined]
[14]:

def run_all_methods(): gc.collect() subfolder_main = results_folder_main+"/results_desired_irr_smoothing" make_run(subfolder_main,use_desired_irradiance_smoothing = True,T_margin=None) gc.collect() subfolder_main = results_folder_main+"/results_classical" make_run(subfolder_main,use_desired_irradiance_smoothing = False,T_margin=None) gc.collect() run_all_methods()
in create lens
after system init
after system to device
pre smoother init
after smoother init
after eval_func init
BEGIN: opti after refine: coeff shape: torch.Size([4, 4])
last_merit tensor(0.0071, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00705260743574
last_error (tensor(0.0082), tensor(0.0002), tensor(0.7922)) 0.008244025422616102
END
BEGIN: opti after refine: coeff shape: torch.Size([6, 6])
last_merit tensor(0.0064, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00641845394323
last_error (tensor(0.0077), tensor(0.0002), tensor(0.8056)) 0.00765247376305787
END
BEGIN: opti after refine: coeff shape: torch.Size([10, 10])
last_merit tensor(0.0046, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00464712997668
last_error (tensor(0.0062), tensor(0.0001), tensor(0.8206)) 0.006184337578308565
END
BEGIN: opti after refine: coeff shape: torch.Size([18, 18])
last_merit tensor(0.0031, device='cuda:0', grad_fn=<SqrtBackward0>) 0.0031097300493
last_error (tensor(0.0050), tensor(9.9376e-05), tensor(0.8425)) 0.005003939945132245
END
BEGIN: opti after refine: coeff shape: torch.Size([34, 34])
last_merit tensor(0.0020, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00198103558025
last_error (tensor(0.0044), tensor(8.7174e-05), tensor(0.8618)) 0.004392787688376916
END
BEGIN: opti after refine: coeff shape: torch.Size([66, 66])
last_merit tensor(0.0012, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00122569508378
last_error (tensor(0.0041), tensor(8.1533e-05), tensor(0.8743)) 0.004112682494093111
END
BEGIN: opti after refine: coeff shape: torch.Size([130, 130])
last_merit tensor(0.0010, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00100309784371
last_error (tensor(0.0040), tensor(8.0040e-05), tensor(0.8829)) 0.0040419741300820634
END
100%|██████████| 1000/1000 [12:15<00:00,  1.36it/s]
Data saved to gdrive/MyDrive/results_final/lens_picture//results_desired_irr_smoothing/results_dict.pkl
in create lens
after system init
after system to device
pre smoother init
after smoother init
after eval_func init
BEGIN: opti after refine: coeff shape: torch.Size([4, 4])
last_merit tensor(0.0087, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00869124639883
last_error (tensor(0.0087), tensor(0.0002), tensor(0.7489)) 0.008648570836628374
END
BEGIN: opti after refine: coeff shape: torch.Size([6, 6])
last_merit tensor(0.0078, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00784546959036
last_error (tensor(0.0078), tensor(0.0002), tensor(0.7961)) 0.007776924767509648
END
BEGIN: opti after refine: coeff shape: torch.Size([10, 10])
last_merit tensor(0.0063, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00628575566533
last_error (tensor(0.0063), tensor(0.0001), tensor(0.8058)) 0.006265553724726324
END
BEGIN: opti after refine: coeff shape: torch.Size([18, 18])
last_merit tensor(0.0051, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00513838046929
last_error (tensor(0.0051), tensor(0.0001), tensor(0.8308)) 0.005098846773479705
END
BEGIN: opti after refine: coeff shape: torch.Size([34, 34])
last_merit tensor(0.0043, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00431877371606
last_error (tensor(0.0045), tensor(8.8706e-05), tensor(0.8521)) 0.004471681287180115
END
BEGIN: opti after refine: coeff shape: torch.Size([66, 66])
last_merit tensor(0.0039, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00385829548256
last_error (tensor(0.0042), tensor(8.4029e-05), tensor(0.8596)) 0.004237167682689041
END
BEGIN: opti after refine: coeff shape: torch.Size([130, 130])
last_merit tensor(0.0037, device='cuda:0', grad_fn=<SqrtBackward0>) 0.00368949622911
last_error (tensor(0.0043), tensor(8.4396e-05), tensor(0.8656)) 0.0042489995618780925
END
100%|██████████| 1000/1000 [12:15<00:00,  1.36it/s]
Data saved to gdrive/MyDrive/results_final/lens_picture//results_classical/results_dict.pkl
[6]:

dit.plotting.system2D.plot(system,RayPaths,500,show = False) """dit.plotting.system2D.annotated_arrow([0,offset_arrows],[lens_distance,offset_arrows],(-30,-12),f"${int(lens_distance)}$[mm]","<->") dit.plotting.system2D.annotated_arrow([lens_distance,offset_arrows],[lens_distance+lens_thickness,offset_arrows],(-12,-12),f"${int(lens_thickness)}$[mm]","<->") dit.plotting.system2D.annotated_arrow([lens_distance+lens_thickness,offset_arrows],[lens_distance+lens_thickness+detector_distance,offset_arrows],(0,-12),f"${int(detector_distance)}$[mm]","<->") dit.plotting.system2D.annotated_arrow([-1,-aperture_radius_source],[-1,aperture_radius_source],(-12,-12),f"${int(aperture_radius_source*2)}$[mm]","<->",rotation=90) dit.plotting.system2D.annotated_arrow([lens_distance+lens_thickness+detector_distance+1,-aperture_radius_detector],[lens_distance+lens_thickness+detector_distance+1,aperture_radius_detector],(3,-12),f"${int(aperture_radius_detector*2)}$[mm]","<->",rotation=90) dit.plotting.system2D.annotate_position([0,aperture_radius_source],(-20,20),"Light source") dit.plotting.system2D.annotate_position([lens_distance+lens_thickness,aperture_radius_lens],(15,10),"Lens") dit.plotting.system2D.annotate_position([lens_distance+lens_thickness+detector_distance,aperture_radius_detector],(-50,10),"Target") """ ax = plt.gca() z_source = 0.0 z_lens_start = 5.0 z_lens_end = 10.0 z_target = 70.0 source_half_height = 21.0 # 42 mm total lens_half_height = 25.0 # 50 mm total (covers full aperture) target_half_height = 25.0 # 50 mm total # Target (green vertical line) ax.plot([z_target, z_target], [-target_half_height, target_half_height], color='limegreen', linewidth=2.0, solid_capstyle='butt') # --- Annotations --- # "Light source" label with arrow ax.annotate('Light source', xy=(z_source + 0.3, source_half_height - 1), xytext=(12, 27), fontsize=11, arrowprops=dict(arrowstyle='->', color='black', lw=1.0), ha='left', va='bottom') # "Target" label with arrow ax.annotate('Target', xy=(z_target - 0.3, target_half_height - 1), xytext=(65, 27), fontsize=11, arrowprops=dict(arrowstyle='->', color='black', lw=1.0), ha='left', va='bottom') # --- Dimension arrows --- from matplotlib.patches import FancyArrowPatch def dim_arrow(ax, x0, y0, x1, y1): """Draw a double-headed dimension arrow with tips exactly at endpoints.""" arrow = FancyArrowPatch( (x0, y0), (x1, y1), arrowstyle='<->', mutation_scale=10, color='black', lw=1.0, shrinkA=0, shrinkB=0, clip_on=False) ax.add_patch(arrow) # Vertical dimension: 42 mm on left side (close to source) dim_x_left = -3.0 dim_arrow(ax, dim_x_left, -source_half_height, dim_x_left, source_half_height) ax.text(dim_x_left - 2.0, 0, '42 mm', fontsize=10, ha='center', va='center', rotation=90) # Vertical dimension: 50 mm on right side (close to target) dim_x_right = 83.0 dim_arrow(ax, dim_x_right, -target_half_height, dim_x_right, target_half_height) ax.text(dim_x_right + 3.0, 0, '50 mm', fontsize=10, ha='center', va='center', rotation=90) # Horizontal dimensions at bottom dim_y = -29.0 # 5 mm: z=0 to z=5 dim_arrow(ax, z_source, dim_y, z_lens_start, dim_y) ax.text((z_source + z_lens_start) / 2 - 4.0, dim_y - 1.5, '5 mm', fontsize=10, ha='center', va='top', rotation=45) # 5 mm: z=5 to z=10 dim_arrow(ax, z_lens_start, dim_y, z_lens_end, dim_y) ax.text((z_lens_start + z_lens_end) / 2 - 2.5, dim_y - 1.5, '5 mm', fontsize=10, ha='center', va='top', rotation=45) # 70 mm: z=10 to z=80 dim_arrow(ax, z_lens_end, dim_y, z_target, dim_y) ax.text((z_lens_end + z_target) / 2, dim_y - 2.0, '60 mm', fontsize=10, ha='center', va='top') # --- Remove frame, axis labels, tick labels --- ax.set_axis_off() # Set limits to give appropriate padding ax.set_xlim(-8, 88) ax.set_ylim(-34, 32) ax.set_aspect('equal') plt.tight_layout() plt.savefig(path+"/layout3.png", dpi=400, bbox_inches='tight') #import os #os.kill(os.getpid(), 9)
WARNING: ray_paths will project the ray position onto the y-z plane!
_images/diffinytrace_server_lens_picture_6_1.png
[ ]: