psychmetal
Native Metal stimulus presentation and Core Audio sound on Apple silicon Macs, from Python, with an interface resembling Psychtoolbox's Screen. There is no OpenGL anywhere in the path. The same engine serves PsychMetal for MATLAB and Octave.
Version 0.9.0 runs on Apple silicon Macs and in the separately built iPhone/iPad app. It has audio (sounds scheduled to the sample or to a frame, amplitude modulation on the same clock, recording and a voice key), native timelines with keyframes and live control, analytic masks, masked images, custom fragment shaders, and environment reports. See AUDIO.md, TIMELINE.md, GPU-MASKS.md, MASKED-IMAGES.md and CUSTOM-SHADERS.md in the source tree.
Install it into a virtual environment. Homebrew's Python (and any Python following PEP 668) refuses packages installed outside one:
python3 -m venv ~/venvs/psychmetal # once
source ~/venvs/psychmetal/bin/activate # in each new Terminal window
pip install /path/to/PsychMetal-0.9.0 # the source folder, or a release wheel
Requires macOS 14 or later on Apple silicon, an arm64 Python 3.10 or later, and numpy.
import psychmetal as pm
with pm.open_window(0, [0, 0, 0]) as (w, rect, ifi):
pm.fill_rect(w, [255, 0, 0], [100, 100, 300, 300])
vbl, onset, flip_return, missed, slipped = pm.flip(w)
pm.wait_secs(1)
Each PsychMetal command is a function with the snake_case name and the same arguments, order and defaults as in MATLAB; MATLAB's [] is None. Colours run 0–255 by default. Key indices are 0-based (kb_name('ESCAPE') is 40). Several rectangles, dot positions and per-item colours keep MATLAB's 4xN, 2xN and 3xN/4xN orientation, and images are numpy arrays (H, W[, C]) in any memory layout, read without copying. help(psychmetal) covers threading, batching and the other details.
Demos and hardware checks (Gabors, dynamic noise, textures, dot motion, keyboard, a live spectrogram with a recorder, phase and frequency matching of flicker and sound, an inventory of every command) are in the repository's python folder.
Flip timestamps come from Metal's presentation reports, and sound times from Core Audio's, not from a photodiode or a microphone. See the repository for validation and its limits.
info = pm.open_audio()
beep = pm.make_sound(pm.tone(1000, 0.05, info['rate']))
pm.play(beep, when=pm.get_secs() + 0.5)
print(pm.audio_results(wait=1)) # when it started, on the sample nearest the time asked
pm.close_audio()
pm.play_timeline(w, frames, tracks) replays a queued scene natively, with no
per-frame Python calls; timeline_demo.py shows it. pm.draw_masked_texture
applies analytic GPU coverage to an image; masked_image_demo.py shows it.
pm.stop() ends a running experiment, including native playback and waits.
MIT license.
Metadata
Release files for psychmetal 0.9.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| psychmetal-0.9.0.tar.gz | 189.6 kB | Details |
Built distributions (wheels)
| File | Reset | |||
|---|---|---|---|---|
| psychmetal-0.9.0-cp314-cp314-macosx_14_0_arm64.whl | CPython 3.14 | CPython 3.14 | macOS 14.0+ ARM64 | Details |
| psychmetal-0.9.0-cp313-cp313-macosx_14_0_arm64.whl | CPython 3.13 | CPython 3.13 | macOS 14.0+ ARM64 | Details |
| psychmetal-0.9.0-cp312-cp312-macosx_14_0_arm64.whl | CPython 3.12 | CPython 3.12 | macOS 14.0+ ARM64 | Details |
| psychmetal-0.9.0-cp311-cp311-macosx_14_0_arm64.whl | CPython 3.11 | CPython 3.11 | macOS 14.0+ ARM64 | Details |
| psychmetal-0.9.0-cp310-cp310-macosx_14_0_arm64.whl | CPython 3.10 | CPython 3.10 | macOS 14.0+ ARM64 | Details |
Total release size: 1.9 MB
Release files / psychmetal-0.9.0.tar.gz
| Download URL | psychmetal-0.9.0.tar.gz |
|---|---|
| Size | 189.6 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
91eb087e9e1ee0f8dececa24e2579a37335395fa1db4412f3adb4466f5513850
|
|
BLAKE2b-256 checksum How to use checksums |
6ca05301e5a97e453c80af07d123e0bf72d31362a299e281f25047b5e2696397
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency logRelease files / psychmetal-0.9.0-cp314-cp314-macosx_14_0_arm64.whl
| Download URL | psychmetal-0.9.0-cp314-cp314-macosx_14_0_arm64.whl |
|---|---|
| Size | 336.7 kB |
| Tags | CPython 3.14 macOS 14.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
9de4af996af612cdad6ca2c2a8b23de60c311715f2fc397314cf17941e07fc5f
|
|
BLAKE2b-256 checksum How to use checksums |
0ffa3b18c5874cea6116aabd9373f94e191058f746095b7225a4c25f1c30af82
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency logRelease files / psychmetal-0.9.0-cp313-cp313-macosx_14_0_arm64.whl
| Download URL | psychmetal-0.9.0-cp313-cp313-macosx_14_0_arm64.whl |
|---|---|
| Size | 336.7 kB |
| Tags | CPython 3.13 macOS 14.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
329864d06677b47a44c68775310334d219b3391fd3ff9ef6de3e4b19a6677f09
|
|
BLAKE2b-256 checksum How to use checksums |
4b5a891373eabdbbbae8e6dd2678baa122b2d1132328525aa6c74b7dd1c54735
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency logRelease files / psychmetal-0.9.0-cp312-cp312-macosx_14_0_arm64.whl
| Download URL | psychmetal-0.9.0-cp312-cp312-macosx_14_0_arm64.whl |
|---|---|
| Size | 336.7 kB |
| Tags | CPython 3.12 macOS 14.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
ff5430aa73bb0e8948e58048ca5c90bdd04e776a9550648c7e46cd02a3a5b758
|
|
BLAKE2b-256 checksum How to use checksums |
6ece2bab569412a06db3197bfb3373db5bf793f56da0930ecc85f6a98799a68a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency logRelease files / psychmetal-0.9.0-cp311-cp311-macosx_14_0_arm64.whl
| Download URL | psychmetal-0.9.0-cp311-cp311-macosx_14_0_arm64.whl |
|---|---|
| Size | 336.6 kB |
| Tags | CPython 3.11 macOS 14.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
8681ace977df2aa30c580eefa4de6c0a1290e2e23b0bbcf3b87a2c27f7983af0
|
|
BLAKE2b-256 checksum How to use checksums |
37c7d9db98883d7eb728f6e7423f6cac4b0ca9e7195068a1c0fda21290878b66
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency logRelease files / psychmetal-0.9.0-cp310-cp310-macosx_14_0_arm64.whl
| Download URL | psychmetal-0.9.0-cp310-cp310-macosx_14_0_arm64.whl |
|---|---|
| Size | 336.6 kB |
| Tags | CPython 3.10 macOS 14.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
f73b178a8547c8edbf601c542bae0cb09aa85735e3baa215a0c54ed4667dfc90
|
|
BLAKE2b-256 checksum How to use checksums |
6b5d9af0ff519d2c88f01a49da741637f970fed420a6ac0a625be1dde0c2f373
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.
Transparency log