1 /* 2 KBlackBox - A simple game inspired by an emacs module 3 4 SPDX-FileCopyrightText: 1999-2000 Robert Cimrman <cimrman3@students.zcu.cz> 5 SPDX-FileCopyrightText: 2007 Nicolas Roffet <nicolas-kde@roffet.com> 6 7 SPDX-License-Identifier: GPL-2.0-or-later 8 */ 9 10 11 12 #ifndef KBBSCALABLEGRAPHICWIDGET_H 13 #define KBBSCALABLEGRAPHICWIDGET_H 14 15 16 class QAction; 17 class QGraphicsScene; 18 #include <QGraphicsView> 19 class QLCDNumber; 20 class QResizeEvent; 21 22 23 class KGamePopupItem; 24 class QPushButton; 25 26 27 class KBBBallsOnBoard; 28 class KBBGameDoc; 29 class KBBGraphicsItem; 30 class KBBGraphicsItemBallRepository; 31 class KBBGraphicsItemBlackBox; 32 class KBBGraphicsItemCursor; 33 class KBBGraphicsItemRay; 34 class KBBGraphicsItemSet; 35 class KBBThemeManager; 36 37 38 39 /** 40 * @brief Scalable graphic central widget for KBlackBox 41 */ 42 class KBBScalableGraphicWidget : public QGraphicsView 43 { 44 Q_OBJECT 45 46 public: 47 /** 48 * @brief Distance between the black box and the widget border 49 * 50 * Note: The widget is scalable, so it's just an arbitrary default compared with other ranges. 51 * It's the minimal distance as the width/height ratio is constant and the widget may have another width/height ratio. 52 * @see RATIO 53 */ 54 static int const BORDER_SIZE = 50; 55 56 /** 57 * @brief Width and height of a single square on the black box 58 * 59 * Note: The widget is scalable, so it's just an arbitrary default compared with other ranges. 60 */ 61 static int const RATIO = 25; 62 63 /** 64 * @brief Every graphic items 65 * 66 * Values are used to define the relative heights between the displayed graphic items. 67 * @see KBBThemeManager::zValue(const KBBScalableGraphicWidget::itemType itemType); 68 */ 69 enum itemType { 70 background=0, 71 informationBackground=1, 72 blackbox=2, 73 blackboxGrid=3, 74 tutorialMarker=4, 75 markerNothing=5, 76 solutionRay=6, 77 playerRay=7, 78 resultBackground=8, 79 resultBackgroundHighlight=9, 80 resultReflection=10, 81 resultHit=11, 82 resultText=12, 83 solutionBall=13, 84 playerBall=14, 85 unsureBall=15, 86 wrongPlayerBall=16, 87 rightPlayerBall=17, 88 interactionInfoDeflection=18, 89 interactionInfoHit=19, 90 interactionInfoNothing=20, 91 interactionInfoReflection=21, 92 interactionInfoReflectionSym=22, 93 laser0=23, 94 laser90=24, 95 laser180=25, 96 laser270=26, 97 cursor=27 98 }; 99 100 101 /** 102 * @brief Constructor 103 */ 104 explicit KBBScalableGraphicWidget(KBBGameDoc* gameDoc, KBBThemeManager* themeManager, QAction* done); 105 ~KBBScalableGraphicWidget() override; 106 107 108 void addBall(int boxPosition); 109 void addBall(int boxPosition, int outsidePosition); 110 void addBallUnsure(const int boxPosition); 111 void addMarkerNothing(const int boxPosition); 112 void drawRay(const int borderPosition); 113 void mouseBorderClick(const int borderPosition); 114 void mouseBoxClick(const Qt::MouseButton button, int boxPosition); 115 int moveBall(const int boxPositionFrom, const int boxPositionTo); 116 int moveMarkerNothing(const int boxPositionFrom, const int boxPositionTo); 117 void newGame(int columns, int rows, int ballNumber); 118 119 /** 120 * @brief Message to display 121 * 122 * @param text Message. Attention: Message should not be too wide. 123 * @param time Time (in ms) the message remains displayed. 0 = forever. 124 */ 125 void popupText(const QString& text, int time = 5000); 126 127 int positionAfterMovingBall(const int boxPositionFrom, const int boxPositionTo) const; 128 129 void setPause(bool state); 130 void removeAllBalls(); 131 void removeBall(const int boxPosition); 132 void removeRay(); 133 void resizeEvent(QResizeEvent*) override; 134 QGraphicsScene* scene(); 135 void setScore(int score); 136 137 /** 138 * @brief display the solution 139 * 140 * Used at the end of the game and for the sandbox mode. 141 * @param continueGame Sould the game continue after displaying the solution? (Yes for sandbox mode, no for normal game end). 142 */ 143 void solve(const bool continueGame); 144 145 void toggleCursor(); 146 147 public Q_SLOTS: 148 void cursorOff(); 149 void hoverMovePosition(int newPosition); 150 void cursorAtNewPosition(int borderPosition); 151 void keyboardEnter(); 152 void keyboardMoveDown(); 153 void keyboardMoveLeft(); 154 void keyboardMoveRight(); 155 void keyboardMoveUp(); 156 void keyboardSpace(); 157 158 159 protected: 160 void drawBackground(QPainter* painter, const QRectF&) override; 161 162 163 private: 164 /** 165 * @brief Minimum width and height 166 * 167 * Minimum width and minimum height of the widget. The widget needs a minimal site: it is ugly if it is too small. 168 */ 169 static int const MINIMUM_SIZE = 250; 170 171 static int const OFFSET_DONE_BUTTON = 12; 172 173 void fillBallsOutside(); 174 void removeMarkerNothing(const int boxPosition); 175 void setBallUnsure(const int boxPosition, const bool unsure); 176 void setInputAccepted(bool inputAccepted); 177 void switchBall(); 178 void switchMarker(); 179 void updateDoneButton(); 180 void useLaser(const int incomingPosition); 181 182 183 // Graphics items 184 KBBGraphicsItemBlackBox* m_blackbox; 185 KBBGraphicsItemSet* m_balls; 186 KBBGraphicsItemSet* m_ballsSolution; 187 KBBGraphicsItemSet* m_ballsUnsure; 188 KBBGraphicsItemCursor* m_cursor; 189 KBBGraphicsItemBallRepository* m_ballRepository; 190 KBBGraphicsItemSet* m_lasers; 191 KBBGraphicsItemSet* m_markersNothing; 192 KBBGraphicsItemSet* m_rayResults; 193 KBBGraphicsItemRay* m_playerRay; 194 KBBGraphicsItemRay* m_solutionRay; 195 196 197 /** 198 * @brief Position and size of the background in scene coordinates 199 * 200 * Used for drwing the background. 201 * @see drawBackground(QPainter* painter, const QRectF&) 202 */ 203 QRectF m_rectBackground; 204 205 // Various member variables 206 int m_ballNumber; 207 KBBBallsOnBoard* m_boardBalls; 208 KBBBallsOnBoard* m_boardBallsPlaced; 209 int m_columns; 210 QAction* m_doneAction; 211 QPushButton* m_doneButton; 212 KBBGameDoc* m_gameDoc; 213 KGamePopupItem* m_infoScore; 214 bool m_inputAccepted; 215 bool m_pause; 216 int m_rayNumber; 217 218 int m_rows; 219 QGraphicsScene* m_scene; //TODO: Remove it because scene() already gives it back. 220 QLCDNumber* m_score; 221 KBBThemeManager* m_themeManager; 222 bool m_cursorFollowsMouse; //enable cursor following 223 }; 224 225 #endif // KBBSCALABLEGRAPHICWIDGET_H 226