From e990cbdba7b2e14e9a9f1b9fe28da5b9ebff936a Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Tue, 10 Feb 2026 23:53:19 +0800 Subject: [PATCH 1/8] Figure.colorbar: Pythonic way to set labels and annotations --- pygmt/src/colorbar.py | 101 +++++++++++++++++++++++++++++++++++++----- 1 file changed, 89 insertions(+), 12 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index a52c8d9336f..588a45f43c4 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -11,12 +11,58 @@ from pygmt.exceptions import GMTValueError from pygmt.helpers import build_arg_list, fmt_docstring, use_alias from pygmt.helpers.utils import is_nonstr_iter -from pygmt.params import Box, Position +from pygmt.params import Axis, Box, Frame, Position from pygmt.src._common import _parse_position __doctest_skip__ = ["colorbar"] +def _build_frame( + annot: float | None = None, + tick: float | None = None, + grid: float | None = None, + annot_angel: float | None = None, + annot_prefix: str | None = None, + annot_unit: str | None = None, + label: str | None = None, + unit: str | None = None, + frame=None, +): + """ + Create the list of Alias objects for the -B option. + + >>> _build_frame(annot=1, tick=0.5, xlabel="Distance", ylabel="Depth") + Frame(xaxis=Axis(annot=1, tick=0.5, label='Distance'), yaxis=Axis(label='Depth')) + """ + if frame is not None and frame is not False: + return frame + + _xaxis_is_set = any( + v is not None + for v in {annot, tick, grid, annot_angel, annot_prefix, annot_unit, label} + ) + _yaxis_is_set = unit is not None + + # Need to return None if no parameters are give. Otherwise, it may return "". + if not (_xaxis_is_set or _yaxis_is_set): + return None + + xaxis, yaxis = None, None + if _xaxis_is_set: + xaxis = Axis( + annot=annot, + tick=tick, + grid=grid, + # angle=annot_angel, + # prefix=annot_prefix, + # unit=annot_unit, + label=label, + ) + if _yaxis_is_set: + yaxis = Axis(label=unit) + return Frame(xaxis=xaxis, yaxis=yaxis) + + def _alias_option_D( # noqa: N802, PLR0913 position=None, length=None, @@ -153,6 +199,15 @@ def colorbar( # noqa: PLR0913 length: float | str | None = None, width: float | str | None = None, orientation: Literal["horizontal", "vertical"] | None = None, + label: str | None = None, + unit: str | None = None, + annot: float | None = None, + tick: float | None = None, + grid: float | None = None, + annot_angel: float | None = None, + annot_prefix: str | None = None, + annot_unit: str | None = None, + frame: str | Sequence[str] | bool = False, reverse: bool = False, nan: bool = False, nan_position: Literal["start", "end"] | None = None, @@ -168,7 +223,6 @@ def colorbar( # noqa: PLR0913 scale: float | None = None, projection: str | None = None, region: Sequence[float | str] | str | None = None, - frame: str | Sequence[str] | bool = False, verbose: Literal["quiet", "error", "warning", "timing", "info", "compat", "debug"] | bool = False, panel: int | Sequence[int] | bool = False, @@ -201,7 +255,6 @@ def colorbar( # noqa: PLR0913 Full GMT docs at :gmt-docs:`colorbar.html`. $aliases - - B = frame - F = box - G = truncate - I = shading @@ -217,6 +270,7 @@ def colorbar( # noqa: PLR0913 .. hlist:: :columns: 1 + - B = label, unit, annot, tick, grid, annot_angel, annot_prefix, annot_unit - D = position, **+w**: length/width, **+h**/**+v**: orientation, **+r**: reverse, **+n**: nan/nan_position, **+e**: fg_triangle/bg_triangle/triangle_height, @@ -244,6 +298,26 @@ def colorbar( # noqa: PLR0913 given with unit ``%`` then it is in percentage of the bar length. [Length defaults to 80% of the corresponding plot side dimension, and width defaults to 4% of the bar length]. + label + unit + Set the label and unit for the colorbar. The label is placed along the colorbar + and the unit is placed at the end of the colorbar. + annot + grid + tick + Intervals for annotations, grid lines, and ticks. Refer to + :class:`pygmt.params.Axis` for more details on how these parameters work. + Parameters ``annot_prefix``, ``annot_unit``, and ``annot_angel`` can be used to + further customize the annotations. + frame + Set colorbar boundary frame, labels, and axes attributes. + + .. deprecated:: v0.19.0 + + Use ``annot``, ``tick``, ``grid``, ``annot_angel``, ``annot_prefix``, + ``annot_unit``, ``label``, and ``unit`` parameters to customize the colorbar + annotations and labels. + orientation Set the colorbar orientation to either ``"horizontal"`` or ``"vertical"``. [Default is vertical, unless ``position`` is set to bottom-center or top-center @@ -321,8 +395,6 @@ def colorbar( # noqa: PLR0913 requested colorbar length. $projection $region - frame - Set colorbar boundary frame, labels, and axes attributes. $verbose $panel $perspective @@ -336,12 +408,7 @@ def colorbar( # noqa: PLR0913 >>> # Create a basemap >>> fig.basemap(region=[0, 10, 0, 3], projection="X10c/3c", frame=True) >>> # Call the colorbar method for the plot - >>> fig.colorbar( - ... # Set cmap to the "roma" CPT - ... cmap="SCM/roma", - ... # Label the x-axis "Velocity" and the y-axis "m/s" - ... frame=["x+lVelocity", "y+lm/s"], - ... ) + >>> fig.colorbar(cmap="SCM/roma", label="Velocity", unit="m/s") >>> # Show the plot >>> fig.show() """ @@ -386,7 +453,17 @@ def colorbar( # noqa: PLR0913 Q=Alias(log, name="log"), W=Alias(scale, name="scale"), ).add_common( - B=frame, + B=_build_frame( + annot=annot, + tick=tick, + grid=grid, + annot_angel=annot_angel, + annot_prefix=annot_prefix, + annot_unit=annot_unit, + label=label, + unit=unit, + frame=frame, + ), J=projection, R=region, V=verbose, From 3c75b9398554361de677442f6e537746b6dac6ba Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Wed, 11 Feb 2026 22:31:49 +0800 Subject: [PATCH 2/8] Fix doctest --- pygmt/src/colorbar.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index 588a45f43c4..ecb02e2cf3c 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -31,8 +31,8 @@ def _build_frame( """ Create the list of Alias objects for the -B option. - >>> _build_frame(annot=1, tick=0.5, xlabel="Distance", ylabel="Depth") - Frame(xaxis=Axis(annot=1, tick=0.5, label='Distance'), yaxis=Axis(label='Depth')) + >>> list(_build_frame(annot=1, tick=0.5, label="Distance", unit="Depth")) + ['xa1f0.5+lDistance', 'y+lDepth'] """ if frame is not None and frame is not False: return frame From c9461983782c922ca6866a9f97376f01c3ba5e54 Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 16:54:17 +0800 Subject: [PATCH 3/8] Fix typing issue --- pygmt/src/colorbar.py | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index ecb02e2cf3c..037bdefdca4 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -18,9 +18,9 @@ def _build_frame( - annot: float | None = None, - tick: float | None = None, - grid: float | None = None, + annot: float | bool = False, + tick: float | bool = False, + grid: float | bool = False, annot_angel: float | None = None, annot_prefix: str | None = None, annot_unit: str | None = None, @@ -201,9 +201,9 @@ def colorbar( # noqa: PLR0913 orientation: Literal["horizontal", "vertical"] | None = None, label: str | None = None, unit: str | None = None, - annot: float | None = None, - tick: float | None = None, - grid: float | None = None, + annot: float | bool = False, + tick: float | bool = False, + grid: float | bool = False, annot_angel: float | None = None, annot_prefix: str | None = None, annot_unit: str | None = None, From de43548c37b3633d637bcd1294bd30ac117fbaa1 Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 16:59:14 +0800 Subject: [PATCH 4/8] Support angle/prefix/unit --- pygmt/src/colorbar.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index 037bdefdca4..a9dfe08bd6a 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -34,6 +34,7 @@ def _build_frame( >>> list(_build_frame(annot=1, tick=0.5, label="Distance", unit="Depth")) ['xa1f0.5+lDistance', 'y+lDepth'] """ + # Using the old 'frame' parameter. if frame is not None and frame is not False: return frame @@ -53,9 +54,9 @@ def _build_frame( annot=annot, tick=tick, grid=grid, - # angle=annot_angel, - # prefix=annot_prefix, - # unit=annot_unit, + angle=annot_angel, + prefix=annot_prefix, + unit=annot_unit, label=label, ) if _yaxis_is_set: From 072fde2385b166d677d547e6d59148426c6afda9 Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 17:19:03 +0800 Subject: [PATCH 5/8] Fix a typo --- pygmt/src/colorbar.py | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index a9dfe08bd6a..2fdeb081482 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -21,7 +21,7 @@ def _build_frame( annot: float | bool = False, tick: float | bool = False, grid: float | bool = False, - annot_angel: float | None = None, + annot_angle: float | None = None, annot_prefix: str | None = None, annot_unit: str | None = None, label: str | None = None, @@ -40,7 +40,7 @@ def _build_frame( _xaxis_is_set = any( v is not None - for v in {annot, tick, grid, annot_angel, annot_prefix, annot_unit, label} + for v in {annot, tick, grid, annot_angle, annot_prefix, annot_unit, label} ) _yaxis_is_set = unit is not None @@ -54,7 +54,7 @@ def _build_frame( annot=annot, tick=tick, grid=grid, - angle=annot_angel, + angle=annot_angle, prefix=annot_prefix, unit=annot_unit, label=label, @@ -205,7 +205,7 @@ def colorbar( # noqa: PLR0913 annot: float | bool = False, tick: float | bool = False, grid: float | bool = False, - annot_angel: float | None = None, + annot_angle: float | None = None, annot_prefix: str | None = None, annot_unit: str | None = None, frame: str | Sequence[str] | bool = False, @@ -271,7 +271,7 @@ def colorbar( # noqa: PLR0913 .. hlist:: :columns: 1 - - B = label, unit, annot, tick, grid, annot_angel, annot_prefix, annot_unit + - B = label, unit, annot, tick, grid, annot_angle, annot_prefix, annot_unit - D = position, **+w**: length/width, **+h**/**+v**: orientation, **+r**: reverse, **+n**: nan/nan_position, **+e**: fg_triangle/bg_triangle/triangle_height, @@ -308,14 +308,14 @@ def colorbar( # noqa: PLR0913 tick Intervals for annotations, grid lines, and ticks. Refer to :class:`pygmt.params.Axis` for more details on how these parameters work. - Parameters ``annot_prefix``, ``annot_unit``, and ``annot_angel`` can be used to + Parameters ``annot_prefix``, ``annot_unit``, and ``annot_angle`` can be used to further customize the annotations. frame Set colorbar boundary frame, labels, and axes attributes. .. deprecated:: v0.19.0 - Use ``annot``, ``tick``, ``grid``, ``annot_angel``, ``annot_prefix``, + Use ``annot``, ``tick``, ``grid``, ``annot_angle``, ``annot_prefix``, ``annot_unit``, ``label``, and ``unit`` parameters to customize the colorbar annotations and labels. @@ -458,7 +458,7 @@ def colorbar( # noqa: PLR0913 annot=annot, tick=tick, grid=grid, - annot_angel=annot_angel, + annot_angle=annot_angle, annot_prefix=annot_prefix, annot_unit=annot_unit, label=label, From 7aa50bd83e0970e81696367093f793343760310d Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 17:19:16 +0800 Subject: [PATCH 6/8] Add more doctests --- pygmt/src/colorbar.py | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index 2fdeb081482..72915174718 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -31,8 +31,25 @@ def _build_frame( """ Create the list of Alias objects for the -B option. - >>> list(_build_frame(annot=1, tick=0.5, label="Distance", unit="Depth")) - ['xa1f0.5+lDistance', 'y+lDepth'] + >>> list(_build_frame(annot=1, tick=0.5, label="Distance", unit="km")) + ['xa1f0.5+lDistance', 'y+lkm'] + + >>> list( + ... _build_frame( + ... annot=1, + ... tick=0.5, + ... grid=0.2, + ... annot_angel=30, + ... annot_prefix="m", + ... annot_unit="s", + ... label="Distance", + ... unit="km", + ... ) + ... ) + ['xa1f0.5g0.2a30+m+s+lDistance', 'y+lkm'] + >>> list(_build_frame(frame=["xaf0.5+lDistance", "y+lkm"]))) + ['xaf0.5+lDistance', 'y+lkm'] + """ # Using the old 'frame' parameter. if frame is not None and frame is not False: From 13f13bfaa1a0352181346a5e0f5e4ac1cbe9da44 Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 18:33:01 +0800 Subject: [PATCH 7/8] Fix a typo in doctest --- pygmt/src/colorbar.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index 72915174718..de9f63e3c02 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -39,7 +39,7 @@ def _build_frame( ... annot=1, ... tick=0.5, ... grid=0.2, - ... annot_angel=30, + ... annot_angle=30, ... annot_prefix="m", ... annot_unit="s", ... label="Distance", From b0037260f590c1804b16417c7a0e7f58e57f8de0 Mon Sep 17 00:00:00 2001 From: Dongdong Tian Date: Thu, 12 Feb 2026 22:08:59 +0800 Subject: [PATCH 8/8] Fix doctest --- pygmt/src/colorbar.py | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/pygmt/src/colorbar.py b/pygmt/src/colorbar.py index de9f63e3c02..89d24f1094d 100644 --- a/pygmt/src/colorbar.py +++ b/pygmt/src/colorbar.py @@ -40,14 +40,12 @@ def _build_frame( ... tick=0.5, ... grid=0.2, ... annot_angle=30, - ... annot_prefix="m", - ... annot_unit="s", ... label="Distance", ... unit="km", ... ) ... ) - ['xa1f0.5g0.2a30+m+s+lDistance', 'y+lkm'] - >>> list(_build_frame(frame=["xaf0.5+lDistance", "y+lkm"]))) + ['xa1f0.5g0.2+lDistance+a30', 'y+lkm'] + >>> list(_build_frame(frame=["xaf0.5+lDistance", "y+lkm"])) ['xaf0.5+lDistance', 'y+lkm'] """