Skip to content

Commit 65836d1

Browse files
feat(bokeh): implement wireframe-3d-basic (#1063)
## Implementation: `wireframe-3d-basic` - bokeh Implements the **bokeh** version of `wireframe-3d-basic`. **File:** `plots/wireframe-3d-basic/implementations/bokeh.py` **Parent Issue:** #1015 --- :robot: *[impl-generate workflow](https://github.com/MarkusNeusinger/pyplots/actions/runs/20274573237)* --------- Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
1 parent 17f5a6a commit 65836d1

2 files changed

Lines changed: 140 additions & 0 deletions

File tree

Lines changed: 117 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
"""
2+
wireframe-3d-basic: Basic 3D Wireframe Plot
3+
Library: bokeh
4+
"""
5+
6+
import numpy as np
7+
from bokeh.io import export_png, save
8+
from bokeh.models import Range1d
9+
from bokeh.plotting import figure
10+
from bokeh.resources import CDN
11+
12+
13+
# Data - create a ripple surface z = sin(sqrt(x^2 + y^2))
14+
np.random.seed(42)
15+
16+
# Grid setup - 30x30 for clear wireframe
17+
n_points = 30
18+
x = np.linspace(-4, 4, n_points)
19+
y = np.linspace(-4, 4, n_points)
20+
X, Y = np.meshgrid(x, y)
21+
22+
# Ripple function
23+
R = np.sqrt(X**2 + Y**2)
24+
Z = np.sin(R)
25+
26+
# 3D to 2D projection (elevation=30, azimuth=45)
27+
elev_rad = np.radians(30)
28+
azim_rad = np.radians(45)
29+
30+
# Rotation around z-axis (azimuth)
31+
X_rot = X * np.cos(azim_rad) - Y * np.sin(azim_rad)
32+
Y_rot = X * np.sin(azim_rad) + Y * np.cos(azim_rad)
33+
34+
# Rotation around x-axis (elevation) and project
35+
X_proj = X_rot
36+
Z_proj = Y_rot * np.sin(elev_rad) + Z * np.cos(elev_rad)
37+
38+
# Collect wireframe lines
39+
# Lines along x-direction (rows)
40+
x_lines_xs = []
41+
x_lines_ys = []
42+
for i in range(n_points):
43+
x_lines_xs.append(X_proj[i, :].tolist())
44+
x_lines_ys.append(Z_proj[i, :].tolist())
45+
46+
# Lines along y-direction (columns)
47+
y_lines_xs = []
48+
y_lines_ys = []
49+
for j in range(n_points):
50+
y_lines_xs.append(X_proj[:, j].tolist())
51+
y_lines_ys.append(Z_proj[:, j].tolist())
52+
53+
# Combine all lines
54+
all_xs = x_lines_xs + y_lines_xs
55+
all_ys = x_lines_ys + y_lines_ys
56+
57+
# Create Bokeh figure
58+
p = figure(width=4800, height=2700, title="wireframe-3d-basic · bokeh · pyplots.ai", toolbar_location=None, tools="")
59+
60+
# Remove axis labels for cleaner 3D projection look
61+
p.xaxis.visible = False
62+
p.yaxis.visible = False
63+
64+
# Draw wireframe using multi_line with Python Blue
65+
p.multi_line(xs=all_xs, ys=all_ys, line_color="#306998", line_width=2, line_alpha=0.8)
66+
67+
# Set equal aspect ratio and appropriate ranges
68+
x_min, x_max = min(min(xs) for xs in all_xs), max(max(xs) for xs in all_xs)
69+
y_min, y_max = min(min(ys) for ys in all_ys), max(max(ys) for ys in all_ys)
70+
71+
# Add padding
72+
x_pad = (x_max - x_min) * 0.1
73+
y_pad = (y_max - y_min) * 0.1
74+
75+
p.x_range = Range1d(x_min - x_pad, x_max + x_pad)
76+
p.y_range = Range1d(y_min - y_pad, y_max + y_pad)
77+
78+
# Add text annotations for axes
79+
p.text(x=[x_max + x_pad * 0.5], y=[0], text=["X"], text_font_size="28pt", text_color="#666666", text_align="center")
80+
p.text(
81+
x=[x_min - x_pad * 0.3],
82+
y=[y_min - y_pad * 0.2],
83+
text=["Y"],
84+
text_font_size="28pt",
85+
text_color="#666666",
86+
text_align="center",
87+
)
88+
p.text(
89+
x=[x_min - x_pad * 0.5],
90+
y=[y_max + y_pad * 0.3],
91+
text=["Z"],
92+
text_font_size="28pt",
93+
text_color="#666666",
94+
text_align="center",
95+
)
96+
97+
# Styling for 4800x2700 px
98+
p.title.text_font_size = "32pt"
99+
100+
# Grid styling - subtle
101+
p.xgrid.grid_line_color = "#cccccc"
102+
p.ygrid.grid_line_color = "#cccccc"
103+
p.xgrid.grid_line_alpha = 0.3
104+
p.ygrid.grid_line_alpha = 0.3
105+
p.xgrid.grid_line_dash = [6, 4]
106+
p.ygrid.grid_line_dash = [6, 4]
107+
108+
# Background
109+
p.background_fill_color = "#fafafa"
110+
p.border_fill_color = "white"
111+
p.outline_line_color = None
112+
113+
# Save PNG
114+
export_png(p, filename="plot.png")
115+
116+
# Save HTML for interactive version
117+
save(p, filename="plot.html", resources=CDN, title="wireframe-3d-basic · bokeh · pyplots.ai")
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
# Per-library metadata for bokeh implementation of wireframe-3d-basic
2+
# Auto-generated by impl-generate.yml
3+
4+
library: bokeh
5+
specification_id: wireframe-3d-basic
6+
7+
# Preview URLs (filled by workflow)
8+
preview_url: https://storage.googleapis.com/pyplots-images/plots/wireframe-3d-basic/bokeh/plot.png
9+
preview_thumb: https://storage.googleapis.com/pyplots-images/plots/wireframe-3d-basic/bokeh/plot_thumb.png
10+
preview_html: https://storage.googleapis.com/pyplots-images/plots/wireframe-3d-basic/bokeh/plot.html
11+
12+
current:
13+
version: 0
14+
generated_at: 2025-12-16T16:14:12Z
15+
generated_by: claude-opus-4-5-20251101
16+
workflow_run: 20274573237
17+
issue: 1015
18+
quality_score: 91
19+
# Version info (filled by workflow)
20+
python_version: "3.13.11"
21+
library_version: "unknown"
22+
23+
history: []

0 commit comments

Comments
 (0)