Metadata-Version: 2.4
Name: oafuncs
Version: 0.0.99.54
Summary: Oceanic and Atmospheric Functions
Home-page: https://github.com/OAKun/OAFuncs
Author: Kun Liu
Author-email: liukun0312@stu.ouc.edu.cn
License: MIT
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Programming Language :: Python :: Implementation :: CPython
Classifier: Programming Language :: Python :: Implementation :: PyPy
Requires-Python: >=3.10.0
Description-Content-Type: text/markdown
License-File: LICENSE.txt
Requires-Dist: rich
Provides-Extra: data
Requires-Dist: numpy; extra == "data"
Requires-Dist: scipy; extra == "data"
Requires-Dist: pandas; extra == "data"
Requires-Dist: xarray; extra == "data"
Provides-Extra: interp
Requires-Dist: numpy; extra == "interp"
Requires-Dist: xarray; extra == "interp"
Requires-Dist: xesmf; extra == "interp"
Requires-Dist: stratify; python_version >= "3.11" and extra == "interp"
Requires-Dist: pyinterp; python_version >= "3.11" and extra == "interp"
Provides-Extra: nc
Requires-Dist: numpy; extra == "nc"
Requires-Dist: xarray; extra == "nc"
Requires-Dist: dask; extra == "nc"
Requires-Dist: netCDF4; extra == "nc"
Provides-Extra: draw
Requires-Dist: cftime; extra == "draw"
Requires-Dist: imageio; extra == "draw"
Requires-Dist: numpy; extra == "draw"
Requires-Dist: matplotlib; extra == "draw"
Requires-Dist: cartopy; extra == "draw"
Requires-Dist: opencv-python; extra == "draw"
Requires-Dist: pillow; extra == "draw"
Provides-Extra: geo
Requires-Dist: global-land-mask; extra == "geo"
Requires-Dist: numpy; extra == "geo"
Requires-Dist: xarray; extra == "geo"
Requires-Dist: geopandas; extra == "geo"
Requires-Dist: rasterio; extra == "geo"
Requires-Dist: salem; extra == "geo"
Provides-Extra: down
Requires-Dist: numpy; extra == "down"
Requires-Dist: beautifulsoup4; extra == "down"
Requires-Dist: httpx; extra == "down"
Requires-Dist: lxml; extra == "down"
Requires-Dist: openpyxl; extra == "down"
Requires-Dist: pandas; extra == "down"
Requires-Dist: requests; extra == "down"
Requires-Dist: xarray; extra == "down"
Requires-Dist: netCDF4; extra == "down"
Requires-Dist: matplotlib; extra == "down"
Requires-Dist: xlrd; extra == "down"
Provides-Extra: sign
Requires-Dist: beautifulsoup4; extra == "sign"
Requires-Dist: lxml; extra == "sign"
Requires-Dist: requests; extra == "sign"
Provides-Extra: office
Requires-Dist: openpyxl; extra == "office"
Requires-Dist: xlrd; extra == "office"
Requires-Dist: python-docx; extra == "office"
Requires-Dist: python-pptx; extra == "office"
Provides-Extra: parallel
Requires-Dist: psutil; extra == "parallel"
Requires-Dist: dask; extra == "parallel"
Provides-Extra: all
Requires-Dist: beautifulsoup4; extra == "all"
Requires-Dist: cartopy; extra == "all"
Requires-Dist: cftime; extra == "all"
Requires-Dist: dask; extra == "all"
Requires-Dist: geopandas; extra == "all"
Requires-Dist: global-land-mask; extra == "all"
Requires-Dist: httpx; extra == "all"
Requires-Dist: imageio; extra == "all"
Requires-Dist: lxml; extra == "all"
Requires-Dist: matplotlib; extra == "all"
Requires-Dist: netCDF4; extra == "all"
Requires-Dist: numpy; extra == "all"
Requires-Dist: opencv-python; extra == "all"
Requires-Dist: openpyxl; extra == "all"
Requires-Dist: pandas; extra == "all"
Requires-Dist: pillow; extra == "all"
Requires-Dist: psutil; extra == "all"
Requires-Dist: pyinterp; python_version >= "3.11" and extra == "all"
Requires-Dist: python-docx; extra == "all"
Requires-Dist: python-pptx; extra == "all"
Requires-Dist: rasterio; extra == "all"
Requires-Dist: requests; extra == "all"
Requires-Dist: salem; extra == "all"
Requires-Dist: scipy; extra == "all"
Requires-Dist: stratify; python_version >= "3.11" and extra == "all"
Requires-Dist: xarray; extra == "all"
Requires-Dist: xesmf; extra == "all"
Requires-Dist: xlrd; extra == "all"
Provides-Extra: full
Requires-Dist: beautifulsoup4; extra == "full"
Requires-Dist: cartopy; extra == "full"
Requires-Dist: cftime; extra == "full"
Requires-Dist: dask; extra == "full"
Requires-Dist: geopandas; extra == "full"
Requires-Dist: global-land-mask; extra == "full"
Requires-Dist: httpx; extra == "full"
Requires-Dist: imageio; extra == "full"
Requires-Dist: lxml; extra == "full"
Requires-Dist: matplotlib; extra == "full"
Requires-Dist: netCDF4; extra == "full"
Requires-Dist: numpy; extra == "full"
Requires-Dist: opencv-python; extra == "full"
Requires-Dist: openpyxl; extra == "full"
Requires-Dist: pandas; extra == "full"
Requires-Dist: pillow; extra == "full"
Requires-Dist: psutil; extra == "full"
Requires-Dist: pyinterp; python_version >= "3.11" and extra == "full"
Requires-Dist: python-docx; extra == "full"
Requires-Dist: python-pptx; extra == "full"
Requires-Dist: rasterio; extra == "full"
Requires-Dist: requests; extra == "full"
Requires-Dist: salem; extra == "full"
Requires-Dist: scipy; extra == "full"
Requires-Dist: stratify; python_version >= "3.11" and extra == "full"
Requires-Dist: xarray; extra == "full"
Requires-Dist: xesmf; extra == "full"
Requires-Dist: xlrd; extra == "full"
Provides-Extra: science
Requires-Dist: cartopy; extra == "science"
Requires-Dist: cftime; extra == "science"
Requires-Dist: dask; extra == "science"
Requires-Dist: geopandas; extra == "science"
Requires-Dist: global-land-mask; extra == "science"
Requires-Dist: imageio; extra == "science"
Requires-Dist: matplotlib; extra == "science"
Requires-Dist: netCDF4; extra == "science"
Requires-Dist: numpy; extra == "science"
Requires-Dist: opencv-python; extra == "science"
Requires-Dist: pandas; extra == "science"
Requires-Dist: pillow; extra == "science"
Requires-Dist: pyinterp; python_version >= "3.11" and extra == "science"
Requires-Dist: rasterio; extra == "science"
Requires-Dist: salem; extra == "science"
Requires-Dist: scipy; extra == "science"
Requires-Dist: stratify; python_version >= "3.11" and extra == "science"
Requires-Dist: xarray; extra == "science"
Requires-Dist: xesmf; extra == "science"
Dynamic: author
Dynamic: author-email
Dynamic: classifier
Dynamic: description
Dynamic: description-content-type
Dynamic: home-page
Dynamic: license
Dynamic: license-file
Dynamic: provides-extra
Dynamic: requires-dist
Dynamic: requires-python
Dynamic: summary


# OAFuncs

Oceanic and Atmospheric Functions for Python.

OAFuncs provides utilities for NetCDF files, geoscience arrays, plotting, geographic masks, downloads, file operations, model data, and small workflow tools.

## Installation

```bash
pip install oafuncs
```

Optional dependency groups:

```text
data, interp, nc, draw, geo, down, office, parallel, sign, science, all, full
```

## Package Structure

```text
oafuncs
|-- oa_nc.py          NetCDF utilities
|-- oa_data.py        data interpolation helpers
|-- oa_geo.py         geographic and land/ocean mask helpers
|-- oa_draw.py        plotting helpers
|-- oa_cmap.py        colormap helpers
|-- oa_file.py        file operation helpers
|-- oa_date.py        date and timing helpers
|-- oa_down/          download helpers
|-- oa_model/         ROMS and WRF helpers
|-- oa_linux.py       Linux, HPC, and Slurm helpers
|-- oa_office.py      Office document helpers
|-- oa_sign/          website sign-in helpers
`-- oa_tool.py        command, progress bar, email, and parallel helpers
```

## Public API

### `oa_nc`

| Function | Purpose |
| --- | --- |
| `save` | Write arrays, DataArrays, or Datasets to NetCDF. |
| `merge` | Merge multiple NetCDF files. |
| `modify` | Modify a variable value or variable attribute. |
| `rename` | Rename a NetCDF variable or dimension. |
| `check` | Check whether a NetCDF file is readable. |
| `convert_longitude` | Convert longitude coordinates between `[-180, 180]` and `[0, 360]`. |
| `isel` | Select NetCDF data by dimension indices. |
| `draw` | Plot variables from a NetCDF file or xarray object. |
| `compress` | Apply NetCDF compression. |
| `unscale` | Decode and remove `scale_factor` / `add_offset` storage encoding. |

### `oa_data`

| Function | Purpose |
| --- | --- |
| `ensure_list` | Convert a value to a list. |
| `interp_vertical` | Interpolate along the fixed `z` axis in `[t, z, y, x]` order. |
| `interp_horizontal` | Interpolate horizontal fields over the fixed `y, x` axes. |

### `oa_geo`

| Function | Purpose |
| --- | --- |
| `earth_distance` | Calculate great-circle distance between two lon/lat points. |
| `mask_shapefile` | Mask a 2D field using a shapefile. |
| `mask_land_ocean` | Keep land or ocean values using a land/ocean mask. |
| `is_land` | Check whether a lon/lat point is on land. |
| `is_ocean` | Check whether a lon/lat point is in the ocean. |

### `oa_draw`

| Function | Purpose |
| --- | --- |
| `fig_minus` | Format minus signs in axis or colorbar tick labels. |
| `gif` | Create a GIF from image files. |
| `movie` | Create a video from image files. |
| `setup_map` | Configure a Cartopy map. |
| `ticks_symmetric` | Generate ticks symmetric around a center value. |
| `font_CN` | Configure Chinese font support for Matplotlib. |

### `oa_cmap`

| Function | Purpose |
| --- | --- |
| `show` | Preview a colormap. |
| `to_color` | Convert a colormap to a list of colors. |
| `create` | Create a custom colormap from colors or an RGB text file. |
| `get` | Load a Matplotlib or custom colormap. |
| `random_color` | Generate a random hex color. |

### `oa_file`

| Function | Purpose |
| --- | --- |
| `script_dir` | Return the caller script directory, independent of current working directory. |
| `find` | Find files by pattern. |
| `link` | Create symbolic links with wildcard support. |
| `copy` | Copy files or directories with wildcard support. |
| `move` | Move files or directories with wildcard support. |
| `rename` | Rename files by replacing text in filenames. |
| `remove_empty` | Remove empty folders recursively. |
| `remove` | Delete files or directories by pattern. |
| `size` | Return file size in the requested unit. |
| `replace` | Replace text content by `replace_dict` and save it to `output_path`. |

Example:

```python
from oafuncs.oa_file import replace

replace(
    input_path="config.txt",
    replace_dict={"old_value": "new_value"},
    output_path=r"D:\run\config.txt",
)
```

`output_path` accepts either a file name, such as `"result.txt"`, or an absolute
file path. A file name is saved in the input file's directory. Directory-only paths
and relative paths containing directories are rejected to avoid ambiguous output.

### `oa_date`

| Function / Class | Purpose |
| --- | --- |
| `month_days` | Return the number of days in a month. |
| `hour_range` | Generate datetime strings at an hourly interval. |
| `adjust_time` | Offset a base time by a time delta. |
| `timeit` | Decorator class for timing function execution. |

### `oa_down`

| Function | Purpose |
| --- | --- |
| `download` | Download HYCOM data for one time or a time range. |
| `draw_time_range` | Draw the available HYCOM time range. |
| `download_by_doi` | Download literature files from DOI lists. |
| `downloader` | Send a download task to Internet Download Manager. |
| `get_ua` | Return the default user-agent string for download requests. |

### `oa_model`

| Function | Purpose |
| --- | --- |
| `interp` | Interpolate and remap ROMS data to target lon/lat/depth grids. |
| `header_record` | Build a WRF little_r header record. |
| `data_record` | Build a WRF little_r data record. |
| `ending_record` | Build a WRF little_r ending record. |
| `tail_record` | Build a WRF little_r tail record. |

### `oa_linux`

| Function | Purpose |
| --- | --- |
| `patch_slurm` | Update selected `#SBATCH` directives in a Slurm script. |
| `submit` | Submit a Slurm job with queue-aware retry logic. |
| `job_state` | Query Slurm job state. |
| `is_linux` | Check whether the current system is Linux. |
| `get_jobid` | Find a Slurm job ID by path or job name. |

### `oa_office`

| Function | Purpose |
| --- | --- |
| `extract_pptx_notes` | Extract PowerPoint notes to a Word document. |

### `oa_sign`

| Function | Purpose |
| --- | --- |
| `sign_in_love_ocean` | Sign in to 52ocean. |
| `sign_in_meteorological_home` | Sign in to Meteorological Home. |
| `sign_in_scientific_research` | Sign in to AbleSci. |

### `oa_tool`

| Function / Class | Purpose |
| --- | --- |
| `run_command` | Run an external command safely without using a shell. |
| `Pex` | Parallel executor wrapper with progress and timing. `PEx` remains as a deprecated compatibility alias until 2026-12-22. |
| `email` | Send an email. |
| `pbar` | Create a colored progress bar. |

## Links

- PyPI: <https://pypi.org/project/oafuncs>
- GitHub: <https://github.com/OAKun/OAFuncs>
- Download stats: <https://pypistats.org/packages/oafuncs>
- Wiki: <https://deepwiki.com/OAKun/OAFuncs>

## License

MIT License. See [LICENSE.txt](LICENSE.txt).
