Releases: azogue/psychrochart
🎨 Minor fixes and lint update
📦️ Remove `scipy` dependency
Changes (from #59)
- ⚡️ Use simple 1D interpolator to project lines, instead of
scipy.interpolate.interp1d
- ✅ Add tests for convex hulls of given points
- ⚡️ Use simple convex hull algorithm, to compute zones to group annotated points, instead of using
scipy.spatial.ConvexHull
- 📦️ Bump version, removing
scipy
dependency
📦 Migrate to pydantic v2
Move to recent versions of pydantic
, and also upgrade internal linters, moving to ruff-format
Changes
- 📦️ env: Bump version and upgrade deps, requiring
pydantic
v2 - ♻️ Migrate pydantic v2 syntax for validators, parsers, serializers, model load/dump methods, etc.
- 🎨 lint: pre-commit update, moving to
ruff-format
- 🎨 lint: Apply format changes and lint fixes
- 📝 Update CHANGELOG
- 👷 ci: Split actions for tests on PRs and publish package on main
✨ Add customisable annotations
From @tadashiorigami in #44, thanks!
Changes
- ✨ Add styling for annotations (labeled curves in the chart), customizing their font-size, color, and bbox style.
- 🔧 Support negative
constant_h_labels_loc
settings, to strech the constant h line to the left inside the saturated area, giving the chart an aspect closer to the popular ASHRAE chart. - ✅ Add unit test with example from @tadashiorigami, with styled annotations with bbox and hack for negative constant_h_labels_loc
- 📦️ Bump version and update matplotlib to 3.8.0
🐛 Fix install with new pydantic v2
Changes
- 🎨 lint: pre-commit autoupdate
- 📦️ env: Bump patch version and fix deps with pydantic version < v2, and enabling new Python 3.12
- 📝 Update CHANGELOG
✨ Add zone kind 'dbt-wmax' with vapour content limit + bugfixes
Changes
- ✨ Add new kind of overlay zone 'dbt-wmax', to define chart areas delimited between db-temps and absolute humidity values, solving #28
- 🐛 Enable zones defined by 2 points (assume a rectangle defined by left-bottom/right-top coords)
- 🐛 Fix logic for plot regeneration, to plot again if config changes AFTER plotting the chart
- 🐛 Fix ZoneStyle definition when linewidth is 0 and linestyle remains the default (passing inconsistent params to matplotlib)
✨ More kinds of chart zones + CSS for SVG styling
Define new kinds of enclosed areas in chart, between constant RH lines and constant volume or enthalpy values (zone_kind: "volume-rh"/"enthalpy-rh"
),
and enable full potencial for SVG customization by including CSS and/or <defs>
inside it.
Changes
- ✨ Add new kind of overlay zones 'enthalpy-rh' and 'volume-rh', to define chart areas delimited between 2 constant enthalpy or volume lines, and 2 constant humidity lines
- 🎨 Add
chart.remove_zones()
method, like the existent.remove_legend()
and.remove_annotations()
, to clear matplotlib current Axes from each kind of annotated objects - 🐛 Fix artists registry not mirroring objects in plot, by setting a new one each time
chart.plot()
is invoked - ♻️ Set gid for 'chart_legend_background' item if frameon is enabled
- ✨ Pass optional CSS and SVG to
chart.make_svg()
, to include extra-styling inside the produced SVG 🌈 - ✨ Add method
chart.plot_over_saturated_zone()
to create a filled patch in the over-saturated zone of the psychrochart, to colorize that area - 🦄 tests: Add dynamic effects and CSS rules to splash chart for a show of SVG styling capabilities
✨ Lazy generation of chart data, 'Artist' registry, and better SVG export
Now all chart-data parameters, including the overlayed zones, are included in the ChartConfig
,
and curve-generation only happens when chart is plotted (or saved to disk, or if chart.process_chart()
is invoked 😜).
Any change in the chart configuration will trigger a data-regen for all items before plotting.
When plotting over some matplotlib Axes
, all objects created now have meaningful (and deterministic) ids,
and are tracked and accessible under chart.artists
, for easier customization of single matplotlib objects,
also adding a recognizable hierarchy in generated SVGs, (enabling potential for CSS over SVG charts 🌈)
Changes
- ✨ Name each matplotlib
Artist
obj in plot with custom readable IDs, for easier recognition and readable object hierarchy in SVGs, and maintain a registry of all objects in plot to access them by kind underchart.artists
property, allowing fine-grain control to customize all details in the psychrochart - ♻️ Refactor chart 'zones' and store zone definitions in ChartConfig, to regenerate plot patches (closed
PsychroCurve
, withZoneStyle
) on-demand, same as the other chart curves, generating new 'xy' points when config is changed. IfChartParams.with_zones
is enabled, but there are no zones in config when chart is created, the default winter/summer 'dbt-rh' zones are added. - ⚡️ Add lazy generation of psychro curves to avoid updating the chart data until it's needed to plot, and add a
chart.process_chart()
method to trigger data regeneration if the chart config has changed or there is no chart data yet - 💥 Make
chart.saturation
a singlePsychroCurve
, instead of a collection of curves - ✅ tests: Add unit tests for new ChartRegistry and adapt to behaviour changes and readable hierarchy in SVG output
- 📝 Update example notebook showing
chart.artists
usage - 🚀 env: Update deps, bump version, and update CHANGELOG
✨ Chart config auto-refresh + bugfixes 🐛
Before, chart customization was done by creating a new Psychrochart
object based on some modified chart configuration,
so creating custom plots, or even changing chart limits, was challenging 😓
Now, when chart.config
changes, any call to chart.save()
, chart.make_svg()
, or chart.plot()
will regenerate the chart data (limits, enabled curves, styling, etc.) before plotting, with only the visible curves inside limits,
(no more 0-size artifacts in SVGs, and most errors because some var is out of range should be gone now 🤞)
Changes
- ♻️ Update example notebook with API changes, and using
chart.make_svg()
as the recommended method to generate SVGs - 💄 Parse colors into RGBA values, so "red", "#FF0000", "#FF0000FF" produce the same float repr [1., 0., 0., 1.]
- 🏗️ Add mutation control for configuration models, and use it to check if there is any config change before creating a chart, triggering a chart-data regeneration if necessary
- 🔧 Add new field
ChartFigure.dpi
to chart config, for easy customization of matplotlib Figure DPI - ⚡️ Optimize generation of psychrometric curves inside plot limits
- 🐛 Fix convergence and var-out-of-range errors
- 💥 Remove plotting methods from
PsychroCurve
/PsychroCurves
for a more functional approach, using methods inplot_logic.py
- 💥 Add
PsychroCurve.internal_value
field, to identify the trigger value for each curve (constant H/V/RH...), and evolve validation of data arrays - ✅ tests: Increase test coverage and optimize tests for faster run (~2x)
- 📦️ env: Add slugify to deps and bump version
♻️ Full re-work on internals to use pydantic models
🧹 Internal evolution to update the code style to the latest versions and de facto standards, with better typing, input validation, and serialization.
Hardly any new features (.make_svg()
), but some bug fixes.
BREAKING-CHANGE: Now the chart creation from a configuration key/file/dict is done with
PsychroChart.create(config)
, instead of oldPsychroChart(config)
Changes
-
🏗️ Add
pydantic
models for chart + annotations styling and config, for better (de)serialization and parameter validation.New models are:
CurveStyle
,LabelStyle
,TickStyle
,ZoneStyle
:= to parse & handle defaults for matplotlib styling parametersChartConfig
for the full chart configuration, including sub-modelsChartFigure
,ChartLimits
, andChartParams
, to mirror the old obfuscated config, with the same default values as beforeChartPoint
andChartSeries
for styled single-point or array-data annotationsChartLine
for styled connectors between named points (now without outline 'marker' by default)ChartArea
for styled convex areas delimited by a list of named pointsChartAnnots
as container for all of the aboveChartZone
(andChartZones
as a list), for styled fixed areas (like the default winter/summer comfort zones)
-
♻️ Evolve load methods to parse inputs into pydantic models with near-zero (expected 🤞) breaks when reading old data
-
💥 Rework
PsychroChart
class to work with pydanticPsychroChartModel
. As the chart is now a pydantic model, there is achart.json(...)
method, and loading from serialized data is available withPsychroChart.parse_file(
/.validate(
/ etc 🤩 -
✨ Add
.make_svg()
method to produce a SVG file as text, and evolve.save(...)
with optionalcanvas_cls: Type[FigureCanvasBase]
, to select kind of matplotlib canvas where to print the chart -
✨ Support file creation in subfolders with chart.save(dest)
-
🚚 rsc: Deterministic SVG output in tests, and README images without date metadata
-
✅ tests: Adapt API changes in unit tests, remove usages of
unittest.TestCase
, add new tests for pydantic models, annotations, and serialization methods.