Skip to content

Commit e50fbe8

Browse files
committed
DOC: Add file-based listed gallery order for examples
This adds support for a file "gallery_order.txt" in gallery folders for specifying the display order or examples. Advantages compared to the previous order approach: - Orders are now defined inside each gallery and not in a central list - The placeholder '*' allows to put some examples at the front, some at the end, and all others alphabetically sorted in the position of the placeholder - Checking of entries that do no exist as examples - Checking that all examples are listed (if no placeholder is specified)
1 parent 4946ac3 commit e50fbe8

10 files changed

Lines changed: 131 additions & 40 deletions

File tree

doc/sphinxext/gallery_order.py

Lines changed: 84 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
"""
55

66
import itertools
7+
from pathlib import Path
8+
79
from sphinx_gallery.sorting import ExplicitOrder
810

911
# Gallery sections shall be displayed in the following order.
@@ -23,7 +25,7 @@
2325
'../galleries/examples/style_sheets',
2426
'../galleries/examples/pyplots',
2527
'../galleries/examples/axes_grid1',
26-
'../galleries/examples/axisartist',
28+
'../galleries/examples/axisartst',
2729
'../galleries/examples/showcase',
2830
UNSORTED,
2931
'../galleries/examples/userdemo',
@@ -72,62 +74,104 @@ def __call__(self, item):
7274
list_all = [
7375
# **Tutorials**
7476
# introductory
75-
"quick_start", "pyplot", "images", "lifecycle", "customizing",
77+
"quick_start", "customizing",
7678
# intermediate
77-
"artists", "legend_guide", "color_cycle",
79+
"legend_guide", "color_cycle",
7880
"constrainedlayout_guide", "tight_layout_guide",
7981
# advanced
8082
# text
8183
"text_intro", "text_props",
8284
# colors
83-
"colors",
84-
85-
# **Examples**
86-
# animation
87-
"simple_anim", # Most basic example
88-
# color
89-
"color_demo",
90-
# pies
91-
"pie_features", "pie_demo2",
92-
# scales
93-
"scales", # Scales overview
94-
95-
# **Plot Types
96-
# Basic
97-
"plot", "scatter_plot", "bar", "stem", "step", "fill_between",
98-
# Arrays
99-
"imshow", "pcolormesh", "contour", "contourf",
100-
"barbs", "quiver", "streamplot",
101-
# Stats
102-
"hist_plot", "boxplot_plot", "errorbar_plot", "violin",
103-
"eventplot", "hist2d", "hexbin", "pie",
104-
# Unstructured
105-
"tricontour", "tricontourf", "tripcolor", "triplot",
106-
# Spines
107-
"spines", "spine_placement_demo", "spines_dropped",
108-
"multiple_yaxis_with_spines", "centered_spines_with_arrows",
109-
]
85+
"colors", ]
11086
explicit_subsection_order = [item + ".py" for item in list_all]
11187

11288

113-
class MplExplicitSubOrder(ExplicitOrder):
114-
"""For use within the 'within_subsection_order' key."""
89+
class MplFileExplicitOrder(ExplicitOrder):
90+
"""
91+
An explicit order class that reads the order of examples from 'gallery_order.txt'.
92+
93+
For use with the sphinx_gallery 'within_subsection_order' key.
94+
95+
The file contains a list of example filenames (without the .py extension) in the
96+
desired order, with an optional '*' to indicate where unsorted examples should be
97+
placed.
98+
99+
If '*' is not present, all examples must be listed, or an error will be raised.
100+
Use this if you want to ensure that a full order is intentionally maintained.
101+
"""
115102
def __init__(self, src_dir):
116-
self.src_dir = src_dir # src_dir is unused here
117-
self.ordered_list = explicit_subsection_order
103+
ordered_list = self.read_gallery_order(Path(src_dir)) or []
104+
super().__init__(ordered_list)
105+
106+
@staticmethod
107+
def read_gallery_order(src_dir: Path):
108+
"""Return the list of examples to be sorted; read from 'gallery_order.txt'."""
109+
gallery_order_txt = src_dir / "gallery_order.txt"
110+
if not gallery_order_txt.exists():
111+
return None
112+
lines = [
113+
line.strip()
114+
for line in gallery_order_txt.read_text().splitlines()
115+
if line.strip() and not line.startswith("#")
116+
]
117+
118+
try:
119+
placeholder_index = lines.index("*")
120+
except ValueError:
121+
placeholder_index = None
122+
123+
lines = [line + ".py" for line in lines]
124+
125+
if placeholder_index is None:
126+
front = lines
127+
back = []
128+
else:
129+
front = lines[:placeholder_index]
130+
back = lines[placeholder_index+1:]
131+
132+
listed_examples = set(front + back)
133+
existing_examples = set(
134+
str(file.name) for file in src_dir.iterdir() if file.suffix == ".py"
135+
)
136+
137+
non_exiting_examples = listed_examples - existing_examples
138+
missing_examples = existing_examples - listed_examples
139+
print(f"non_exiting_examples: {non_exiting_examples}")
140+
print(f"missing_examples: {missing_examples}")
141+
142+
if non_exiting_examples:
143+
raise ValueError(
144+
f"The following examples listed in {gallery_order_txt} do not exist: "
145+
f"{', '.join(non_exiting_examples)}"
146+
)
147+
if placeholder_index is None and missing_examples:
148+
raise ValueError(
149+
f"The following examples are not listed in {gallery_order_txt}. "
150+
f"Either include them or add a '*' to indicate where not listed"
151+
f"examples should be placed: "
152+
f"{', '.join(missing_examples)}"
153+
)
154+
155+
mid = list(
156+
sorted(
157+
str(file.name) for file in src_dir.iterdir()
158+
if file.suffix == ".py" and str(file.name) not in listed_examples
159+
)
160+
)
161+
return front + mid + back
118162

119163
def __call__(self, item):
120164
"""Return a string determining the sort order."""
121-
if item in self.ordered_list:
122-
return f"{self.ordered_list.index(item):04d}"
123-
else:
124-
# ensure not explicitly listed items come last.
125-
return "zzz" + item
165+
if not self.ordered_list:
166+
return item
167+
return f"{self.ordered_list.index(item):04d}"
126168

169+
def __repr__(self):
170+
return '<%s: %s>' % (self.__class__.__name__, self.ordered_list)
127171

128172
# Provide the above classes for use in conf.py
129173
sectionorder = MplExplicitOrder(explicit_order_folders)
130-
subsectionorder = MplExplicitSubOrder
174+
subsectionorder = MplFileExplicitOrder
131175

132176
_preserve_count = itertools.count()
133177

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
simple_anim
3+
*
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
color_demo
3+
*
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
pie_features
3+
*
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
scales
3+
*
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
spines
3+
spine_placement_demo
4+
spines_dropped
5+
multiple_yaxis_with_spines
6+
centered_spines_with_arrows
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
plot
3+
scatter_plot
4+
bar
5+
stem
6+
fill_between
7+
stackplot
8+
stairs
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
hist_plot
3+
boxplot_plot
4+
errorbar_plot
5+
violin
6+
eventplot
7+
hist2d
8+
hexbin
9+
pie
10+
ecdf
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
tricontour
3+
tricontourf
4+
tripcolor
5+
triplot
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# Explicit example order this gallery. For details see doc/sphinxext/gallery_order.py::MplFileExplicitOder
2+
pyplot
3+
images
4+
lifecycle
5+
artists
6+
coding_shortcuts

0 commit comments

Comments
 (0)