Python Plotly中y轴autorange功能失效问题求助
Plotly子图X轴同步后Y轴自动适配可见数据范围的解决方法
仅设置autorange=True无法实现X轴缩放时Y轴自动适配,因为Plotly默认只在图表初始化阶段计算Y轴范围。要实现动态调整,需添加自定义JavaScript逻辑监听缩放事件,重新计算每个子图的Y轴范围。
修改后的完整代码:
import plotly.graph_objects as go from plotly.subplots import make_subplots fig = make_subplots(rows=4, cols=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["Pnl"], name="Pnl"), row=1, col=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["USDCAD"], name="USDCAD"), row=2, col=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["USD"], name="USD"), row=3, col=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["USD_SMA30"], name="USD SMA"), row=3, col=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["CAD"], name="CAD"), row=4, col=1) fig.append_trace(go.Line(x=df["Datetime"], y=df["CAD_SMA30"], name="CAD SMA"), row=4, col=1) fig.update_layout(width=1000, height=2000) fig.update_xaxes(matches='x') fig.update_yaxes(autorange=True) # 注入自定义JS监听缩放事件,动态调整Y轴范围 fig.add_annotation( text=f""" <script> var gd = document.getElementById('{fig.layout.id}'); gd.on('plotly_relayout', function(eventData) {{ if (eventData['xaxis.range[0]'] || eventData['xaxis.range[1]']) {{ const xMin = eventData['xaxis.range[0]'] || gd.layout.xaxis.range[0]; const xMax = eventData['xaxis.range[1]'] || gd.layout.xaxis.range[1]; // 遍历4个子图的Y轴 for (let i = 1; i <= 4; i++) {{ const yAxisKey = i === 1 ? 'yaxis' : `yaxis${{i}}`; const relevantTraces = gd.data.filter(t => t.yaxis === yAxisKey); if (!relevantTraces.length) continue; // 收集当前X范围内的所有Y值 const yValues = []; relevantTraces.forEach(trace => {{ trace.x.forEach((xVal, idx) => {{ if (xVal >= xMin && xVal <= xMax) {{ yValues.push(trace.y[idx]); }} }}); }}); // 计算Y轴范围并添加边距 const yMin = Math.min(...yValues); const yMax = Math.max(...yValues); const margin = (yMax - yMin) * 0.05; // 更新Y轴范围 Plotly.relayout(gd, {{ [`${{yAxisKey}}.range[0]`]: yMin - margin, [`${{yAxisKey}}.range[1]`]: yMax + margin }}); }} }} }}); </script> """, showarrow=False, x=0, y=0, xref='paper', yref='paper', xanchor='left', yanchor='bottom', font=dict(size=0) ) fig.show()
代码说明
- 监听
plotly_relayout事件:用户缩放或平移图表时触发该事件,捕获X轴的新范围。 - 筛选可见数据:针对每个子图,提取当前X轴范围内的所有Y值,计算最大最小值。
- 动态更新Y轴:为Y轴范围添加5%的边距(避免数据紧贴轴边界),然后更新对应子图的Y轴范围。
- 保留X轴同步:原有的
matches='x'设置确保所有子图X轴范围始终一致。
内容的提问来源于stack exchange,提问作者Matt
相关产品推荐
相关产品推荐

