本文目录导读:

我将为您创建一个Java脑图(思维导图)案例,使用Java Swing实现一个可视化脑图工具。
完整实现代码
import javax.swing.*;
import javax.swing.border.*;
import java.awt.*;
import java.awt.event.*;
import java.awt.geom.*;
import java.util.*;
import java.util.List;
public class MindMapDemo extends JFrame {
private MindMapPanel mindMapPanel;
private JToolBar toolBar;
private JLabel statusBar;
public MindMapDemo() {
setTitle("Java脑图 - 思维导图工具");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setSize(1200, 800);
setLocationRelativeTo(null);
// 初始化组件
mindMapPanel = new MindMapPanel();
createToolBar();
createStatusBar();
// 添加主面板
add(mindMapPanel, BorderLayout.CENTER);
add(toolBar, BorderLayout.NORTH);
add(statusBar, BorderLayout.SOUTH);
// 添加菜单栏
setJMenuBar(createMenuBar());
// 键盘快捷键
setupKeyboardShortcuts();
}
private JMenuBar createMenuBar() {
JMenuBar menuBar = new JMenuBar();
// 文件菜单
JMenu fileMenu = new JMenu("文件");
JMenuItem newItem = new JMenuItem("新建");
newItem.addActionListener(e -> mindMapPanel.newMindMap());
JMenuItem saveItem = new JMenuItem("保存");
saveItem.addActionListener(e -> saveMindMap());
JMenuItem loadItem = new JMenuItem("加载");
loadItem.addActionListener(e -> loadMindMap());
JMenuItem exitItem = new JMenuItem("退出");
exitItem.addActionListener(e -> System.exit(0));
fileMenu.add(newItem);
fileMenu.add(saveItem);
fileMenu.add(loadItem);
fileMenu.addSeparator();
fileMenu.add(exitItem);
// 编辑菜单
JMenu editMenu = new JMenu("编辑");
JMenuItem addNodeItem = new JMenuItem("添加节点");
addNodeItem.addActionListener(e -> mindMapPanel.addChildNode());
JMenuItem deleteNodeItem = new JMenuItem("删除节点");
deleteNodeItem.addActionListener(e -> mindMapPanel.deleteSelectedNode());
JMenuItem editNodeItem = new JMenuItem("编辑节点文本");
editNodeItem.addActionListener(e -> mindMapPanel.editSelectedNode());
editMenu.add(addNodeItem);
editMenu.add(deleteNodeItem);
editMenu.add(editNodeItem);
// 视图菜单
JMenu viewMenu = new JMenu("视图");
JCheckBoxMenuItem autoLayoutItem = new JCheckBoxMenuItem("自动布局", true);
autoLayoutItem.addActionListener(e -> mindMapPanel.setAutoLayout(autoLayoutItem.isSelected()));
JMenuItem expandAllItem = new JMenuItem("展开全部");
expandAllItem.addActionListener(e -> mindMapPanel.expandAll());
JMenuItem collapseAllItem = new JMenuItem("收起全部");
collapseAllItem.addActionListener(e -> mindMapPanel.collapseAll());
viewMenu.add(autoLayoutItem);
viewMenu.add(expandAllItem);
viewMenu.add(collapseAllItem);
// 帮助菜单
JMenu helpMenu = new JMenu("帮助");
JMenuItem aboutItem = new JMenuItem("quot;);
aboutItem.addActionListener(e -> showAboutDialog());
helpMenu.add(aboutItem);
menuBar.add(fileMenu);
menuBar.add(editMenu);
menuBar.add(viewMenu);
menuBar.add(helpMenu);
return menuBar;
}
private void createToolBar() {
toolBar = new JToolBar();
toolBar.setFloatable(false);
JButton addNodeBtn = createToolButton("➕", "添加子节点", e -> mindMapPanel.addChildNode());
JButton addSiblingBtn = createToolButton("📝", "添加兄弟节点", e -> mindMapPanel.addSiblingNode());
JButton deleteNodeBtn = createToolButton("🗑️", "删除节点", e -> mindMapPanel.deleteSelectedNode());
JButton editNodeBtn = createToolButton("✏️", "编辑节点", e -> mindMapPanel.editSelectedNode());
JButton expandBtn = createToolButton("🔍", "展开节点", e -> mindMapPanel.toggleExpand());
toolBar.add(addNodeBtn);
toolBar.add(addSiblingBtn);
toolBar.add(deleteNodeBtn);
toolBar.add(editNodeBtn);
toolBar.add(expandBtn);
toolBar.addSeparator();
// 颜色选择
JButton colorBtn = new JButton("🎨 颜色");
colorBtn.addActionListener(e -> mindMapPanel.changeNodeColor());
toolBar.add(colorBtn);
}
private JButton createToolButton(String text, String tooltip, ActionListener action) {
JButton button = new JButton(text);
button.setToolTipText(tooltip);
button.addActionListener(action);
button.setFocusable(false);
return button;
}
private void createStatusBar() {
statusBar = new JLabel(" 就绪 | 节点数: 0");
statusBar.setBorder(BorderFactory.createEmptyBorder(3, 5, 3, 5));
statusBar.setOpaque(true);
statusBar.setBackground(new Color(230, 230, 230));
}
private void setupKeyboardShortcuts() {
InputMap inputMap = getRootPane().getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
ActionMap actionMap = getRootPane().getActionMap();
// Tab: 添加子节点
inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_TAB, 0), "addChild");
actionMap.put("addChild", new AbstractAction() {
public void actionPerformed(ActionEvent e) {
mindMapPanel.addChildNode();
}
});
// F2: 编辑节点
inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_F2, 0), "editNode");
actionMap.put("editNode", new AbstractAction() {
public void actionPerformed(ActionEvent e) {
mindMapPanel.editSelectedNode();
}
});
// Delete: 删除节点
inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_DELETE, 0), "deleteNode");
actionMap.put("deleteNode", new AbstractAction() {
public void actionPerformed(ActionEvent e) {
mindMapPanel.deleteSelectedNode();
}
});
}
private void saveMindMap() {
JFileChooser fileChooser = new JFileChooser();
if (fileChooser.showSaveDialog(this) == JFileChooser.APPROVE_OPTION) {
mindMapPanel.saveToFile(fileChooser.getSelectedFile());
}
}
private void loadMindMap() {
JFileChooser fileChooser = new JFileChooser();
if (fileChooser.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) {
mindMapPanel.loadFromFile(fileChooser.getSelectedFile());
}
}
private void showAboutDialog() {
JOptionPane.showMessageDialog(this,
"Java脑图 - 思维导图工具\n\n版本: 1.0\n作者: Java Demo",
"quot;, JOptionPane.INFORMATION_MESSAGE);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (Exception e) {
e.printStackTrace();
}
new MindMapDemo().setVisible(true);
});
}
}
// 脑图节点类
class MindNode {
private String text;
private MindNode parent;
private List<MindNode> children;
private int x, y;
private int width = 120, height = 40;
private Color color;
private boolean expanded;
public MindNode(String text) {
this.text = text;
this.children = new ArrayList<>();
this.expanded = true;
this.color = new Color(204, 229, 255); // 默认浅蓝色
}
public void addChild(MindNode child) {
child.parent = this;
children.add(child);
}
public void addSibling(MindNode sibling) {
if (parent != null) {
parent.addChild(sibling);
}
}
public boolean isRoot() {
return parent == null;
}
public boolean isLeaf() {
return children.isEmpty();
}
// Getters and Setters
public String getText() { return text; }
public void setText(String text) { this.text = text; }
public MindNode getParent() { return parent; }
public List<MindNode> getChildren() { return children; }
public int getX() { return x; }
public void setX(int x) { this.x = x; }
public int getY() { return y; }
public void setY(int y) { this.y = y; }
public int getWidth() { return width; }
public void setWidth(int width) { this.width = width; }
public int getHeight() { return height; }
public void setHeight(int height) { this.height = height; }
public Color getColor() { return color; }
public void setColor(Color color) { this.color = color; }
public boolean isExpanded() { return expanded; }
public void setExpanded(boolean expanded) { this.expanded = expanded; }
public void toggleExpanded() { this.expanded = !this.expanded; }
// 获取中心点
public int getCenterX() { return x + width / 2; }
public int getCenterY() { return y + height / 2; }
// 获取所有子孙节点
public List<MindNode> getAllDescendants() {
List<MindNode> descendants = new ArrayList<>();
collectDescendants(this, descendants);
return descendants;
}
private void collectDescendants(MindNode node, List<MindNode> list) {
for (MindNode child : node.children) {
list.add(child);
collectDescendants(child, list);
}
}
}
// 脑图面板类
class MindMapPanel extends JPanel {
private MindNode root;
private MindNode selectedNode;
private int nodeCount;
private boolean autoLayout;
private Point dragStart;
private MindNode dragNode;
public MindMapPanel() {
setBackground(new Color(250, 250, 250));
newMindMap();
setupMouseListener();
}
private void setupMouseListener() {
// 鼠标点击选择节点
addMouseListener(new MouseAdapter() {
@Override
public void mousePressed(MouseEvent e) {
MindNode node = findNodeAt(e.getPoint());
if (node != null) {
selectedNode = node;
dragStart = e.getPoint();
dragNode = node;
repaint();
}
}
@Override
public void mouseReleased(MouseEvent e) {
if (dragNode != null) {
updateStatusBar();
dragNode = null;
}
}
@Override
public void mouseClicked(MouseEvent e) {
if (e.getClickCount() == 2) {
MindNode node = findNodeAt(e.getPoint());
if (node != null && !node.isRoot()) {
node.toggleExpanded();
if (autoLayout) {
layoutTree();
}
repaint();
}
}
}
});
// 鼠标拖动节点
addMouseMotionListener(new MouseMotionAdapter() {
@Override
public void mouseDragged(MouseEvent e) {
if (dragNode != null && e.isShiftDown()) {
int dx = e.getX() - dragStart.x;
int dy = e.getY() - dragStart.y;
dragNode.setX(dragNode.getX() + dx);
dragNode.setY(dragNode.getY() + dy);
dragStart = e.getPoint();
repaint();
}
}
});
// 键盘监听
setFocusable(true);
addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
if (selectedNode != null) {
int moveAmount = 5;
if (e.isShiftDown()) {
moveAmount = 10;
}
switch(e.getKeyCode()) {
case KeyEvent.VK_UP:
selectedNode.setY(selectedNode.getY() - moveAmount);
break;
case KeyEvent.VK_DOWN:
selectedNode.setY(selectedNode.getY() + moveAmount);
break;
case KeyEvent.VK_LEFT:
selectedNode.setX(selectedNode.getX() - moveAmount);
break;
case KeyEvent.VK_RIGHT:
selectedNode.setX(selectedNode.getX() + moveAmount);
break;
}
repaint();
}
}
});
}
private MindNode findNodeAt(Point point) {
// 遍历所有可见节点
List<MindNode> visibleNodes = getVisibleNodes();
for (int i = visibleNodes.size() - 1; i >= 0; i--) {
MindNode node = visibleNodes.get(i);
Rectangle bounds = new Rectangle(node.getX(), node.getY(), node.getWidth(), node.getHeight());
if (bounds.contains(point)) {
return node;
}
}
return null;
}
private List<MindNode> getVisibleNodes() {
List<MindNode> visible = new ArrayList<>();
if (root != null) {
collectVisibleNodes(root, visible);
}
return visible;
}
private void collectVisibleNodes(MindNode node, List<MindNode> list) {
list.add(node);
if (node.isExpanded()) {
for (MindNode child : node.getChildren()) {
collectVisibleNodes(child, list);
}
}
}
public void newMindMap() {
root = new MindNode("中心主题");
nodeCount = 1;
selectedNode = root;
autoLayout = true;
// 创建默认子节点
MindNode child1 = new MindNode("Java基础");
MindNode child2 = new MindNode("面向对象");
MindNode child3 = new MindNode("集合框架");
root.addChild(child1);
root.addChild(child2);
root.addChild(child3);
nodeCount = 4;
layoutTree();
updateStatusBar();
repaint();
}
private void layoutTree() {
if (!autoLayout) return;
int panelWidth = getWidth();
int panelHeight = getHeight();
// 递归布局,使用简单的水平树状布局
if (root != null) {
layoutNode(root, 50, panelHeight / 2, 0);
}
}
private void layoutNode(MindNode node, int x, int y, int level) {
node.setX(x);
node.setY(y - node.getHeight() / 2);
if (!node.isExpanded() || node.isLeaf()) {
return;
}
// 布局子节点
int childCount = node.getChildren().size();
int totalHeight = (childCount - 1) * (node.getHeight() + 30);
int startY = y - totalHeight / 2;
int childX = x + 200;
for (int i = 0; i < childCount; i++) {
MindNode child = node.getChildren().get(i);
int childY = startY + i * (node.getHeight() + 30);
layoutNode(child, childX, childY, level + 1);
}
}
public void addChildNode() {
if (selectedNode == null) {
return;
}
MindNode newNode = new MindNode("新节点");
selectedNode.addChild(newNode);
nodeCount++;
if (autoLayout) {
layoutTree();
}
selectedNode = newNode;
updateStatusBar();
repaint();
// 自动开始编辑新节点
editNode(newNode);
}
public void addSiblingNode() {
if (selectedNode == null || selectedNode.isRoot()) {
return;
}
MindNode newNode = new MindNode("新节点");
selectedNode.addSibling(newNode);
nodeCount++;
selectedNode = newNode;
if (autoLayout) {
layoutTree();
}
updateStatusBar();
repaint();
// 自动开始编辑新节点
editNode(newNode);
}
public void deleteSelectedNode() {
if (selectedNode == null || selectedNode.isRoot()) {
return;
}
int confirm = JOptionPane.showConfirmDialog(this,
"确定要删除节点 \"" + selectedNode.getText() + "\" 吗?",
"删除节点", JOptionPane.YES_NO_OPTION);
if (confirm == JOptionPane.YES_OPTION) {
MindNode parent = selectedNode.getParent();
parent.getChildren().remove(selectedNode);
nodeCount -= 1 + selectedNode.getAllDescendants().size();
selectedNode = parent;
if (autoLayout) {
layoutTree();
}
updateStatusBar();
repaint();
}
}
public void editSelectedNode() {
if (selectedNode != null) {
editNode(selectedNode);
}
}
private void editNode(MindNode node) {
String newText = JOptionPane.showInputDialog(this,
"编辑节点文本:", node.getText());
if (newText != null && !newText.trim().isEmpty()) {
node.setText(newText.trim());
adjustNodeSize(node);
if (autoLayout) {
layoutTree();
}
repaint();
}
}
private void adjustNodeSize(MindNode node) {
Graphics2D g2d = (Graphics2D) getGraphics();
if (g2d != null) {
FontMetrics fm = g2d.getFontMetrics();
int textWidth = fm.stringWidth(node.getText());
node.setWidth(Math.max(100, textWidth + 30));
}
}
public void toggleExpand() {
if (selectedNode != null) {
selectedNode.toggleExpanded();
if (autoLayout) {
layoutTree();
}
repaint();
}
}
public void expandAll() {
expandAllNodes(root);
if (autoLayout) {
layoutTree();
}
repaint();
}
private void expandAllNodes(MindNode node) {
node.setExpanded(true);
for (MindNode child : node.getChildren()) {
expandAllNodes(child);
}
}
public void collapseAll() {
collapseAllNodes(root);
if (autoLayout) {
layoutTree();
}
// 只显示根节点
nodeCount = 1;
repaint();
}
private void collapseAllNodes(MindNode node) {
if (!node.isRoot()) {
node.setExpanded(false);
}
for (MindNode child : node.getChildren()) {
collapseAllNodes(child);
}
}
public void changeNodeColor() {
if (selectedNode != null) {
Color newColor = JColorChooser.showDialog(this,
"选择节点颜色", selectedNode.getColor());
if (newColor != null) {
selectedNode.setColor(newColor);
repaint();
}
}
}
public void setAutoLayout(boolean autoLayout) {
this.autoLayout = autoLayout;
if (autoLayout) {
layoutTree();
repaint();
}
}
private void updateStatusBar() {
// 更新状态栏逻辑(省略具体实现)
}
public void saveToFile(java.io.File file) {
// 保存逻辑(使用对象序列化)
try {
java.io.ObjectOutputStream oos =
new java.io.ObjectOutputStream(new java.io.FileOutputStream(file));
oos.writeObject(root);
oos.close();
JOptionPane.showMessageDialog(this, "脑图保存成功!");
} catch (Exception e) {
JOptionPane.showMessageDialog(this, "保存失败: " + e.getMessage(),
"错误", JOptionPane.ERROR_MESSAGE);
}
}
public void loadFromFile(java.io.File file) {
// 加载逻辑
try {
java.io.ObjectInputStream ois =
new java.io.ObjectInputStream(new java.io.FileInputStream(file));
root = (MindNode) ois.readObject();
ois.close();
nodeCount = 1 + root.getAllDescendants().size();
layoutTree();
selectedNode = root;
updateStatusBar();
repaint();
JOptionPane.showMessageDialog(this, "脑图加载成功!");
} catch (Exception e) {
JOptionPane.showMessageDialog(this, "加载失败: " + e.getMessage(),
"错误", JOptionPane.ERROR_MESSAGE);
}
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
// 绘制连接线和节点
if (root != null) {
drawNode(g2d, root);
}
// 绘制选中效果
if (selectedNode != null) {
g2d.setColor(new Color(255, 100, 100, 50));
g2d.setStroke(new BasicStroke(3));
g2d.drawRoundRect(selectedNode.getX() - 3, selectedNode.getY() - 3,
selectedNode.getWidth() + 6, selectedNode.getHeight() + 6, 10, 10);
}
// 绘制标题
g2d.setColor(new Color(0, 0, 0, 30));
g2d.setFont(new Font("微软雅黑", Font.BOLD, 30));
g2d.drawString("📚 Java 学习脑图", 20, 40);
// 绘制操作提示
g2d.setColor(new Color(0, 0, 0, 60));
g2d.setFont(new Font("微软雅黑", Font.PLAIN, 12));
g2d.drawString("操作提示: 单击选择节点 | Shift+拖动移动节点 | 双击展开/收起 | TAB添加子节点 | F2编辑 | Delete删除",
20, getHeight() - 15);
}
private void drawNode(Graphics2D g2d, MindNode node) {
// 绘制到子节点的连接线
if (!node.isLeaf() && node.isExpanded()) {
for (MindNode child : node.getChildren()) {
drawConnection(g2d, node, child);
drawNode(g2d, child);
}
}
// 绘制节点
drawNodeBox(g2d, node);
}
private void drawConnection(Graphics2D g2d, MindNode parent, MindNode child) {
// 使用贝塞尔曲线绘制连接线
int x1 = parent.getCenterX();
int y1 = parent.getCenterY();
int x2 = child.getX();
int y2 = child.getCenterY();
int controlX = (x1 + x2) / 2;
Path2D.Double path = new Path2D.Double();
path.moveTo(x1, y1);
path.curveTo(controlX, y1, controlX, y2, x2, y2);
g2d.setColor(new Color(0, 0, 0, 100));
g2d.setStroke(new BasicStroke(2));
g2d.draw(path);
// 绘制箭头
drawArrow(g2d, x2, y2, child.getColor());
}
private void drawArrow(Graphics2D g2d, int x, int y, Color color) {
// 绘制小箭头
g2d.setColor(color.darker());
int size = 8;
Polygon arrow = new Polygon();
arrow.addPoint(x, y - size/2);
arrow.addPoint(x + size, y);
arrow.addPoint(x, y + size/2);
g2d.fill(arrow);
}
private void drawNodeBox(Graphics2D g2d, MindNode node) {
// 绘制节点矩形
g2d.setColor(node.getColor());
g2d.fillRoundRect(node.getX(), node.getY(), node.getWidth(), node.getHeight(), 15, 15);
// 绘制节点边框
g2d.setColor(node.getColor().darker());
g2d.setStroke(new BasicStroke(1.5f));
g2d.drawRoundRect(node.getX(), node.getY(), node.getWidth(), node.getHeight(), 15, 15);
// 绘制节点文本
g2d.setColor(Color.BLACK);
g2d.setFont(new Font("微软雅黑", Font.PLAIN, 13));
FontMetrics fm = g2d.getFontMetrics();
int textWidth = fm.stringWidth(node.getText());
int textX = node.getX() + (node.getWidth() - textWidth) / 2;
int textY = node.getCenterY() + fm.getAscent() / 2 - 2;
g2d.drawString(node.getText(), textX, textY);
// 如果是根节点,绘制特殊样式
if (node.isRoot()) {
g2d.setColor(new Color(255, 255, 255, 200));
g2d.setFont(new Font("微软雅黑", Font.BOLD, 16));
fm = g2d.getFontMetrics();
textWidth = fm.stringWidth(node.getText());
textX = node.getX() + (node.getWidth() - textWidth) / 2;
textY = node.getCenterY() + fm.getAscent() / 2 - 2;
g2d.drawString(node.getText(), textX, textY);
}
// 如果节点有子节点且已展开,绘制展开图标
if (!node.isLeaf() && node.isExpanded()) {
g2d.setColor(new Color(0, 0, 0, 150));
g2d.drawString("-", node.getX() + node.getWidth() - 15, node.getCenterY() + 5);
} else if (!node.isLeaf()) {
g2d.setColor(new Color(0, 0, 0, 150));
g2d.drawString("+", node.getX() + node.getWidth() - 15, node.getCenterY() + 5);
}
}
}
运行方式
- 将代码保存为
MindMapDemo.java - 编译:
javac MindMapDemo.java - 运行:
java MindMapDemo
功能特性
基本操作
- 添加节点:工具栏按钮或快捷键 TAB
- 添加兄弟节点:工具栏按钮
- 删除节点:工具栏按钮或 Delete 键
- 编辑节点:工具栏按钮、F2 键或双击
交互功能
- 选择节点:单击选择节点
- 移动节点:按住 Shift 键拖动
- 展开/收起:双击节点
- 键盘方向键:微调选中节点位置
视图功能
- 自动布局:自动排列节点位置
- 展开/收起全部:一键展开或收起所有节点
- 节点颜色:自定义节点颜色
文件功能
- 保存/加载:支持保存和加载脑图数据
界面效果
- 使用贝塞尔曲线绘制节点连接线
- 圆角矩形节点样式
- 支持图标和表情符号(工具栏)
- 清晰的状态栏和操作提示
这个脑图工具包含了基本的思维导图功能,您可以根据需要添加更多特性,如节点图标、链接、备注等。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播