You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何基于Plotly图形对象列表创建按钮触发的动画?

解决方案

要实现通过按钮切换天气图层的动画效果,无需重复创建完整图形对象,只需基于同一个包含城市点的基础图,将不同日期的天气图层配置为动画帧(frames),再添加控制按钮即可。以下是修改后的完整代码:

import requests
from bs4 import BeautifulSoup
import pandas as pd
import plotly.express as px
import plotly.graph_objects as go

# 加载城市地理数据
us_cities = pd.read_csv("https://raw.githubusercontent.com/plotly/datasets/master/us-cities-top-1k.csv")

# 获取天气数据的时间范围
r = requests.get('https://geo.weather.gc.ca/geomet?service=WMS&version=1.3.0&request=GetCapabilities&layer=GDPS.DIAG_NW_PT1H')
soup = BeautifulSoup(r.text, 'xml')
start, end = soup.findAll('Dimension')[0].text.split('/')[:2]
dates = pd.date_range(start, end, freq='1h').strftime('%Y-%m-%dT%H:%M:%SZ')[0::3]

# 创建基础图形(仅包含城市点,不添加天气图层)
base_fig = px.scatter_mapbox(us_cities, lat="lat", lon="lon", hover_name="City", hover_data=["State", "Population"],
                             color_discrete_sequence=["black"], zoom=3, height=600, center={'lat': 42.18845, 'lon':-87.81544},
                             title=dates[0])

base_fig.update_layout(
    mapbox_style="open-street-map",
    margin={"r":0,"t":50,"l":0,"b":0}
)

# 生成动画帧:每个帧对应一个日期的天气图层配置
frames = []
for date in dates:
    frame = go.Frame(
        data=[],  # 城市点数据不变,无需重复定义
        layout=go.Layout(
            mapbox_layers=[
                {
                    "below": 'traces',
                    "sourcetype": "raster",
                    "sourceattribution": "Government of Canada",
                    "source": [
                        f"https://geo.weather.gc.ca/geomet/?SERVICE=WMS&VERSION=1.3.0&REQUEST=GetMap&BBOX={{bbox-epsg-3857}}&CRS=EPSG:3857&WIDTH=1000&HEIGHT=1000&LAYERS=GDPS.DIAG_NW_PT1H&TILED=true&FORMAT=image/png&TIME={date}"
                    ],
                }
            ],
            title=f"天气图层时间: {date}"
        )
    )
    frames.append(frame)

# 添加动画控制按钮
base_fig.update(
    frames=frames,
    updatemenus=[
        dict(
            type="buttons",
            buttons=[
                dict(label="播放",
                     method="animate",
                     args=[None, {"frame": {"duration": 500, "redraw": True},
                                  "fromcurrent": True, "transition": {"duration": 300}}]),
                dict(label="暂停",
                     method="animate",
                     args=[[None], {"frame": {"duration": 0, "redraw": False},
                                    "mode": "immediate", "transition": {"duration": 0}}]),
                dict(label="上一步",
                     method="animate",
                     args=[[-1], {"frame": {"duration": 300, "redraw": True},
                                  "transition": {"duration": 300}}]),
                dict(label="下一步",
                     method="animate",
                     args=[[1], {"frame": {"duration": 300, "redraw": True},
                                  "transition": {"duration": 300}}])
            ],
            direction="left",
            pad={"r": 10, "t": 87},
            showactive=True,
            x=0.1,
            xanchor="right",
            y=0,
            yanchor="top"
        )
    ]
)

base_fig.show()

关键说明:

  • 基础图复用:只创建一次包含城市点的基础图形,避免重复渲染静态数据,提升性能。
  • 动画帧设计:每个帧仅更新mapbox_layers配置和标题,不改动城市点数据,精准实现天气图层的切换。
  • 按钮控制:通过updatemenus添加播放、暂停、步进按钮,配置帧切换的时长和过渡效果,与官网示例的交互逻辑一致。

内容的提问来源于stack exchange,提问作者It_is_Chris

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 08:32:17