使用Python构建刺客信条编年史交互式时间线实战
一、环境准备与依赖安装
本指南将使用Python的Pandas库进行数据处理,结合Plotly库生成可交互的甘特图时间线。在开始编写代码前,需要确保本地环境已安装Python 3.8及以上版本。请打开终端或命令行工具,执行以下命令安装核心依赖库:
```bash
pip install pandas plotly
```
执行完毕后,可以通过以下命令验证库是否安装成功,确保版本兼容性:
```bash
python -c "import pandas; import plotly; print('环境就绪')"
```
二、数据源构建与清洗
为了构建完整的编年史,我们需要整理《刺客信条》系列主序作及其重要发售时间。数据将包含游戏名称、发售年份、所属时代以及主角信息。我们将直接在代码中构建结构化的字典数据,模拟从数据库或API获取的数据源。
请在项目目录下创建一个名为ac_timeline.py的文件,并输入以下数据准备代码:
```python
import pandas as pd
from plotly.figure_factory import create_distplot
import plotly.graph_objects as go
import datetime
原始数据定义:包含游戏名、发售年份、时代背景、主角
raw_data = [
{"title": "刺客信条", "year": 2007, "era": "十字军东征", "protagonist": "阿泰尔"},
{"title": "刺客信条2", "year": 2009, "era": "文艺复兴", "protagonist": "艾吉奥"},
{"title": "刺客信条:兄弟会", "year": 2010, "era": "文艺复兴", "protagonist": "艾吉奥"},
{"title": "刺客信条:启示录", "year": 2011, "era": "文艺复兴", "protagonist": "艾吉奥"},
{"title": "刺客信条3", "year": 2012, "era": "美国革命", "protagonist": "康纳"},
{"title": "刺客信条4:黑旗", "year": 2013, "era": "黄金时代", "protagonist": "爱德华"},
{"title": "刺客信条:叛变", "year": 2014, "era": "七年战争", "protagonist": "谢伊"},
{"title": "刺客信条:大革命", "year": 2014, "era": "法国大革命", "protagonist": "亚诺"},
{"title": "刺客信条:枭雄", "year": 2015, "era": "维多利亚时代", "protagonist": "雅各/伊薇"},
{"title": "刺客信条:起源", "year": 2017, "era": "托勒密埃及", "protagonist": "巴耶克"},
{"title": "刺客信条:奥德赛", "year": 2018, "era": "伯罗奔尼撒战争", "protagonist": "卡珊德拉/阿列克谢欧斯"},
{"title": "刺客信条:英灵殿", "year": 2020, "era": "维京入侵", "protagonist": "艾沃尔"},
{"title": "刺客信条:幻景", "year": 2023, "era": "伊斯兰黄金时代", "protagonist": "巴辛姆"}
]
转换为DataFrame以便处理
df = pd.DataFrame(raw_data)
数据清洗:将年份转换为Plotly可识别的时间格式
为了在时间线上显示为点,我们将Start和End都设为同一年
df['Start'] = pd.to_datetime(df['year'], format='%Y')
df['Finish'] = df['Start'] + pd.Timedelta(days=365) 视觉上延长一年以便于点击
根据时代定义颜色映射,增强视觉区分
color_map = {
"十字军东征": "95a5a6",
"文艺复兴": "c0392b",
"美国革命": "2980b9",
"黄金时代": "f39c12",
"七年战争": "8e44ad",
"法国大革命": "2c3e50",
"维多利亚时代": "7f8c8d",
"托勒密埃及": "d35400",
"伯罗奔尼撒战争": "16a085",
"维京入侵": "2ecc71",
"伊斯兰黄金时代": "e67e22"
}
df['Color'] = df['era'].map(color_map)
```
三、核心可视化代码实现
接下来使用Plotly的Graph Objects模块构建图表。这里不使用简单的`plot`函数,而是使用`Figure`对象进行精细控制,确保生成的图表符合专业展示标准。我们将创建一个基于时间轴的散点图,通过悬停显示详细信息。
继续在ac_timeline.py中追加以下核心绘图逻辑:
```python
初始化Figure对象
fig = go.Figure()
遍历DataFrame,为每一个游戏添加一个轨迹点
这种方式比直接传入整个DataFrame更能控制每个点的样式
for index, row in df.iterrows():
fig.add_trace(go.Scatter(
x=[row['Start']], X轴为时间
y=[row['title']], Y轴为游戏名
name=row['title'],
mode='markers',
marker=dict(
size=20,
color=row['Color'],
line=dict(color='white', width=2)
),
自定义悬停信息
hovertemplate=(
"
%{y}"
"发售年份: %{x|%Y}
"
"时代背景: " + row['era'] + "
"
"主角: " + row['protagonist'] +
"
"
),
showlegend=False 隐藏图例,避免拥挤
))
更新布局,设置标题和坐标轴样式
fig.update_layout(
title={
'text': '《刺客信条》系列编年史 (2007-2023)',
'x': 0.5,
'xanchor': 'center',
'font': {'size': 24, 'color': '2c3e50'}
},
xaxis=dict(
title='发售时间',
showgrid=True,
gridcolor='e0e0e0',
tickformat='%Y' 仅显示年份
),
yaxis=dict(
title='游戏作品',
autorange='reversed', 让最早的游戏显示在顶部,符合时间线阅读习惯
showgrid=False
),
plot_bgcolor='rgba(255,255,255,0.9)', 背景色
height=800, 设置图表高度
hovermode='closest' 悬停模式
)
```
四、生成HTML与本地预览
为了实现零门槛查看,我们将图表导出为独立的HTML文件。这样即使在没有Python环境的设备上,也可以直接用浏览器打开查看。同时,我们将添加一段简单的逻辑,自动在生成后尝试调用系统默认浏览器打开该文件。
在文件末尾添加导出和预览代码:
```python
定义输出文件名
output_file = "assassins_creed_timeline.html"
将图表写入HTML文件
fig.write_html(output_file)
print(f"交互式时间线已生成:{output_file}")
自动打开浏览器的辅助逻辑
import webbrowser
import os
获取文件的绝对路径
abs_path = os.path.abspath(output_file)
在不同操作系统下调用默认浏览器
try:
webbrowser.open('file://' + abs_path)
print("已自动在浏览器中打开文件。")
except Exception as e:
print(f"无法自动打开浏览器,请手动打开文件:{abs_path}")
```
五、完整代码执行
现在,所有的逻辑都已封装在ac_timeline.py中。请确保该文件包含了上述所有代码片段。回到终端,在文件所在目录下运行以下命令启动程序:
```bash
python ac_timeline.py
```
程序运行成功后,会看到提示“交互式时间线已生成”,并且浏览器会自动弹出一个新窗口展示结果。在生成的图表中,你可以:
- 缩放时间轴:使用鼠标滚轮或框选区域来放大查看特定年份的细节。
- 查看详情:鼠标悬停在代表游戏的圆点上,会显示该游戏的时代背景和主角信息。
- 保存图片:点击图表右上角的相机图标,可以将当前视图保存为静态图片。
如果遇到浏览器未自动弹出的情况,请直接在文件夹中找到assassins_creed_timeline.html并双击打开。该HTML文件是完全独立的,可以随意发送给其他人查看。