[TOC]
这个界面是用户看到的主界面。总体由QStackedWidget组成。
QStackedWidget应当持有几个QWidget:
- ShopBoard
- PVE(本地对战机器)
- PVP(联网对战)*
- SelectBoard(人物选择界面,由以上两个调用)
- 关于(开发者名单等)*
- 设置(音量等)*
- 登陆界面(这个应该在进入欢迎界面之前出现)*
商店界面应当提供:
- 英雄的展示:
- 皮肤
- 名称,描述
- 血量,魔力值
- 技能的名称和描述
- 价格
- 购买按钮和选择按钮 (两者只能有一个可点击,根据购买情况决定)
- 音效(如果可能的话)
- 合适的背景图片
- 合适的背景音乐
游戏界面应当展示三个部分:
- 角色的皮肤,血量,魔力值
- 可点击的技能
- 所有的砖块,仅此而已
- 角色的皮肤,血量,魔力值(魔力值可以不给看)
- 不可点击的技能
制作人员名单
- 背景音量
- 音效(消除砖块时,技能释放时)音量
- 登录
- 注册
/*members*/
public:
static const int size = 64;//Stone的默认大小
int TYPE = NORMAL_STONE;//Stone的类型
int HP = 0, DAMAGE = 0, MP = 0;
QColor background;
QPixmap foreground;
QPen edge;//绘制边缘用
bool isAnimating = false;//是否处于运动中
private:
bool mouseHasEntered = false;//鼠标是否曾经进入过这个Stone
QSize defaultSize = QSize(25, 25);
QSize Stone::sizeHint() const;
//sizeHint会决定Stone的默认大小
//要获取size,请使用Stone::size
bool Stone::isValid() const;
//判断一个Stone是否合法
bool Stone::match(const Stone * stone) const;
//判断两个Stone是否类型相同
virtual void setData();
//设置HP,DAMAGE,MP
virtual void setImage();
//设置background和foreground
protected:
void paintEvent(QPaintEvent * event) override;
//由构造器或者update()调用,请勿显性调用
void mouseReleaseEvent(QMouseEvent * event) override;
//当鼠标松开时触发
//当该砖块处于isAnimating的状态中时,无法
void enterEvent(QEvent * event) override;
//鼠标进入时触发:边缘发光
void leaveEvent(QEvent * event) override;
//鼠标离开时触发:取消边缘发光
signals:
void clicked(Stone* me);
//由mouseReleaseEvent触发
public:
const int boardSize = 8;
QVector<QVector<Stone*>> board;
private:
bool isAnimating = false;
Stone* first;Stone* second;
QPoint firstPos;QPoint secondPos;
MoveData md;
EvaluateState es;
QVector<QPair<int, int>> pathOne, pathTwo;
QVector<QPair<int, int>> stoneToCrush;
ExchangeAnimation* exchangeAnimaion;
CrushAnimation* crushAnimation;
GravityAnimation* gravityAnimation;
StoneManager stoneManager;
public:
GameLogic(QWidget *parent = Q_NULLPTR);
void setMoveData(int fx, int fy, int sx, int sy);
private:
bool isTwoStonesConnected();
//invoke if two stones have been chosen
bool evaluate(EvaluateState state = Normal, QVector<QVector<bool>>& visited = QVector<QVector<bool>>(0));
void initializeVisitedVector(QVector<QVector<bool>>& visited);
bool isPositionValid(int position) const;
bool isPositionValid(int col, int row) const;
bool isMoveValid() const;
void DFS(int x, int y, QVector<QVector<bool>>& visited, QVector<QPair<int, int>>& stones);
void evaluatePath(QVector<QPair<int, int>>& path);
//remove illegal elements in path
void evaluateStonesToCrush(QVector<QPair<int, int>>& path);
void animateCrushingStones();
void waitForStopAnimation();
void enableAllStones();
void stonesCrushing(int hp, int damage, int mp);
public slots:
void fillBoard();
void clickedStone(Stone* stone);//invoke by Stone::clicked()
void deleteStone();
void deleteStone(int col, int row);
void changeStone(int row, int col, int type);
void deleteRect();
void deleteRect(int col, int row, int width, int height);
void forceExchange();
void forceExchange(int x1, int y1, int x2, int y2);
protected slots:
void endMove();
void gravity();
void gravityFinished();
//evaluate board, if there are stones to crush, go on gravity
- Character (从Account获取)
- 血量,魔力值(以进度条的形式显示)
- 技能
- 皮肤
- 技能
- 技能音效
void takeDamage(int);
void recoverHP(int);
void recoverMP(int);
void send(QString account, int hp, int damage, int mp);
(连接至GameLogic)void dead(QString account);
- 砖块消除
void receive(QString account, int hp, int damage, int mp);
(从GameServer获得的消息)- 鼠标悬停(悬停在图片上显示角色描述,悬停在技能上显示技能描述)
win(QString account);
特指敌人的Player,按钮无法点击(需要视觉效果提示)
name: QString
cost: int
description: QString
- 释放技能
void useSkill(QString skillName, int skillCost);
通知Player消耗了多少魔力值,Player再发送信号给GameServer消耗魔力值
这个widget由昌凯枫负责。
初始化时从Account类读取,决定哪些Character是可购买的(不可购买的意味着可以直接点击选择)
- 我猜你需要记录最后一个被点击的角色。每次
success()
之后重置
void success();//记得改变两个按钮的状态
void fail();
void buy(QString name);
-
点击事件(两个按钮)
-
void outcome(bool flag);//flag = true,购买成功
-
void changeCharacter();//记得把原来的角色的选择按钮变为可点击
动态读取Skill文件夹
技能名
技能描述
技能消耗
//关于技能如何调用,这里还需要讨论
Skill* getSkill(QString skillName,QWidget* parent);
name: QString
description: QString
price: int
hp: int
mp: int
skin: QString
skills: QList<QString>
set and get
读取Character文件夹,保存在map中
角色名字
角色描述
角色价格
血量上限
魔力值上限
皮肤路径
技能
技能
...
技能
characters: QMap(QString, Character)
void readCharacter(QFile file);
void initialize();//读取文件夹,对每一个文件,使用readCharacter
Character getCharacter(QString name) const;
name: QString
money: int
characters: QList<QString>//记录购买过的角色名
character: Character//玩家使用的character
bool hasBoughtCharacter(QString name) const;
bool buyCharacter(QString name, int cost);//如果钱不够,返回false;否则扣钱,返回true
bool setCharacter(QString name);//设置使用的角色
Character* getSelectedCharacter() const;//提供给Player
updateFile();//退出时更改文件
读取Account类信息
用户名
金钱数
默认角色
已购买角色
...
已购买角色
Player受到信息后,会根据Account来决定如何处理。这个类需要网络通信,很可能需要一个额外的线程。
暂时考虑由张永泰来完成这个重任?
Account1和2: QString
void recieve(QString account, int hp, int damage, int mp);
void send(QString account, int hp, int damage, int mp);
这一块与设置连接紧密。建议由同一个人负责。
需要用到的声音:
- 背景音乐(也许不同界面需要切换)
- 音效(石头的点击,消除,角色的技能)