openpiv – skill Thiết kế & UI cho agent AI
Thực hiện phân tích Particle Image Velocimetry (PIV) với OpenPIV. Dùng khi trích xuất trường vận tốc từ cặp ảnh PIV, phân tích động lực học chất lỏng hoặc thí nghiệm trực quan hóa dòng chảy, tương quan chéo các cửa sổ thẩm vấn (interrogation windows), kiểm tra và thay thế các vector PIV sai lệch, hoặc tính toán độ xoáy, tốc độ biến dạng và độ rối
Cài skill openpiv bằng một lệnh
Chọn công cụ bạn đang dùng, copy lệnh và dán vào terminal. Skill sẽ nằm trong thư mục skills của công cụ đó và sẵn sàng dùng ở phiên làm việc tiếp theo.
Claude Code
mkdir -p ~/.claude/skills && curl -fsSL https://skill.dn1nguoi.com/z/openpiv-eb545.tgz | tar xz -C ~/.claude/skills
Gọi trong Claude Code: /openpiv – rồi mô tả công việc bạn muốn làm.
Codex
mkdir -p ~/.codex/skills && curl -fsSL https://skill.dn1nguoi.com/z/openpiv-eb545.tgz | tar xz -C ~/.codex/skills
Gọi trong Codex: $openpiv – rồi mô tả công việc bạn muốn làm.
Hermes Agent
mkdir -p ~/.hermes/skills && curl -fsSL https://skill.dn1nguoi.com/z/openpiv-eb545.tgz | tar xz -C ~/.hermes/skills
Gọi trong Hermes Agent: /openpiv – rồi mô tả công việc bạn muốn làm.
DeepSeek
mkdir -p ~/.deepcode/skills && curl -fsSL https://skill.dn1nguoi.com/z/openpiv-eb545.tgz | tar xz -C ~/.deepcode/skills
Gọi trong DeepSeek: /openpiv – rồi mô tả công việc bạn muốn làm.
Nội dung SKILL.md
Nội dung SKILL.md gốc bằng tiếng Anh.
OpenPIV
Overview
OpenPIV (Open Particle Image Velocimetry) analyzes fluid flow from PIV image pairs. It covers
preprocessing, cross-correlation, vector validation, outlier replacement, smoothing, and scaling to
physical units.
Targets openpiv 0.26.1. Synthetic checks ran on Python 3.13, NumPy 2.5.3, SciPy 1.18.1,
scikit-image 0.26.0, and Matplotlib 3.11.2. Rust was not installed; use backend="scipy" for the
tested path. See [review evidence](references/advanced_algorithms.md#review-sources-and-verification).
When to use
Use this skill when working with experimental PIV or flow-visualization image pairs: measuring 2D
velocity fields, tuning interrogation-window parameters, validating vectors, or deriving vorticity,
strain rate, and turbulence statistics. For *simulating* flow rather than measuring it, use a CFD
skill instead.
Quick Start
Install OpenPIV:
uv pip install openpiv
# Pin it when the analysis needs to be reproducible -- this is the version every
# snippet below was checked against.
uv pip install "openpiv==0.26.1"Run PIV analysis on an image pair:
import numpy as np
from openpiv import tools, pyprocess, validation, filters, scaling
frame_a = tools.imread("image_a.bmp")
frame_b = tools.imread("image_b.bmp")
# Always returns (u, v, s2n); s2n is all NaN if sig2noise_method=None.
u, v, s2n = pyprocess.extended_search_area_piv(
frame_a.astype(np.float32),
frame_b.astype(np.float32),
window_size=32,
overlap=12,
dt=0.02,
search_area_size=38,
correlation_method="linear", # circular also supports extended search
normalized_correlation=True,
backend="scipy",
sig2noise_method="peak2peak",
)
x, y = pyprocess.get_coordinates(
image_size=frame_a.shape,
search_area_size=38,
overlap=12,
center_on_field=False, # matches sliding-window positions
)
# flags is a boolean array: True marks a spurious vector.
flags = validation.sig2noise_val(s2n, threshold=1.05) | ~np.isfinite(s2n)
flags |= ~np.isfinite(u) | ~np.isfinite(v)
u, v = filters.replace_outliers(u, v, flags, method="localmean", max_iter=3, kernel_size=2)
# Scale, then convert to right-handed image-boundary coordinates.
x, y, u, v = scaling.uniform(x, y, u, v, scaling_factor=96.52)
y, v = frame_a.shape[0] / 96.52 - y, -v
tools.save("vectors.txt", x, y, u, v, flags)Or use the bundled CLI, which also checks inputs and preserves masks and processing parameters:
python skills/openpiv/scripts/runner.py \
--image frame_a.bmp --image frame_b.bmp --output_dir results --verboseCore Concepts
PIV Fundamentals
Particle Image Velocimetry is an optical method for measuring fluid velocity by tracking illuminated
tracer particles between two images.
Process flow:
1. Capture an image pair (frame_a, frame_b) separated by a known time dt.
2. Divide the images into interrogation windows.
3. Cross-correlate matching windows to find peak displacement.
4. Validate vectors (signal-to-noise, global range, local median).
5. Replace spurious vectors with interpolated values.
6. Scale pixel displacements to physical units.
Interrogation Window Parameters
window_size — correlation window in pixels (typically 16–128). Larger windows give better
correlation but coarser spatial resolution.
overlap — pixels shared between adjacent windows (typically 50–75% of window_size). Higher
overlap raises vector density and cost, but adjacent vectors become correlated rather than
independent.
search_area_size — the window searched in the second frame. Must be ≥ window_size; a few
pixels larger accommodates larger displacements. Both "circular" and "linear" support extended
search. The CLI chooses zero-padded "linear" with normalized_correlation=True for it; this
does not recover arbitrary displacement or eliminate spurious peaks. Grid stride is
search_area_size - overlap, so overlap must be smaller than the search area.
Rules of thumb: keep the largest displacement under about a quarter of window_size, and aim for
5–10 particles per window.
Signal-to-Noise Ratio
s2n measures how distinct the correlation peak is. sig2noise_method controls how it is computed —
"peak2mean" (the function default) or "peak2peak". The two are on different scales, so a
threshold tuned for one is meaningless for the other. Typical peak2peak thresholds are 1.05–1.3.
flags = validation.sig2noise_val(s2n, threshold=1.05)
# flags is bool: True == spurious. `~flags` selects the good vectors.Common Operations
Dynamic Masking
Masking lives in openpiv.preprocess and returns (image, mask). Use floating-point copies
to avoid unsigned subtraction artifacts. Inspect masks on both frames before analysis.
from openpiv import preprocess
# Intensity masking uses Otsu; the threshold argument is for edges.
frame_a_masked, mask_a = preprocess.dynamic_masking(
frame_a.astype(np.float64), method="intensity", filter_size=7, threshold=0.005
)
frame_b_masked, mask_b = preprocess.dynamic_masking(
frame_b.astype(np.float64), method="intensity", filter_size=7, threshold=0.005
)Preserve the union mask_a | mask_b as excluded physical regions. The CLI samples it at
interrogation centers, saves it, and keeps those velocities NaN after replacement. Windows
straddling an object can still be biased: inspect/dilate masks for the experiment. In 0.26.1
method="edges" indexes with uint8 instead of bool, potentially corrupting the image or failing.
The CLI refuses it; use intensity masking or a verified boolean mask in a custom workflow.
Multi-Pass Processing
Multi-pass (window deformation) lives in openpiv.windef, driven by a PIVSettings dataclass.
pyprocess has no multi-pass entry point.
import numpy as np
from openpiv import scaling, windef
settings = windef.PIVSettings(
windowsizes=(64, 32, 16), overlap=(32, 16, 8), num_iterations=3,
backend="scipy", sig2noise_method="peak2peak", sig2noise_threshold=1.05,
)
x, y, u, v, flags = windef.simple_multipass(
frame_a.astype(np.float32), frame_b.astype(np.float32), settings
)
# Output is in PIXELS PER FRAME -- convert yourself. scaling.uniform only divides
# by scaling_factor, so apply dt separately.
dt = 0.02
x, y, u, v = scaling.uniform(x, y, u, v, scaling_factor=96.52)
u, v = u / dt, v / dtsimple_multipass validates, replaces outliers, fills remaining NaNs with zeros, and transforms
coordinates. Keep its flags: repaired/zero-filled output is not an independent measurement.
Always pass settings: its no-settings path has two window sizes but three iterations in 0.26.1.
Units trap: simple_multipass and its alias multigrid_windef ignore settings.dt and
settings.scaling_factor; convert their arrays as above. Batch windef.piv(settings) applies
both before saving — do not scale its files again. The simple wrapper does not honor all batch
preprocessing/output switches.
For control over individual passes, windef.first_pass and windef.multipass_img_deform are the
lower-level building blocks.
Validation and Post-Processing
Validation Methods
Every validator returns a boolean array where True marks a spurious vector. Also reject
nonfinite u, v, and s2n: sig2noise_val alone does not flag NaN.
# Signal-to-noise
flags = validation.sig2noise_val(s2n, threshold=1.05)
# Global range -- takes (min, max) TUPLES, positionally or as u_thresholds/v_thresholds.
flags = validation.global_val(u, v, (-300, 300), (-300, 300))
# Local median -- u_threshold and v_threshold are REQUIRED; size is the neighbourhood half-width.
flags = validation.local_median_val(u, v, u_threshold=30.0, v_threshold=30.0, size=1)
# Combine with boolean OR (not np.maximum -- these are bool arrays).
flags = (
validation.sig2noise_val(s2n, threshold=1.05)
| validation.global_val(u, v, (-300, 300), (-300, 300))
| validation.local_median_val(u, v, u_threshold=30.0, v_threshold=30.0)
)Set these thresholds in the units of u and v, not in pixels per frame.
extended_search_area_piv divides by dt, so with dt=0.02 a 3 px/frame displacement arrives as
150 px/s. The thresholds above suit that case; the (-30, 30) figure that PIV literature and
PIVSettings.min_max_u_disp use is a px/frame limit, and applying it to px/s output rejects the
entire field. Correlate with dt=1 to validate displacements before conversion, or adjust
thresholds to the actual velocity units (including both time and calibration factors).
Outlier Replacement
u, v = filters.replace_outliers(
u, v, flags, method="localmean", max_iter=3, tol=1e-3, kernel_size=2
)method accepts "localmean", "disk", or "distance"; an invalid name raises ValueError
when filling missing cells. Use kernel_size>=2 for "distance": size 1 truncates all neighbor
weights to zero in 0.26.1 and leaves h
… (nội dung đầy đủ có trong gói tải về)
Skill liên quan
- design-system – Ghi nhận bản sắc thương hiệu của người dùng chỉ một lần qua trình hướng dẫn 10 câu hỏi…
- optimize-for-gpu – Tăng tốc Python khoa học trên phần cứng NVIDIA bằng GPU và kiểm tra kết quả đúng và…
- postgresql-table-design – Dùng kỹ năng này khi thiết kế hoặc rà soát schema dành riêng cho PostgreSQL. Bao gồm…
- baseline-ui – Nhanh chóng làm sạch code UI bằng cách sửa khoảng cách, phân cấp, typography và các lỗi…
- epic-design – Xây dựng website 2.5D tương tác, điện ảnh, sử dụng kể chuyện theo cuộn trang, parallax…
- beatra-ai-video-studio – Cài đặt và sử dụng gói Beatra AI Video Studio chính thức, ghim theo digest, cho các tác…
- bento-ui – Hướng dẫn triển khai Bento UI cho Web và App. Kích hoạt khi người dùng muốn thẻ lưới…
- brand-guidelines – Viết nội dung theo hướng dẫn thương hiệu Sentry. Dùng khi viết văn bản giao diện, thông…