From 947cd1736c250b39a7a03f6bf1d958c1df20f431 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sat, 22 Aug 2009 19:34:48 +0200 Subject: [PATCH 1/8] initial commit for chat channels --- cockatrice/cockatrice.pro | 6 ++- cockatrice/src/chatwidget.cpp | 85 ++++++++++++++++++++++++++++++ cockatrice/src/chatwidget.h | 38 +++++++++++++ cockatrice/src/client.cpp | 22 ++++++++ cockatrice/src/client.h | 5 ++ cockatrice/src/game.cpp | 5 +- cockatrice/src/gameselector.cpp | 26 ++++++--- cockatrice/src/gameselector.h | 2 + cockatrice/src/gamesmodel.cpp | 2 + cockatrice/src/gamesmodel.h | 2 +- cockatrice/src/servereventdata.cpp | 82 +++++++++++++++------------- cockatrice/src/servereventdata.h | 36 +++++++++---- cockatrice/src/window_main.cpp | 16 ++++-- cockatrice/src/window_main.h | 4 ++ servatrice/servatrice.pro | 6 ++- servatrice/src/chatchannel.cpp | 39 ++++++++++++++ servatrice/src/chatchannel.h | 25 +++++++++ servatrice/src/returnmessage.cpp | 1 + servatrice/src/returnmessage.h | 2 +- servatrice/src/server.cpp | 4 ++ servatrice/src/server.h | 3 ++ servatrice/src/serversocket.cpp | 55 +++++++++++++++++++ servatrice/src/serversocket.h | 8 ++- 23 files changed, 408 insertions(+), 66 deletions(-) create mode 100644 cockatrice/src/chatwidget.cpp create mode 100644 cockatrice/src/chatwidget.h create mode 100644 servatrice/src/chatchannel.cpp create mode 100644 servatrice/src/chatchannel.h diff --git a/cockatrice/cockatrice.pro b/cockatrice/cockatrice.pro index e24a899d..c3cc92a7 100644 --- a/cockatrice/cockatrice.pro +++ b/cockatrice/cockatrice.pro @@ -44,7 +44,8 @@ HEADERS += src/counter.h \ src/window_sets.h \ src/abstractgraphicsitem.h \ src/dlg_settings.h \ - src/phasestoolbar.h + src/phasestoolbar.h \ + src/chatwidget.h SOURCES += src/counter.cpp \ src/gameselector.cpp \ src/dlg_creategame.cpp \ @@ -82,5 +83,6 @@ SOURCES += src/counter.cpp \ src/window_sets.cpp \ src/abstractgraphicsitem.cpp \ src/dlg_settings.cpp \ - src/phasestoolbar.cpp + src/phasestoolbar.cpp \ + src/chatwidget.cpp TRANSLATIONS += translations/cockatrice_de.ts translations/cockatrice_en.ts diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp new file mode 100644 index 00000000..3d044d58 --- /dev/null +++ b/cockatrice/src/chatwidget.cpp @@ -0,0 +1,85 @@ +#include +#include "chatwidget.h" +#include "client.h" + +ChannelWidget::ChannelWidget(QWidget *parent) + : QWidget(parent) +{ + playerList = new QListWidget; + + textEdit = new QTextEdit; + sayEdit = new QLineEdit; + + QVBoxLayout *vbox = new QVBoxLayout; + vbox->addWidget(textEdit); + vbox->addWidget(sayEdit); + + QHBoxLayout *hbox = new QHBoxLayout; + hbox->addLayout(vbox); + hbox->addWidget(playerList); + + setLayout(hbox); +} + +ChatWidget::ChatWidget(Client *_client, QWidget *parent) + : QWidget(parent), client(_client) +{ + channelList = new QTreeWidget; + tab = new QTabWidget; + + QHBoxLayout *hbox = new QHBoxLayout; + hbox->addWidget(channelList); + hbox->addWidget(tab, 1); + + retranslateUi(); + setLayout(hbox); +} + +void ChatWidget::retranslateUi() +{ + QTreeWidgetItem *header = channelList->headerItem(); + Q_ASSERT(header != 0); + header->setText(0, tr("Channel")); + header->setText(1, tr("Description")); + header->setText(2, tr("Players")); +} + +void ChatWidget::enableChat() +{ + connect(client, SIGNAL(chatEvent(const ChatEventData &)), this, SLOT(chatEvent(const ChatEventData &))); + client->chatListChannels(); + show(); +} + +void ChatWidget::disableChat() +{ + disconnect(client, 0, this, 0); + hide(); +} + +void ChatWidget::chatEvent(const ChatEventData &data) +{ + const QStringList &msg = data.getEventData(); + switch (data.getEventType()) { + case eventChatListChannels: { + if (msg.size() != 3) + break; + channelList->addTopLevelItem(new QTreeWidgetItem(QStringList() << msg[0] << msg[1] << msg[2])); + break; + } + case eventChatJoinChannel: { + break; + } + case eventChatListPlayers: { + break; + } + case eventChatLeaveChannel: { + break; + } + case eventChatSay: { + break; + } + default: { + } + } +} diff --git a/cockatrice/src/chatwidget.h b/cockatrice/src/chatwidget.h new file mode 100644 index 00000000..3f1a6353 --- /dev/null +++ b/cockatrice/src/chatwidget.h @@ -0,0 +1,38 @@ +#ifndef CHATWIDGET_H +#define CHATWIDGET_H + +#include +#include "servereventdata.h" + +class QListWidget; +class QTextEdit; +class QLineEdit; +class QTreeWidget; +class QTabWidget; +class Client; + +class ChannelWidget : public QWidget { +private: + QListWidget *playerList; + QTextEdit *textEdit; + QLineEdit *sayEdit; +public: + ChannelWidget(QWidget *parent = 0); +}; + +class ChatWidget : public QWidget { + Q_OBJECT +private: + QTreeWidget *channelList; + QTabWidget *tab; + Client *client; +private slots: + void chatEvent(const ChatEventData &data); +public: + ChatWidget(Client *_client, QWidget *parent = 0); + void retranslateUi(); + void enableChat(); + void disableChat(); +}; + +#endif diff --git a/cockatrice/src/client.cpp b/cockatrice/src/client.cpp index 1e05f3f7..cd8407c3 100644 --- a/cockatrice/src/client.cpp +++ b/cockatrice/src/client.cpp @@ -110,6 +110,8 @@ void Client::readLine() emit playerIdReceived(id, data[1]); } else emit gameEvent(event); + } else if (prefix == "chat") { + emit chatEvent(ChatEventData(line)); } else if (prefix == "resp") { if (values.size() != 2) { // XXX @@ -231,6 +233,26 @@ void Client::ping() cmd("ping"); } +PendingCommand *Client::chatListChannels() +{ + return cmd("chat_list_channels"); +} + +PendingCommand *Client::chatJoinChannel(const QString &name) +{ + return cmd(QString("chat_join_channel|%1").arg(name)); +} + +PendingCommand *Client::chatLeaveChannel(const QString &name) +{ + return cmd(QString("chat_leave_channel|%1").arg(name)); +} + +PendingCommand *Client::chatSay(const QString &channel, const QString &s) +{ + return cmd(QString("chat_say|%1|%2").arg(channel).arg(s)); +} + PendingCommand *Client::listGames() { return cmd("list_games"); diff --git a/cockatrice/src/client.h b/cockatrice/src/client.h index 8939fd38..4abde05e 100644 --- a/cockatrice/src/client.h +++ b/cockatrice/src/client.h @@ -57,6 +57,7 @@ signals: void responseReceived(int msgid, ServerResponse resp); void playerIdReceived(int id, QString name); void gameEvent(const ServerEventData &msg); + void chatEvent(const ChatEventData &msg); void serverTimeout(); void logSocketError(const QString &errorString); void serverError(ServerResponse resp); @@ -90,6 +91,10 @@ public: void connectToServer(const QString &hostname, unsigned int port, const QString &_playerName, const QString &_password); void disconnectFromServer(); public slots: + PendingCommand *chatListChannels(); + PendingCommand *chatJoinChannel(const QString &name); + PendingCommand *chatLeaveChannel(const QString &name); + PendingCommand *chatSay(const QString &name, const QString &s); PendingCommand *listGames(); PendingCommand *listPlayers(); PendingCommand *createGame(const QString &description, const QString &password, unsigned int maxPlayers); diff --git a/cockatrice/src/game.cpp b/cockatrice/src/game.cpp index 12ba6aee..f3638983 100644 --- a/cockatrice/src/game.cpp +++ b/cockatrice/src/game.cpp @@ -300,9 +300,12 @@ void Game::gameEvent(const ServerEventData &msg) p->gameEvent(msg); break; } - case eventInvalid: + case eventInvalid: { qDebug("Unhandled global event"); } + default: { + } + } } } diff --git a/cockatrice/src/gameselector.cpp b/cockatrice/src/gameselector.cpp index 02891695..7616f8a4 100644 --- a/cockatrice/src/gameselector.cpp +++ b/cockatrice/src/gameselector.cpp @@ -27,18 +27,13 @@ GameSelector::GameSelector(Client *_client, QWidget *parent) connect(createButton, SIGNAL(clicked()), this, SLOT(actCreate())); connect(joinButton, SIGNAL(clicked()), this, SLOT(actJoin())); - - connect(client, SIGNAL(gameListEvent(ServerGame *)), gameListModel, SLOT(updateGameList(ServerGame *))); - connect(client, SIGNAL(statusChanged(ProtocolStatus)), this, SLOT(statusChanged(ProtocolStatus))); - - client->listGames(); } void GameSelector::actCreate() { DlgCreateGame dlg(client, this); if (dlg.exec()) - deleteLater(); + disableGameList(); } void GameSelector::actRefresh() @@ -49,7 +44,7 @@ void GameSelector::actRefresh() void GameSelector::statusChanged(ProtocolStatus status) { if (status == StatusDisconnected) - deleteLater(); + disableGameList(); } void GameSelector::checkResponse(ServerResponse response) @@ -58,7 +53,7 @@ void GameSelector::checkResponse(ServerResponse response) joinButton->setEnabled(true); if (response == RespOk) - deleteLater(); + disableGameList(); else { QMessageBox::critical(this, tr("Error"), tr("XXX")); return; @@ -84,3 +79,18 @@ void GameSelector::actJoin() createButton->setEnabled(false); joinButton->setEnabled(false); } + +void GameSelector::enableGameList() +{ + connect(client, SIGNAL(gameListEvent(ServerGame *)), gameListModel, SLOT(updateGameList(ServerGame *))); + connect(client, SIGNAL(statusChanged(ProtocolStatus)), this, SLOT(statusChanged(ProtocolStatus))); + client->listGames(); + show(); +} + +void GameSelector::disableGameList() +{ + disconnect(client, 0, this, 0); + hide(); + gameListModel->cleanList(); +} diff --git a/cockatrice/src/gameselector.h b/cockatrice/src/gameselector.h index 2d4b447c..b8937ad3 100644 --- a/cockatrice/src/gameselector.h +++ b/cockatrice/src/gameselector.h @@ -13,6 +13,8 @@ class GameSelector : public QWidget { Q_OBJECT public: GameSelector(Client *_client, QWidget *parent = 0); + void enableGameList(); + void disableGameList(); private slots: void actCreate(); void actRefresh(); diff --git a/cockatrice/src/gamesmodel.cpp b/cockatrice/src/gamesmodel.cpp index cf542c44..848b6ce0 100644 --- a/cockatrice/src/gamesmodel.cpp +++ b/cockatrice/src/gamesmodel.cpp @@ -69,8 +69,10 @@ void GamesModel::updateGameList(ServerGame *game) void GamesModel::cleanList() { + beginRemoveRows(QModelIndex(), 0, gameList.size() - 1); QListIterator i(gameList); while (i.hasNext()) delete i.next(); gameList.clear(); + endRemoveRows(); } diff --git a/cockatrice/src/gamesmodel.h b/cockatrice/src/gamesmodel.h index 545939ba..ef352fb9 100644 --- a/cockatrice/src/gamesmodel.h +++ b/cockatrice/src/gamesmodel.h @@ -16,11 +16,11 @@ public: QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const; ServerGame *getGame(int row); + void cleanList(); public slots: void updateGameList(ServerGame *game); private: QList gameList; - void cleanList(); }; #endif diff --git a/cockatrice/src/servereventdata.cpp b/cockatrice/src/servereventdata.cpp index cf7ba9f4..df97bf60 100644 --- a/cockatrice/src/servereventdata.cpp +++ b/cockatrice/src/servereventdata.cpp @@ -3,49 +3,57 @@ // Message structure for server events: // {"private","public"}|PlayerId|PlayerName|EventType|EventData -const int event_count = 21; -const event_string event_strings[event_count] = { - {eventPlayerId, "player_id"}, - {eventSay, "say"}, - {eventName, "name"}, - {eventJoin, "join"}, - {eventLeave, "leave"}, - {eventReadyStart, "ready_start"}, - {eventSetupZones, "setup_zones"}, - {eventGameStart, "game_start"}, - {eventShuffle, "shuffle"}, - {eventRollDice, "roll_dice"}, - {eventDraw, "draw"}, - {eventMoveCard, "move_card"}, - {eventCreateToken, "create_token"}, - {eventSetCardAttr, "set_card_attr"}, - {eventAddCounter, "add_counter"}, - {eventSetCounter, "set_counter"}, - {eventDelCounter, "del_counter"}, - {eventSetActivePlayer, "set_active_player"}, - {eventSetActivePhase, "set_active_phase"}, - {eventDumpZone, "dump_zone"}, - {eventStopDumpZone, "stop_dump_zone"} -}; +QHash ServerEventData::eventHash; ServerEventData::ServerEventData(const QString &line) { - QStringList values = line.split("|"); + if (eventHash.isEmpty()) { + eventHash.insert("player_id", eventPlayerId); + eventHash.insert("say", eventSay); + eventHash.insert("name", eventName); + eventHash.insert("join", eventJoin); + eventHash.insert("leave", eventLeave); + eventHash.insert("ready_start", eventReadyStart); + eventHash.insert("setup_zones", eventSetupZones); + eventHash.insert("game_start", eventGameStart); + eventHash.insert("shuffle", eventShuffle); + eventHash.insert("roll_dice", eventRollDice); + eventHash.insert("draw", eventDraw); + eventHash.insert("move_card", eventMoveCard); + eventHash.insert("create_token", eventCreateToken); + eventHash.insert("set_card_attr", eventSetCardAttr); + eventHash.insert("add_counter", eventAddCounter); + eventHash.insert("set_counter", eventSetCounter); + eventHash.insert("del_counter", eventDelCounter); + eventHash.insert("set_active_player", eventSetActivePlayer); + eventHash.insert("set_active_phase", eventSetActivePhase); + eventHash.insert("dump_zone", eventDumpZone); + eventHash.insert("stop_dump_zone", eventStopDumpZone); + } + + QStringList values = line.split('|'); IsPublic = !values.takeFirst().compare("public"); PlayerId = values.takeFirst().toInt(); PlayerName = values.takeFirst(); - - QString type = values.takeFirst(); - bool found = false; - for (int i = 0; i < event_count; i++) - if (!type.compare(event_strings[i].str)) { - EventType = event_strings[i].type; - found = true; - break; - } - if (!found) - EventType = eventInvalid; - + EventType = eventHash.value(values.takeFirst(), eventInvalid); EventData = values; } + +QHash ChatEventData::eventHash; + +ChatEventData::ChatEventData(const QString &line) +{ + if (eventHash.isEmpty()) { + eventHash.insert("list_channels", eventChatListChannels); + eventHash.insert("join_channel", eventChatJoinChannel); + eventHash.insert("list_players", eventChatListPlayers); + eventHash.insert("leave_channel", eventChatLeaveChannel); + eventHash.insert("say", eventChatSay); + } + + QStringList values = line.split('|'); + values.removeFirst(); + eventType = eventHash.value(values.takeFirst(), eventChatInvalid); + eventData = values; +} diff --git a/cockatrice/src/servereventdata.h b/cockatrice/src/servereventdata.h index f471fc22..50233af5 100644 --- a/cockatrice/src/servereventdata.h +++ b/cockatrice/src/servereventdata.h @@ -2,6 +2,7 @@ #define SERVEREVENTDATA_H #include +#include enum ServerEventType { eventInvalid, @@ -28,16 +29,10 @@ enum ServerEventType { eventStopDumpZone }; -struct event_string { - ServerEventType type; - char *str; -}; - -extern const int event_count; -extern const event_string event_strings[]; - class ServerEventData { private: + static QHash eventHash; + bool IsPublic; int PlayerId; QString PlayerName; @@ -47,9 +42,30 @@ public: ServerEventData(const QString &line); bool getPublic() const { return IsPublic; } int getPlayerId() const { return PlayerId; } - QString getPlayerName() const { return PlayerName; } + const QString &getPlayerName() const { return PlayerName; } ServerEventType getEventType() const { return EventType; } - QStringList getEventData() const { return EventData; } + const QStringList &getEventData() const { return EventData; } +}; + +enum ChatEventType { + eventChatInvalid, + eventChatListChannels, + eventChatJoinChannel, + eventChatListPlayers, + eventChatLeaveChannel, + eventChatSay +}; + +class ChatEventData { +private: + static QHash eventHash; + + ChatEventType eventType; + QStringList eventData; +public: + ChatEventData(const QString &line); + ChatEventType getEventType() const { return eventType; } + const QStringList &getEventData() const { return eventData; } }; #endif diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index fc7696d2..4e1b1f54 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -35,6 +35,7 @@ #include "zoneviewzone.h" #include "zoneviewwidget.h" #include "zoneviewlayout.h" +#include "chatwidget.h" void MainWindow::hoverCard(QString name) { @@ -86,8 +87,8 @@ void MainWindow::statusChanged(ProtocolStatus _status) phasesToolbar->setActivePhase(-1); phasesToolbar->setEnabled(false); - GameSelector *gameSelector = new GameSelector(client); - viewLayout->insertWidget(0, gameSelector); + gameSelector->enableGameList(); + chatWidget->enableChat(); break; } case StatusPlaying: @@ -211,6 +212,7 @@ void MainWindow::retranslateUi() sayLabel->setText(tr("&Say:")); cardInfo->retranslateUi(); + chatWidget->retranslateUi(); } void MainWindow::createActions() @@ -272,6 +274,7 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) scene = new QGraphicsScene(0, 0, 1096, 1160, this); view = new GameView(scene); + view->hide(); // view->setViewport(new QGLWidget(QGLFormat(QGL::SampleBuffers))); @@ -285,6 +288,12 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) sayLabel = new QLabel; sayEdit = new QLineEdit; sayLabel->setBuddy(sayEdit); + + client = new Client(this); + gameSelector = new GameSelector(client); + gameSelector->hide(); + chatWidget = new ChatWidget(client); + chatWidget->hide(); QHBoxLayout *hLayout = new QHBoxLayout; hLayout->addWidget(sayLabel); @@ -296,6 +305,8 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) verticalLayout->addLayout(hLayout); viewLayout = new QVBoxLayout; + viewLayout->addWidget(gameSelector); + viewLayout->addWidget(chatWidget); viewLayout->addWidget(view); phasesToolbar = new PhasesToolbar; @@ -312,7 +323,6 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) connect(sayEdit, SIGNAL(returnPressed()), this, SLOT(actSay())); - client = new Client(this); connect(client, SIGNAL(serverTimeout()), this, SLOT(serverTimeout())); connect(client, SIGNAL(statusChanged(ProtocolStatus)), this, SLOT(statusChanged(ProtocolStatus))); connect(client, SIGNAL(playerIdReceived(int, QString)), this, SLOT(playerIdReceived(int, QString))); diff --git a/cockatrice/src/window_main.h b/cockatrice/src/window_main.h index 460ca2bc..39f821e5 100644 --- a/cockatrice/src/window_main.h +++ b/cockatrice/src/window_main.h @@ -40,6 +40,8 @@ class ServerZoneCard; class ZoneViewLayout; class ZoneViewWidget; class PhasesToolbar; +class GameSelector; +class ChatWidget; class MainWindow : public QMainWindow { Q_OBJECT @@ -80,6 +82,8 @@ private: QLabel *sayLabel; QLineEdit *sayEdit; PhasesToolbar *phasesToolbar; + GameSelector *gameSelector; + ChatWidget *chatWidget; Client *client; QGraphicsScene *scene; diff --git a/servatrice/servatrice.pro b/servatrice/servatrice.pro index 626dc610..89d87379 100755 --- a/servatrice/servatrice.pro +++ b/servatrice/servatrice.pro @@ -21,7 +21,8 @@ HEADERS += src/server.h src/servergame.h src/serversocket.h \ src/counter.h \ src/abstractrng.h \ src/rng_qt.h \ - src/returnmessage.h + src/returnmessage.h \ + src/chatchannel.h SOURCES += src/main.cpp \ src/server.cpp \ src/servergame.cpp \ @@ -30,4 +31,5 @@ SOURCES += src/main.cpp \ src/card.cpp \ src/counter.cpp \ src/rng_qt.cpp \ - src/returnmessage.cpp + src/returnmessage.cpp \ + src/chatchannel.cpp diff --git a/servatrice/src/chatchannel.cpp b/servatrice/src/chatchannel.cpp new file mode 100644 index 00000000..f8f1528e --- /dev/null +++ b/servatrice/src/chatchannel.cpp @@ -0,0 +1,39 @@ +#include "chatchannel.h" +#include "serversocket.h" + +ChatChannel::ChatChannel(const QString &_name, const QString &_description) + : name(_name), description(_description) +{ +} + +void ChatChannel::addPlayer(ServerSocket *player) +{ + QString str = QString("chat|join_channel|%1|%2").arg(name).arg(player->getPlayerName()); + for (int i = 0; i < size(); ++i) + at(i)->msg(str); + + append(player); + + for (int i = 0; i < size(); ++i) + player->msg(QString("chat|list_players|%1|%2").arg(name).arg(at(i)->getPlayerName())); + + emit channelInfoChanged(); +} + +void ChatChannel::removePlayer(ServerSocket *player) +{ + QString str = QString("chat|leave_channel|%1|%2").arg(name).arg(player->getPlayerName()); + + removeAt(indexOf(player)); + for (int i = 0; i < size(); ++i) + at(i)->msg(str); + + emit channelInfoChanged(); +} + +void ChatChannel::say(ServerSocket *player, const QString &s) +{ + QString str = QString("chat|say|%1|%2|%3").arg(name).arg(player->getPlayerName()).arg(s); + for (int i = 0; i < size(); ++i) + at(i)->msg(str); +} diff --git a/servatrice/src/chatchannel.h b/servatrice/src/chatchannel.h new file mode 100644 index 00000000..822b8489 --- /dev/null +++ b/servatrice/src/chatchannel.h @@ -0,0 +1,25 @@ +#ifndef CHATCHANNEL_H +#define CHATCHANNEL_H + +#include +#include + +class ServerSocket; + +class ChatChannel : public QObject, public QList { + Q_OBJECT +signals: + void channelInfoChanged(); +private: + QString name; + QString description; +public: + ChatChannel(const QString &_name, const QString &_description); + QString getName() const { return name; } + QString getDescription() const { return description; } + void addPlayer(ServerSocket *player); + void removePlayer(ServerSocket *player); + void say(ServerSocket *player, const QString &s); +}; + +#endif diff --git a/servatrice/src/returnmessage.cpp b/servatrice/src/returnmessage.cpp index 210f2644..14d1eca3 100644 --- a/servatrice/src/returnmessage.cpp +++ b/servatrice/src/returnmessage.cpp @@ -10,6 +10,7 @@ bool ReturnMessage::send(ReturnCode code) switch (code) { case ReturnNothing: return true; case ReturnOk: returnCodeString = "ok"; break; + case ReturnNameNotFound: returnCodeString = "name_not_found"; break; case ReturnLoginNeeded: returnCodeString = "login_needed"; break; case ReturnSyntaxError: returnCodeString = "syntax"; break; case ReturnContextError: returnCodeString = "context"; break; diff --git a/servatrice/src/returnmessage.h b/servatrice/src/returnmessage.h index 37837bca..58a464a1 100644 --- a/servatrice/src/returnmessage.h +++ b/servatrice/src/returnmessage.h @@ -9,7 +9,7 @@ private: unsigned int msg_id; QString cmd; public: - enum ReturnCode { ReturnNothing, ReturnOk, ReturnLoginNeeded, ReturnSyntaxError, ReturnContextError, ReturnPasswordWrong }; + enum ReturnCode { ReturnNothing, ReturnOk, ReturnNameNotFound, ReturnLoginNeeded, ReturnSyntaxError, ReturnContextError, ReturnPasswordWrong }; ReturnMessage(QObject *parent = 0) : QObject(parent), msg_id(0) { } unsigned int getMsgId() const { return msg_id; } void setMsgId(unsigned int _msg_id) { msg_id = _msg_id; } diff --git a/servatrice/src/server.cpp b/servatrice/src/server.cpp index b8aa8c9a..3b477a69 100644 --- a/servatrice/src/server.cpp +++ b/servatrice/src/server.cpp @@ -22,6 +22,7 @@ #include "serversocket.h" #include "counter.h" #include "rng_qt.h" +#include "chatchannel.h" #include #include @@ -35,6 +36,9 @@ Server::Server(QObject *parent) QString dbType = settings->value("database/type").toString(); if (dbType == "mysql") openDatabase(); + + chatChannelList << new ChatChannel("channel1", "testchannel 1"); + chatChannelList << new ChatChannel("channel2", "testchannel 2"); } Server::~Server() diff --git a/servatrice/src/server.h b/servatrice/src/server.h index 467f62e9..299a0d7a 100644 --- a/servatrice/src/server.h +++ b/servatrice/src/server.h @@ -27,6 +27,7 @@ class ServerSocket; class QSqlDatabase; class QSettings; class AbstractRNG; +class ChatChannel; enum AuthenticationResult { PasswordWrong = 0, PasswordRight = 1, UnknownUser = 2 }; @@ -45,6 +46,7 @@ public: bool checkGamePassword(int gameId, const QString &password); AuthenticationResult checkUserPassword(const QString &user, const QString &password); QList listOpenGames(); + QList getChatChannelList() { return chatChannelList; } ServerGame *getGame(int gameId); AbstractRNG *getRNG() const { return rng; } void broadcastGameListUpdate(ServerGame *game); @@ -53,6 +55,7 @@ private: void incomingConnection(int SocketId); QList games; QList players; + QList chatChannelList; int nextGameId; AbstractRNG *rng; }; diff --git a/servatrice/src/serversocket.cpp b/servatrice/src/serversocket.cpp index d16157e0..dbc393b9 100644 --- a/servatrice/src/serversocket.cpp +++ b/servatrice/src/serversocket.cpp @@ -28,6 +28,7 @@ #include "counter.h" #include "card.h" #include "abstractrng.h" +#include "chatchannel.h" ServerSocket::ServerSocket(Server *_server, QObject *parent) : QTcpSocket(parent), server(_server), game(0), PlayerStatus(StatusNormal), authState(PasswordWrong), acceptsGameListChanges(false) @@ -166,6 +167,11 @@ const ServerSocket::CommandProperties ServerSocket::commandList[ServerSocket::nu {"ping", false, false, false, QList(), &ServerSocket::cmdPing}, {"login", false, false, false, QList() << QVariant::String << QVariant::String, &ServerSocket::cmdLogin}, + {"chat_list_channels", true, false, false, QList(), &ServerSocket::cmdChatListChannels}, + {"chat_join_channel", true, false, false, QList() << QVariant::String, &ServerSocket::cmdChatJoinChannel}, + {"chat_leave_channel", true, false, false, QList() << QVariant::String, &ServerSocket::cmdChatLeaveChannel}, + {"chat_say", true, false, false, QList() << QVariant::String + << QVariant::String, &ServerSocket::cmdChatSay}, {"list_games", true, false, false, QList(), &ServerSocket::cmdListGames}, {"create_game", true, false, false, QList() << QVariant::String << QVariant::String @@ -231,6 +237,55 @@ ReturnMessage::ReturnCode ServerSocket::cmdLogin(const QList ¶ms) return ReturnMessage::ReturnOk; } +ReturnMessage::ReturnCode ServerSocket::cmdChatListChannels(const QList &/*params*/) +{ + QList chatChannelList = server->getChatChannelList(); + for (int i = 0; i < chatChannelList.size(); ++i) + msg(QString("chat|list_channels|%1|%2|%3").arg(chatChannelList[i]->getName()).arg(chatChannelList[i]->getDescription()).arg(chatChannelList[i]->size())); + + acceptsChatChannelListChanges = true; + return ReturnMessage::ReturnOk; +} + +ReturnMessage::ReturnCode ServerSocket::cmdChatJoinChannel(const QList ¶ms) +{ + for (int i = 0; i < chatChannels.size(); ++i) + if (chatChannels[i]->getName() == params[0]) + return ReturnMessage::ReturnContextError; + + QList allChannels = server->getChatChannelList(); + for (int i = 0; i < allChannels.size(); ++i) + if (allChannels[i]->getName() == params[0]) { + allChannels[i]->addPlayer(this); + chatChannels << allChannels[i]; + return ReturnMessage::ReturnOk; + } + return ReturnMessage::ReturnNameNotFound; +} + +ReturnMessage::ReturnCode ServerSocket::cmdChatLeaveChannel(const QList ¶ms) +{ + for (int i = 0; i < chatChannels.size(); ++i) { + ChatChannel *c = chatChannels[i]; + if (c->getName() == params[0]) { + chatChannels.removeAt(i); + c->removePlayer(this); + return ReturnMessage::ReturnOk; + } + } + return ReturnMessage::ReturnNameNotFound; +} + +ReturnMessage::ReturnCode ServerSocket::cmdChatSay(const QList ¶ms) +{ + for (int i = 0; i < chatChannels.size(); ++i) + if (chatChannels[i]->getName() == params[0]) { + chatChannels[i]->say(this, params[1].toString()); + return ReturnMessage::ReturnOk; + } + return ReturnMessage::ReturnNameNotFound; +} + ReturnMessage::ReturnCode ServerSocket::cmdListGames(const QList &/*params*/) { QList gameList = server->listOpenGames(); diff --git a/servatrice/src/serversocket.h b/servatrice/src/serversocket.h index 1b7b1874..5aee3148 100644 --- a/servatrice/src/serversocket.h +++ b/servatrice/src/serversocket.h @@ -55,11 +55,15 @@ private: QList paramTypes; CommandHandler handler; }; - static const int numberCommands = 27; + static const int numberCommands = 31; static const CommandProperties commandList[numberCommands]; ReturnMessage::ReturnCode cmdPing(const QList ¶ms); ReturnMessage::ReturnCode cmdLogin(const QList ¶ms); + ReturnMessage::ReturnCode cmdChatListChannels(const QList ¶ms); + ReturnMessage::ReturnCode cmdChatJoinChannel(const QList ¶ms); + ReturnMessage::ReturnCode cmdChatLeaveChannel(const QList ¶ms); + ReturnMessage::ReturnCode cmdChatSay(const QList ¶ms); ReturnMessage::ReturnCode cmdListGames(const QList ¶ms); ReturnMessage::ReturnCode cmdCreateGame(const QList ¶ms); ReturnMessage::ReturnCode cmdJoinGame(const QList ¶ms); @@ -88,6 +92,7 @@ private: Server *server; ServerGame *game; + QList chatChannels; QList DeckList; QList SideboardList; QList zones; @@ -105,6 +110,7 @@ private: ReturnMessage *remsg; AuthenticationResult authState; bool acceptsGameListChanges; + bool acceptsChatChannelListChanges; public: ServerSocket(Server *_server, QObject *parent = 0); ~ServerSocket(); From 120193fb0bb30c6c881b0d5e5aee9f62314f5753 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sat, 22 Aug 2009 21:57:03 +0200 Subject: [PATCH 2/8] fixed shuffling, more chat widget code --- cockatrice/src/chatwidget.cpp | 105 ++++++++++++++++++++++++++++++-- cockatrice/src/chatwidget.h | 18 +++++- cockatrice/src/client.h | 3 + cockatrice/src/player.cpp | 2 + cockatrice/src/window_main.cpp | 3 + servatrice/servatrice.pro | 2 +- servatrice/src/chatchannel.cpp | 2 +- servatrice/src/serversocket.cpp | 5 +- 8 files changed, 131 insertions(+), 9 deletions(-) diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp index 3d044d58..22ff1469 100644 --- a/cockatrice/src/chatwidget.cpp +++ b/cockatrice/src/chatwidget.cpp @@ -2,8 +2,8 @@ #include "chatwidget.h" #include "client.h" -ChannelWidget::ChannelWidget(QWidget *parent) - : QWidget(parent) +ChannelWidget::ChannelWidget(const QString &_name, QWidget *parent) + : QWidget(parent), name(_name) { playerList = new QListWidget; @@ -15,20 +15,56 @@ ChannelWidget::ChannelWidget(QWidget *parent) vbox->addWidget(sayEdit); QHBoxLayout *hbox = new QHBoxLayout; - hbox->addLayout(vbox); + hbox->addLayout(vbox, 1); hbox->addWidget(playerList); setLayout(hbox); } +void ChannelWidget::joinEvent(const QString &playerName) +{ + textEdit->append(tr("%1 has joined the channel.").arg(playerName)); + playerList->addItem(playerName); +} + +void ChannelWidget::listPlayersEvent(const QString &playerName) +{ + playerList->addItem(playerName); +} + +void ChannelWidget::leaveEvent(const QString &playerName) +{ + textEdit->append(tr("%1 has left the channel.").arg(playerName)); + for (int i = 0; i < playerList->count(); ++i) + if (playerList->item(i)->text() == playerName) { + delete playerList->takeItem(i); + break; + } +} + +void ChannelWidget::sayEvent(const QString &playerName, const QString &s) +{ + textEdit->append(QString("%1: %2").arg(playerName).arg(s)); +} + ChatWidget::ChatWidget(Client *_client, QWidget *parent) : QWidget(parent), client(_client) { channelList = new QTreeWidget; + + joinButton = new QPushButton; + connect(joinButton, SIGNAL(clicked()), this, SLOT(joinClicked())); + QHBoxLayout *buttonLayout = new QHBoxLayout; + buttonLayout->addStretch(); + buttonLayout->addWidget(joinButton); + QVBoxLayout *leftLayout = new QVBoxLayout; + leftLayout->addWidget(channelList); + leftLayout->addLayout(buttonLayout); + tab = new QTabWidget; QHBoxLayout *hbox = new QHBoxLayout; - hbox->addWidget(channelList); + hbox->addLayout(leftLayout); hbox->addWidget(tab, 1); retranslateUi(); @@ -37,6 +73,8 @@ ChatWidget::ChatWidget(Client *_client, QWidget *parent) void ChatWidget::retranslateUi() { + joinButton->setText(tr("Joi&n")); + QTreeWidgetItem *header = channelList->headerItem(); Q_ASSERT(header != 0); header->setText(0, tr("Channel")); @@ -68,18 +106,77 @@ void ChatWidget::chatEvent(const ChatEventData &data) break; } case eventChatJoinChannel: { + if (msg.size() != 2) + break; + ChannelWidget *w = getChannel(msg[0]); + if (!w) + break; + w->joinEvent(msg[1]); break; } case eventChatListPlayers: { + if (msg.size() != 2) + break; + ChannelWidget *w = getChannel(msg[0]); + if (!w) + break; + w->listPlayersEvent(msg[1]); break; } case eventChatLeaveChannel: { + if (msg.size() != 2) + break; + ChannelWidget *w = getChannel(msg[0]); + if (!w) + break; + w->leaveEvent(msg[1]); break; } case eventChatSay: { + if (msg.size() != 3) + break; + ChannelWidget *w = getChannel(msg[0]); + if (!w) + break; + w->sayEvent(msg[1], msg[2]); break; } default: { } } } + +void ChatWidget::joinClicked() +{ + QTreeWidgetItem *twi = channelList->currentItem(); + if (!twi) + return; + QString channelName = twi->text(0); + if (getChannel(channelName)) + return; + + PendingCommand *pc = client->chatJoinChannel(channelName); + pc->setExtraData(channelName); + connect(pc, SIGNAL(finished(ServerResponse)), this, SLOT(joinFinished(ServerResponse))); +} + +void ChatWidget::joinFinished(ServerResponse resp) +{ + if (resp != RespOk) + return; + + PendingCommand *pc = qobject_cast(sender()); + QString channelName = pc->getExtraData(); + ChannelWidget *cw = new ChannelWidget(channelName); + tab->addTab(cw, channelName); +} + +ChannelWidget *ChatWidget::getChannel(const QString &name) +{ + for (int i = 0; i < tab->count(); ++i) { + ChannelWidget *cw = qobject_cast(tab->widget(i)); + if (cw->getName() == name) + return cw; + } + return 0; +} diff --git a/cockatrice/src/chatwidget.h b/cockatrice/src/chatwidget.h index 3f1a6353..12178cdb 100644 --- a/cockatrice/src/chatwidget.h +++ b/cockatrice/src/chatwidget.h @@ -3,31 +3,45 @@ #include #include "servereventdata.h" +#include "client.h" class QListWidget; class QTextEdit; class QLineEdit; class QTreeWidget; class QTabWidget; -class Client; +class QPushButton; class ChannelWidget : public QWidget { + Q_OBJECT private: QListWidget *playerList; QTextEdit *textEdit; QLineEdit *sayEdit; + QString name; public: - ChannelWidget(QWidget *parent = 0); + ChannelWidget(const QString &_name, QWidget *parent = 0); + const QString &getName() const { return name; } + + void joinEvent(const QString &playerName); + void listPlayersEvent(const QString &playerName); + void leaveEvent(const QString &playerName); + void sayEvent(const QString &playerName, const QString &s); }; class ChatWidget : public QWidget { Q_OBJECT private: QTreeWidget *channelList; + QPushButton *joinButton; QTabWidget *tab; Client *client; + + ChannelWidget *getChannel(const QString &name); private slots: void chatEvent(const ChatEventData &data); + void joinClicked(); + void joinFinished(ServerResponse resp); public: ChatWidget(Client *_client, QWidget *parent = 0); void retranslateUi(); diff --git a/cockatrice/src/client.h b/cockatrice/src/client.h index 4abde05e..9aac7c76 100644 --- a/cockatrice/src/client.h +++ b/cockatrice/src/client.h @@ -33,6 +33,7 @@ private: QString cmd; int msgid; int time; + QString extraData; signals: void finished(ServerResponse resp); void timeout(); @@ -42,6 +43,8 @@ public slots: public: int getMsgId() const { return msgid; } QString getCmd() const { return cmd; } + const QString &getExtraData() const { return extraData; } + void setExtraData(const QString &_extraData) { extraData = _extraData; } PendingCommand(const QString &_cmd, int _msgid, QObject *parent = 0); }; diff --git a/cockatrice/src/player.cpp b/cockatrice/src/player.cpp index 22c66602..36b039d0 100644 --- a/cockatrice/src/player.cpp +++ b/cockatrice/src/player.cpp @@ -64,6 +64,8 @@ Player::Player(const QString &_name, int _id, QPointF _base, bool _local, CardDa libraryMenu->addAction(aDrawCard); libraryMenu->addAction(aDrawCards); libraryMenu->addSeparator(); + libraryMenu->addAction(aShuffle); + libraryMenu->addSeparator(); libraryMenu->addAction(aViewLibrary); libraryMenu->addAction(aViewTopCards); zones.findZone("deck")->setMenu(libraryMenu, aDrawCard); diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index 4e1b1f54..412e8d44 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -87,12 +87,15 @@ void MainWindow::statusChanged(ProtocolStatus _status) phasesToolbar->setActivePhase(-1); phasesToolbar->setEnabled(false); + view->hide(); gameSelector->enableGameList(); chatWidget->enableChat(); break; } case StatusPlaying: + chatWidget->disableChat(); phasesToolbar->setEnabled(true); + view->show(); break; default: break; diff --git a/servatrice/servatrice.pro b/servatrice/servatrice.pro index 89d87379..120d7a42 100755 --- a/servatrice/servatrice.pro +++ b/servatrice/servatrice.pro @@ -9,7 +9,7 @@ INCLUDEPATH += . src MOC_DIR = build OBJECTS_DIR = build -# CONFIG += qt debug +CONFIG += qt debug QT += network sql QT -= gui diff --git a/servatrice/src/chatchannel.cpp b/servatrice/src/chatchannel.cpp index f8f1528e..5f33793b 100644 --- a/servatrice/src/chatchannel.cpp +++ b/servatrice/src/chatchannel.cpp @@ -11,7 +11,7 @@ void ChatChannel::addPlayer(ServerSocket *player) QString str = QString("chat|join_channel|%1|%2").arg(name).arg(player->getPlayerName()); for (int i = 0; i < size(); ++i) at(i)->msg(str); - + append(player); for (int i = 0; i < size(); ++i) diff --git a/servatrice/src/serversocket.cpp b/servatrice/src/serversocket.cpp index dbc393b9..824f6d90 100644 --- a/servatrice/src/serversocket.cpp +++ b/servatrice/src/serversocket.cpp @@ -48,6 +48,8 @@ ServerSocket::~ServerSocket() server->removePlayer(this); if (game) game->removePlayer(this); + for (int i = 0; i < chatChannels.size(); ++i) + chatChannels[i]->removePlayer(this); } int ServerSocket::newCardId() @@ -256,9 +258,10 @@ ReturnMessage::ReturnCode ServerSocket::cmdChatJoinChannel(const QList QList allChannels = server->getChatChannelList(); for (int i = 0; i < allChannels.size(); ++i) if (allChannels[i]->getName() == params[0]) { + remsg->send(ReturnMessage::ReturnOk); allChannels[i]->addPlayer(this); chatChannels << allChannels[i]; - return ReturnMessage::ReturnOk; + return ReturnMessage::ReturnNothing; } return ReturnMessage::ReturnNameNotFound; } From e6a419aa3d5cb03da55f57e08f78a6bddcea8bdf Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 03:43:09 +0200 Subject: [PATCH 3/8] chat code --- cockatrice/src/chatwidget.cpp | 24 +++++++++++++++++++++--- cockatrice/src/chatwidget.h | 5 ++++- cockatrice/src/window_main.cpp | 8 ++++---- servatrice/src/chatchannel.cpp | 5 +++++ servatrice/src/chatchannel.h | 1 + servatrice/src/server.cpp | 11 +++++++++++ servatrice/src/server.h | 1 + servatrice/src/serversocket.cpp | 4 +++- servatrice/src/serversocket.h | 1 + 9 files changed, 51 insertions(+), 9 deletions(-) diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp index 22ff1469..ad1f3b34 100644 --- a/cockatrice/src/chatwidget.cpp +++ b/cockatrice/src/chatwidget.cpp @@ -2,13 +2,15 @@ #include "chatwidget.h" #include "client.h" -ChannelWidget::ChannelWidget(const QString &_name, QWidget *parent) - : QWidget(parent), name(_name) +ChannelWidget::ChannelWidget(Client *_client, const QString &_name, QWidget *parent) + : QWidget(parent), client(_client), name(_name) { playerList = new QListWidget; textEdit = new QTextEdit; + textEdit->setReadOnly(true); sayEdit = new QLineEdit; + connect(sayEdit, SIGNAL(returnPressed()), this, SLOT(sendMessage())); QVBoxLayout *vbox = new QVBoxLayout; vbox->addWidget(textEdit); @@ -21,6 +23,14 @@ ChannelWidget::ChannelWidget(const QString &_name, QWidget *parent) setLayout(hbox); } +void ChannelWidget::sendMessage() +{ + if (sayEdit->text().isEmpty()) + return; + client->chatSay(name, sayEdit->text()); + sayEdit->clear(); +} + void ChannelWidget::joinEvent(const QString &playerName) { textEdit->append(tr("%1 has joined the channel.").arg(playerName)); @@ -102,6 +112,14 @@ void ChatWidget::chatEvent(const ChatEventData &data) case eventChatListChannels: { if (msg.size() != 3) break; + for (int i = 0; i < channelList->topLevelItemCount(); ++i) { + QTreeWidgetItem *twi = channelList->topLevelItem(i); + if (twi->text(0) == msg[0]) { + twi->setText(1, msg[1]); + twi->setText(2, msg[2]); + return; + } + } channelList->addTopLevelItem(new QTreeWidgetItem(QStringList() << msg[0] << msg[1] << msg[2])); break; } @@ -167,7 +185,7 @@ void ChatWidget::joinFinished(ServerResponse resp) PendingCommand *pc = qobject_cast(sender()); QString channelName = pc->getExtraData(); - ChannelWidget *cw = new ChannelWidget(channelName); + ChannelWidget *cw = new ChannelWidget(client, channelName); tab->addTab(cw, channelName); } diff --git a/cockatrice/src/chatwidget.h b/cockatrice/src/chatwidget.h index 12178cdb..94bb8944 100644 --- a/cockatrice/src/chatwidget.h +++ b/cockatrice/src/chatwidget.h @@ -18,9 +18,12 @@ private: QListWidget *playerList; QTextEdit *textEdit; QLineEdit *sayEdit; + Client *client; QString name; +private slots: + void sendMessage(); public: - ChannelWidget(const QString &_name, QWidget *parent = 0); + ChannelWidget(Client *_client, const QString &_name, QWidget *parent = 0); const QString &getName() const { return name; } void joinEvent(const QString &playerName); diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index 412e8d44..d6c6af69 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -70,7 +70,7 @@ void MainWindow::statusChanged(ProtocolStatus _status) aRestartGame->setEnabled(false); aLeaveGame->setEnabled(false); phasesToolbar->setActivePhase(-1); - phasesToolbar->setEnabled(false); + phasesToolbar->hide(); emit logDisconnected(); break; case StatusLoggingIn: @@ -85,7 +85,7 @@ void MainWindow::statusChanged(ProtocolStatus _status) aRestartGame->setEnabled(false); aLeaveGame->setEnabled(false); phasesToolbar->setActivePhase(-1); - phasesToolbar->setEnabled(false); + phasesToolbar->hide(); view->hide(); gameSelector->enableGameList(); @@ -94,7 +94,7 @@ void MainWindow::statusChanged(ProtocolStatus _status) } case StatusPlaying: chatWidget->disableChat(); - phasesToolbar->setEnabled(true); + phasesToolbar->show(); view->show(); break; default: @@ -313,7 +313,7 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) viewLayout->addWidget(view); phasesToolbar = new PhasesToolbar; - phasesToolbar->setEnabled(false); + phasesToolbar->hide(); QHBoxLayout *mainLayout = new QHBoxLayout; mainLayout->addWidget(phasesToolbar); diff --git a/servatrice/src/chatchannel.cpp b/servatrice/src/chatchannel.cpp index 5f33793b..fc621013 100644 --- a/servatrice/src/chatchannel.cpp +++ b/servatrice/src/chatchannel.cpp @@ -37,3 +37,8 @@ void ChatChannel::say(ServerSocket *player, const QString &s) for (int i = 0; i < size(); ++i) at(i)->msg(str); } + +QString ChatChannel::getChannelListLine() const +{ + return QString("chat|list_channels|%1|%2|%3").arg(name).arg(description).arg(size()); +} \ No newline at end of file diff --git a/servatrice/src/chatchannel.h b/servatrice/src/chatchannel.h index 822b8489..fdf254f4 100644 --- a/servatrice/src/chatchannel.h +++ b/servatrice/src/chatchannel.h @@ -20,6 +20,7 @@ public: void addPlayer(ServerSocket *player); void removePlayer(ServerSocket *player); void say(ServerSocket *player, const QString &s); + QString getChannelListLine() const; }; #endif diff --git a/servatrice/src/server.cpp b/servatrice/src/server.cpp index 3b477a69..30a0cd53 100644 --- a/servatrice/src/server.cpp +++ b/servatrice/src/server.cpp @@ -39,6 +39,9 @@ Server::Server(QObject *parent) chatChannelList << new ChatChannel("channel1", "testchannel 1"); chatChannelList << new ChatChannel("channel2", "testchannel 2"); + + for (int i = 0; i < chatChannelList.size(); ++i) + connect(chatChannelList[i], SIGNAL(channelInfoChanged()), this, SLOT(broadcastChannelUpdate())); } Server::~Server() @@ -163,6 +166,14 @@ void Server::broadcastGameListUpdate(ServerGame *game) players[i]->msg(line); } +void Server::broadcastChannelUpdate() +{ + QString line = qobject_cast(sender())->getChannelListLine(); + for (int i = 0; i < players.size(); ++i) + if (players[i]->getAcceptsChatChannelListChanges()) + players[i]->msg(line); +} + void Server::addClientToGame(int gameId, ServerSocket *client) { ServerGame *game = getGame(gameId); diff --git a/servatrice/src/server.h b/servatrice/src/server.h index 299a0d7a..62ac25f1 100644 --- a/servatrice/src/server.h +++ b/servatrice/src/server.h @@ -38,6 +38,7 @@ private slots: void addGame(const QString description, const QString password, const int maxPlayers, ServerSocket *creator); void addClientToGame(int gameId, ServerSocket *client); void gameClosing(); + void broadcastChannelUpdate(); public: Server(QObject *parent = 0); ~Server(); diff --git a/servatrice/src/serversocket.cpp b/servatrice/src/serversocket.cpp index 824f6d90..934eb74d 100644 --- a/servatrice/src/serversocket.cpp +++ b/servatrice/src/serversocket.cpp @@ -243,7 +243,7 @@ ReturnMessage::ReturnCode ServerSocket::cmdChatListChannels(const QList chatChannelList = server->getChatChannelList(); for (int i = 0; i < chatChannelList.size(); ++i) - msg(QString("chat|list_channels|%1|%2|%3").arg(chatChannelList[i]->getName()).arg(chatChannelList[i]->getDescription()).arg(chatChannelList[i]->size())); + msg(chatChannelList[i]->getChannelListLine()); acceptsChatChannelListChanges = true; return ReturnMessage::ReturnOk; @@ -306,6 +306,7 @@ ReturnMessage::ReturnCode ServerSocket::cmdCreateGame(const QList &par QString password = params[1].toString(); int maxPlayers = params[2].toInt(); acceptsGameListChanges = false; + acceptsChatChannelListChanges = false; leaveGame(); emit createGame(description, password, maxPlayers, this); return ReturnMessage::ReturnOk; @@ -318,6 +319,7 @@ ReturnMessage::ReturnCode ServerSocket::cmdJoinGame(const QList ¶m if (!server->checkGamePassword(gameId, password)) return ReturnMessage::ReturnPasswordWrong; acceptsGameListChanges = false; + acceptsChatChannelListChanges = false; leaveGame(); emit joinGame(gameId, this); return ReturnMessage::ReturnOk; diff --git a/servatrice/src/serversocket.h b/servatrice/src/serversocket.h index 5aee3148..08b1404b 100644 --- a/servatrice/src/serversocket.h +++ b/servatrice/src/serversocket.h @@ -123,6 +123,7 @@ public: void setPlayerId(int _id) { playerId = _id; } QString getPlayerName() const { return playerName; } bool getAcceptsGameListChanges() const { return acceptsGameListChanges; } + bool getAcceptsChatChannelListChanges() const { return acceptsChatChannelListChanges; } QStringList listCounters() const; QStringList listZones() const; void setupZones(); From 8daa81e462eabbdd1fe69745f861971c7d93953f Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 14:27:44 +0200 Subject: [PATCH 4/8] translation --- cockatrice/src/gameselector.cpp | 11 +- cockatrice/src/gameselector.h | 1 + cockatrice/src/window_main.cpp | 1 + cockatrice/translations/cockatrice_de.ts | 136 ++++++++++++++--------- cockatrice/translations/cockatrice_en.ts | 128 ++++++++++++++------- 5 files changed, 181 insertions(+), 96 deletions(-) diff --git a/cockatrice/src/gameselector.cpp b/cockatrice/src/gameselector.cpp index 7616f8a4..2f84ac84 100644 --- a/cockatrice/src/gameselector.cpp +++ b/cockatrice/src/gameselector.cpp @@ -9,8 +9,8 @@ GameSelector::GameSelector(Client *_client, QWidget *parent) gameListModel = new GamesModel(this); gameListView->setModel(gameListModel); - createButton = new QPushButton(tr("C&reate")); - joinButton = new QPushButton(tr("&Join")); + createButton = new QPushButton; + joinButton = new QPushButton; QHBoxLayout *buttonLayout = new QHBoxLayout; buttonLayout->addStretch(); buttonLayout->addWidget(createButton); @@ -20,6 +20,7 @@ GameSelector::GameSelector(Client *_client, QWidget *parent) mainLayout->addWidget(gameListView); mainLayout->addLayout(buttonLayout); + retranslateUi(); setLayout(mainLayout); setMinimumWidth(gameListView->columnWidth(0) * gameListModel->columnCount()); @@ -94,3 +95,9 @@ void GameSelector::disableGameList() hide(); gameListModel->cleanList(); } + +void GameSelector::retranslateUi() +{ + createButton->setText(tr("C&reate")); + joinButton->setText(tr("&Join")); +} \ No newline at end of file diff --git a/cockatrice/src/gameselector.h b/cockatrice/src/gameselector.h index b8937ad3..76b134e6 100644 --- a/cockatrice/src/gameselector.h +++ b/cockatrice/src/gameselector.h @@ -15,6 +15,7 @@ public: GameSelector(Client *_client, QWidget *parent = 0); void enableGameList(); void disableGameList(); + void retranslateUi(); private slots: void actCreate(); void actRefresh(); diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index d6c6af69..0e8a6024 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -216,6 +216,7 @@ void MainWindow::retranslateUi() cardInfo->retranslateUi(); chatWidget->retranslateUi(); + gameSelector->retranslateUi(); } void MainWindow::createActions() diff --git a/cockatrice/translations/cockatrice_de.ts b/cockatrice/translations/cockatrice_de.ts index 8d0dc78e..0255789e 100644 --- a/cockatrice/translations/cockatrice_de.ts +++ b/cockatrice/translations/cockatrice_de.ts @@ -1,6 +1,6 @@ - - + + @@ -83,6 +83,42 @@ Das Kartenhintergrundbild konnte nicht geladen werden. + + ChannelWidget + + + %1 has joined the channel. + %1hat den Raum betreten. + + + + %1 has left the channel. + %1 hat den Raum verlassen. + + + + ChatWidget + + + Joi&n + Teil&nehmen + + + + Channel + Raum + + + + Description + Beschreibung + + + + Players + Spielerzahl + + DeckList @@ -185,6 +221,7 @@ Spiel erstellen + Error Fehler @@ -316,32 +353,26 @@ Ctrl+L - &Shuffle Mi&schen - Ctrl+S Ctrl+S - &Draw a card Karte &ziehen - Ctrl+D Ctrl+D - D&raw cards... Ka&rten ziehen... - Ctrl+E Ctrl+E @@ -494,47 +525,46 @@ F10 - + Set life Setze Leben - + New life total: Neues Leben insgesammt: - + Roll dice Würfeln - + Number of sides: Anzahl der Seiten: - Draw cards Karten ziehen - + Number: Anzahl: - + Create token Token erstellen - + Name: Name: - + Set counters Setze Zählmarke @@ -542,32 +572,32 @@ GameSelector - + C&reate Spiel e&rstellen - + &Join &Teilnehmen - + Error Fehler - + XXX XXX - + Join game Spiel beitreten - + Password: Passwort: @@ -613,6 +643,9 @@ GeneralSettingsPage + + + Choose path Pfad auswählen @@ -653,6 +686,7 @@ Pfad zur Kartendatenbank: + English Deutsch @@ -661,97 +695,97 @@ MainWindow - + Error Fehler - + Server timeout Server Zeitüberschreitung - + &Connect... &Verbinden... - + &Disconnect Verbindung &trennen - + &Restart game... Spiel neu sta&rten... - + F2 F2 - + &Leave game Spiel ver&lassen - + &Deck editor &Deck-Editor - + &Full screen &Vollbild - + Ctrl+F Ctrl+F - + &Settings... &Einstellungen... - + &Exit &Beenden - + Close most recent zone view Letzte Zonenansicht schließen - + Esc Esc - + &Game Spi&el - + &Actions &Aktionen - + &Card &Karte - + &Say: &Sagen: - + Cockatrice Cockatrice @@ -1208,27 +1242,27 @@ Bib&liothek - + &Graveyard &Friedhof - + &Removed cards Entfe&rnte Karten - + &Sideboard &Sideboard - + View top cards of library Zeige die obersten Karten der Bibliothek - + Number of cards: Anzahl der Karten: @@ -1263,12 +1297,12 @@ Ctrl+S - + Draw cards Karten ziehen - + Number: Anzahl: @@ -1286,12 +1320,12 @@ Sideboard - + Cockatrice decks (*.cod) Cockatrice Decks (*.cod) - + Plain text decks (*.dec *.mwDeck) Text Decks (*.dec *.mwDeck) diff --git a/cockatrice/translations/cockatrice_en.ts b/cockatrice/translations/cockatrice_en.ts index 7d86c9a1..63903b19 100644 --- a/cockatrice/translations/cockatrice_en.ts +++ b/cockatrice/translations/cockatrice_en.ts @@ -1,5 +1,6 @@ - + + CardDatabaseModel @@ -51,6 +52,42 @@ + + ChannelWidget + + + %1 has joined the channel. + + + + + %1 has left the channel. + + + + + ChatWidget + + + Joi&n + + + + + Channel + + + + + Description + + + + + Players + + + DeckList @@ -153,6 +190,7 @@ + Error @@ -397,42 +435,42 @@ - + Set life - + New life total: - + Roll dice - + Number of sides: - + Number: - + Create token - + Name: - + Set counters @@ -440,32 +478,32 @@ GameSelector - + C&reate - + &Join - + Error - + XXX - + Join game - + Password: @@ -511,6 +549,9 @@ GeneralSettingsPage + + + Choose path @@ -551,6 +592,7 @@ + English English @@ -559,97 +601,97 @@ MainWindow - + Error - + Server timeout - + &Connect... - + &Disconnect - + &Restart game... - + F2 - + &Leave game - + &Deck editor - + &Full screen - + Ctrl+F - + &Settings... - + &Exit - + Close most recent zone view - + Esc - + &Game - + &Actions - + &Card - + &Say: - + Cockatrice @@ -1086,27 +1128,27 @@ - + &Graveyard - + &Removed cards - + &Sideboard - + View top cards of library - + Number of cards: @@ -1141,12 +1183,12 @@ - + Draw cards - + Number: @@ -1164,12 +1206,12 @@ - + Cockatrice decks (*.cod) - + Plain text decks (*.dec *.mwDeck) From 5d32bb8bc4aea173cae2fc7e74a9645829492430 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 16:25:10 +0200 Subject: [PATCH 5/8] chat code --- cockatrice/src/cardinfowidget.cpp | 1 + cockatrice/src/chatwidget.cpp | 49 ++++++++++++++++++++++++------ cockatrice/src/chatwidget.h | 4 ++- cockatrice/src/gameselector.cpp | 7 ----- cockatrice/src/gameselector.h | 1 - cockatrice/src/servereventdata.cpp | 1 + cockatrice/src/servereventdata.h | 3 +- cockatrice/src/window_main.cpp | 2 ++ servatrice/servatrice.ini.example | 3 ++ servatrice/src/chatchannel.cpp | 10 +++--- servatrice/src/chatchannel.h | 6 +++- servatrice/src/server.cpp | 15 +++++++-- servatrice/src/server.h | 3 ++ servatrice/src/serversocket.cpp | 8 ++++- 14 files changed, 85 insertions(+), 28 deletions(-) diff --git a/cockatrice/src/cardinfowidget.cpp b/cockatrice/src/cardinfowidget.cpp index 6ebe620b..4d82c656 100644 --- a/cockatrice/src/cardinfowidget.cpp +++ b/cockatrice/src/cardinfowidget.cpp @@ -62,6 +62,7 @@ CardInfoWidget::CardInfoWidget(CardDatabase *_db, QWidget *parent) retranslateUi(); setFrameStyle(QFrame::Panel | QFrame::Raised); + textLabel->setFixedHeight(130); setFixedSize(sizeHint()); } diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp index ad1f3b34..604ffb62 100644 --- a/cockatrice/src/chatwidget.cpp +++ b/cockatrice/src/chatwidget.cpp @@ -2,23 +2,27 @@ #include "chatwidget.h" #include "client.h" -ChannelWidget::ChannelWidget(Client *_client, const QString &_name, QWidget *parent) +ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnly, QWidget *parent) : QWidget(parent), client(_client), name(_name) { playerList = new QListWidget; textEdit = new QTextEdit; textEdit->setReadOnly(true); - sayEdit = new QLineEdit; - connect(sayEdit, SIGNAL(returnPressed()), this, SLOT(sendMessage())); + if (!readOnly) { + sayEdit = new QLineEdit; + connect(sayEdit, SIGNAL(returnPressed()), this, SLOT(sendMessage())); + } QVBoxLayout *vbox = new QVBoxLayout; vbox->addWidget(textEdit); - vbox->addWidget(sayEdit); + if (!readOnly) + vbox->addWidget(sayEdit); QHBoxLayout *hbox = new QHBoxLayout; - hbox->addLayout(vbox, 1); + hbox->addLayout(vbox); hbox->addWidget(playerList); + playerList->setFixedWidth(100); setLayout(hbox); } @@ -57,6 +61,11 @@ void ChannelWidget::sayEvent(const QString &playerName, const QString &s) textEdit->append(QString("%1: %2").arg(playerName).arg(s)); } +void ChannelWidget::serverMessageEvent(const QString &s) +{ + textEdit->append(QString("%1").arg(s)); +} + ChatWidget::ChatWidget(Client *_client, QWidget *parent) : QWidget(parent), client(_client) { @@ -110,7 +119,7 @@ void ChatWidget::chatEvent(const ChatEventData &data) const QStringList &msg = data.getEventData(); switch (data.getEventType()) { case eventChatListChannels: { - if (msg.size() != 3) + if (msg.size() != 4) break; for (int i = 0; i < channelList->topLevelItemCount(); ++i) { QTreeWidgetItem *twi = channelList->topLevelItem(i); @@ -121,6 +130,8 @@ void ChatWidget::chatEvent(const ChatEventData &data) } } channelList->addTopLevelItem(new QTreeWidgetItem(QStringList() << msg[0] << msg[1] << msg[2])); + if (msg[3] == "1") + joinChannel(msg[0]); break; } case eventChatJoinChannel: { @@ -159,11 +170,33 @@ void ChatWidget::chatEvent(const ChatEventData &data) w->sayEvent(msg[1], msg[2]); break; } + case eventChatServerMessage: { + if (msg.size() != 2) + break; + ChannelWidget *w; + if (msg[0].isEmpty()) { + w = getChannel("Server"); + if (!w) { + w = new ChannelWidget(client, "Server", true); + tab->addTab(w, "Server"); + } + } else + w = getChannel(msg[0]); + w->serverMessageEvent(msg[1]); + break; + } default: { } } } +void ChatWidget::joinChannel(const QString &channelName) +{ + PendingCommand *pc = client->chatJoinChannel(channelName); + pc->setExtraData(channelName); + connect(pc, SIGNAL(finished(ServerResponse)), this, SLOT(joinFinished(ServerResponse))); +} + void ChatWidget::joinClicked() { QTreeWidgetItem *twi = channelList->currentItem(); @@ -173,9 +206,7 @@ void ChatWidget::joinClicked() if (getChannel(channelName)) return; - PendingCommand *pc = client->chatJoinChannel(channelName); - pc->setExtraData(channelName); - connect(pc, SIGNAL(finished(ServerResponse)), this, SLOT(joinFinished(ServerResponse))); + joinChannel(channelName); } void ChatWidget::joinFinished(ServerResponse resp) diff --git a/cockatrice/src/chatwidget.h b/cockatrice/src/chatwidget.h index 94bb8944..6e891293 100644 --- a/cockatrice/src/chatwidget.h +++ b/cockatrice/src/chatwidget.h @@ -23,13 +23,14 @@ private: private slots: void sendMessage(); public: - ChannelWidget(Client *_client, const QString &_name, QWidget *parent = 0); + ChannelWidget(Client *_client, const QString &_name, bool readOnly = false, QWidget *parent = 0); const QString &getName() const { return name; } void joinEvent(const QString &playerName); void listPlayersEvent(const QString &playerName); void leaveEvent(const QString &playerName); void sayEvent(const QString &playerName, const QString &s); + void serverMessageEvent(const QString &s); }; class ChatWidget : public QWidget { @@ -41,6 +42,7 @@ private: Client *client; ChannelWidget *getChannel(const QString &name); + void joinChannel(const QString &channelName); private slots: void chatEvent(const ChatEventData &data); void joinClicked(); diff --git a/cockatrice/src/gameselector.cpp b/cockatrice/src/gameselector.cpp index 2f84ac84..65c5c94e 100644 --- a/cockatrice/src/gameselector.cpp +++ b/cockatrice/src/gameselector.cpp @@ -42,12 +42,6 @@ void GameSelector::actRefresh() client->listGames(); } -void GameSelector::statusChanged(ProtocolStatus status) -{ - if (status == StatusDisconnected) - disableGameList(); -} - void GameSelector::checkResponse(ServerResponse response) { createButton->setEnabled(true); @@ -84,7 +78,6 @@ void GameSelector::actJoin() void GameSelector::enableGameList() { connect(client, SIGNAL(gameListEvent(ServerGame *)), gameListModel, SLOT(updateGameList(ServerGame *))); - connect(client, SIGNAL(statusChanged(ProtocolStatus)), this, SLOT(statusChanged(ProtocolStatus))); client->listGames(); show(); } diff --git a/cockatrice/src/gameselector.h b/cockatrice/src/gameselector.h index 76b134e6..fe3ac8cf 100644 --- a/cockatrice/src/gameselector.h +++ b/cockatrice/src/gameselector.h @@ -21,7 +21,6 @@ private slots: void actRefresh(); void actJoin(); void checkResponse(ServerResponse response); - void statusChanged(ProtocolStatus status); private: Client *client; diff --git a/cockatrice/src/servereventdata.cpp b/cockatrice/src/servereventdata.cpp index df97bf60..324e90fe 100644 --- a/cockatrice/src/servereventdata.cpp +++ b/cockatrice/src/servereventdata.cpp @@ -50,6 +50,7 @@ ChatEventData::ChatEventData(const QString &line) eventHash.insert("list_players", eventChatListPlayers); eventHash.insert("leave_channel", eventChatLeaveChannel); eventHash.insert("say", eventChatSay); + eventHash.insert("server_message", eventChatServerMessage); } QStringList values = line.split('|'); diff --git a/cockatrice/src/servereventdata.h b/cockatrice/src/servereventdata.h index 50233af5..9f809fcf 100644 --- a/cockatrice/src/servereventdata.h +++ b/cockatrice/src/servereventdata.h @@ -53,7 +53,8 @@ enum ChatEventType { eventChatJoinChannel, eventChatListPlayers, eventChatLeaveChannel, - eventChatSay + eventChatSay, + eventChatServerMessage }; class ChatEventData { diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index 0e8a6024..d04bab30 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -71,6 +71,8 @@ void MainWindow::statusChanged(ProtocolStatus _status) aLeaveGame->setEnabled(false); phasesToolbar->setActivePhase(-1); phasesToolbar->hide(); + gameSelector->disableGameList(); + chatWidget->disableChat(); emit logDisconnected(); break; case StatusLoggingIn: diff --git a/servatrice/servatrice.ini.example b/servatrice/servatrice.ini.example index 632c525d..c4e7b3ca 100644 --- a/servatrice/servatrice.ini.example +++ b/servatrice/servatrice.ini.example @@ -7,3 +7,6 @@ hostname=localhost database=servatrice user=servatrice password=foobar + +[messages] +login="Example line 1", "Example line 2" diff --git a/servatrice/src/chatchannel.cpp b/servatrice/src/chatchannel.cpp index fc621013..75d8dad6 100644 --- a/servatrice/src/chatchannel.cpp +++ b/servatrice/src/chatchannel.cpp @@ -1,8 +1,8 @@ #include "chatchannel.h" #include "serversocket.h" -ChatChannel::ChatChannel(const QString &_name, const QString &_description) - : name(_name), description(_description) +ChatChannel::ChatChannel(const QString &_name, const QString &_description, bool _autoJoin, const QStringList &_joinMessage) + : name(_name), description(_description), autoJoin(_autoJoin), joinMessage(_joinMessage) { } @@ -16,6 +16,8 @@ void ChatChannel::addPlayer(ServerSocket *player) for (int i = 0; i < size(); ++i) player->msg(QString("chat|list_players|%1|%2").arg(name).arg(at(i)->getPlayerName())); + for (int i = 0; i < joinMessage.size(); ++i) + player->msg(QString("chat|server_message|%1|%2").arg(name).arg(joinMessage[i])); emit channelInfoChanged(); } @@ -40,5 +42,5 @@ void ChatChannel::say(ServerSocket *player, const QString &s) QString ChatChannel::getChannelListLine() const { - return QString("chat|list_channels|%1|%2|%3").arg(name).arg(description).arg(size()); -} \ No newline at end of file + return QString("chat|list_channels|%1|%2|%3|%4").arg(name).arg(description).arg(size()).arg(autoJoin ? 1 : 0); +} diff --git a/servatrice/src/chatchannel.h b/servatrice/src/chatchannel.h index fdf254f4..c7ca5b76 100644 --- a/servatrice/src/chatchannel.h +++ b/servatrice/src/chatchannel.h @@ -3,6 +3,7 @@ #include #include +#include class ServerSocket; @@ -13,10 +14,13 @@ signals: private: QString name; QString description; + bool autoJoin; + QStringList joinMessage; public: - ChatChannel(const QString &_name, const QString &_description); + ChatChannel(const QString &_name, const QString &_description, bool _autoJoin, const QStringList &_joinMessage); QString getName() const { return name; } QString getDescription() const { return description; } + bool getAutoJoin() const { return autoJoin; } void addPlayer(ServerSocket *player); void removePlayer(ServerSocket *player); void say(ServerSocket *player, const QString &s); diff --git a/servatrice/src/server.cpp b/servatrice/src/server.cpp index 30a0cd53..990503cd 100644 --- a/servatrice/src/server.cpp +++ b/servatrice/src/server.cpp @@ -27,7 +27,7 @@ #include Server::Server(QObject *parent) - : QTcpServer(parent), nextGameId(0) + : QTcpServer(parent), nextGameId(0) { rng = new RNG_Qt(this); @@ -37,11 +37,20 @@ Server::Server(QObject *parent) if (dbType == "mysql") openDatabase(); - chatChannelList << new ChatChannel("channel1", "testchannel 1"); - chatChannelList << new ChatChannel("channel2", "testchannel 2"); + int size = settings->beginReadArray("chatchannels"); + for (int i = 0; i < size; ++i) { + settings->setArrayIndex(i); + chatChannelList << new ChatChannel(settings->value("name").toString(), + settings->value("description").toString(), + settings->value("autojoin").toBool(), + settings->value("joinmessage").toStringList()); + } + settings->endArray(); for (int i = 0; i < chatChannelList.size(); ++i) connect(chatChannelList[i], SIGNAL(channelInfoChanged()), this, SLOT(broadcastChannelUpdate())); + + loginMessage = settings->value("messages/login").toStringList(); } Server::~Server() diff --git a/servatrice/src/server.h b/servatrice/src/server.h index 62ac25f1..bccdb292 100644 --- a/servatrice/src/server.h +++ b/servatrice/src/server.h @@ -21,6 +21,7 @@ #define SERVER_H #include +#include class ServerGame; class ServerSocket; @@ -52,12 +53,14 @@ public: AbstractRNG *getRNG() const { return rng; } void broadcastGameListUpdate(ServerGame *game); void removePlayer(ServerSocket *player); + const QStringList &getLoginMessage() const { return loginMessage; } private: void incomingConnection(int SocketId); QList games; QList players; QList chatChannelList; int nextGameId; + QStringList loginMessage; AbstractRNG *rng; }; diff --git a/servatrice/src/serversocket.cpp b/servatrice/src/serversocket.cpp index 934eb74d..c4a07a4b 100644 --- a/servatrice/src/serversocket.cpp +++ b/servatrice/src/serversocket.cpp @@ -236,7 +236,13 @@ ReturnMessage::ReturnCode ServerSocket::cmdLogin(const QList ¶ms) return ReturnMessage::ReturnPasswordWrong; playerName = params[0].toString(); - return ReturnMessage::ReturnOk; + remsg->send(ReturnMessage::ReturnOk); + + QStringList loginMessage = server->getLoginMessage(); + for (int i = 0; i < loginMessage.size(); ++i) + msg("chat|server_message||" + loginMessage[i]); + + return ReturnMessage::ReturnNothing; } ReturnMessage::ReturnCode ServerSocket::cmdChatListChannels(const QList &/*params*/) From b51d4cd4f4a9b4ab1628b8950d28f32b306852b3 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 16:33:45 +0200 Subject: [PATCH 6/8] fixed servatrice.ini.example --- servatrice/servatrice.ini.example | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/servatrice/servatrice.ini.example b/servatrice/servatrice.ini.example index c4e7b3ca..5a36553c 100644 --- a/servatrice/servatrice.ini.example +++ b/servatrice/servatrice.ini.example @@ -10,3 +10,11 @@ password=foobar [messages] login="Example line 1", "Example line 2" + +[chatchannels] +size=1 +1\name="General Chat" +1\description="Discuss anything here." +1\autojoin=true +1\joinmessage="This is the general chat channel.", "This message is only here to show that channels can have a join message." + From b113b78e7cd033bbc790537014b5f5f95b9fe836 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 16:53:51 +0200 Subject: [PATCH 7/8] chat fix --- cockatrice/src/chatwidget.cpp | 18 +++++++++++++++--- cockatrice/src/chatwidget.h | 4 +++- cockatrice/src/window_main.cpp | 2 ++ 3 files changed, 20 insertions(+), 4 deletions(-) diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp index 604ffb62..ae8350fd 100644 --- a/cockatrice/src/chatwidget.cpp +++ b/cockatrice/src/chatwidget.cpp @@ -2,8 +2,8 @@ #include "chatwidget.h" #include "client.h" -ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnly, QWidget *parent) - : QWidget(parent), client(_client), name(_name) +ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnly, bool _virtualChannel, QWidget *parent) + : QWidget(parent), client(_client), name(_name), virtualChannel(_virtualChannel) { playerList = new QListWidget; @@ -27,6 +27,12 @@ ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnl setLayout(hbox); } +ChannelWidget::~ChannelWidget() +{ + if (!virtualChannel) + client->chatLeaveChannel(name); +} + void ChannelWidget::sendMessage() { if (sayEdit->text().isEmpty()) @@ -111,6 +117,12 @@ void ChatWidget::enableChat() void ChatWidget::disableChat() { disconnect(client, 0, this, 0); + while (tab->count()) { + ChannelWidget *cw = qobject_cast(tab->widget(0)); + tab->removeTab(0); + delete cw; + } + channelList->clear(); hide(); } @@ -177,7 +189,7 @@ void ChatWidget::chatEvent(const ChatEventData &data) if (msg[0].isEmpty()) { w = getChannel("Server"); if (!w) { - w = new ChannelWidget(client, "Server", true); + w = new ChannelWidget(client, "Server", true, true); tab->addTab(w, "Server"); } } else diff --git a/cockatrice/src/chatwidget.h b/cockatrice/src/chatwidget.h index 6e891293..c4075f6f 100644 --- a/cockatrice/src/chatwidget.h +++ b/cockatrice/src/chatwidget.h @@ -20,10 +20,12 @@ private: QLineEdit *sayEdit; Client *client; QString name; + bool virtualChannel; private slots: void sendMessage(); public: - ChannelWidget(Client *_client, const QString &_name, bool readOnly = false, QWidget *parent = 0); + ChannelWidget(Client *_client, const QString &_name, bool readOnly = false, bool _virtualChannel = false, QWidget *parent = 0); + ~ChannelWidget(); const QString &getName() const { return name; } void joinEvent(const QString &playerName); diff --git a/cockatrice/src/window_main.cpp b/cockatrice/src/window_main.cpp index d04bab30..b9d76deb 100644 --- a/cockatrice/src/window_main.cpp +++ b/cockatrice/src/window_main.cpp @@ -350,6 +350,8 @@ MainWindow::MainWindow(QTranslator *_translator, QWidget *parent) void MainWindow::closeEvent(QCloseEvent */*event*/) { delete game; + chatWidget->disableChat(); + gameSelector->disableGameList(); } void MainWindow::changeEvent(QEvent *event) From 74ae1c41fcc42d21775b0b95541f17b0e7e67b51 Mon Sep 17 00:00:00 2001 From: Max-Wilhelm Bruker Date: Sun, 23 Aug 2009 17:06:12 +0200 Subject: [PATCH 8/8] chat improvements --- cockatrice/src/chatwidget.cpp | 19 ++++-- cockatrice/translations/cockatrice_de.ts | 73 ++++++++++++------------ cockatrice/translations/cockatrice_en.ts | 73 +++++++++++------------- 3 files changed, 83 insertions(+), 82 deletions(-) diff --git a/cockatrice/src/chatwidget.cpp b/cockatrice/src/chatwidget.cpp index ae8350fd..d42e7ef1 100644 --- a/cockatrice/src/chatwidget.cpp +++ b/cockatrice/src/chatwidget.cpp @@ -6,6 +6,7 @@ ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnl : QWidget(parent), client(_client), name(_name), virtualChannel(_virtualChannel) { playerList = new QListWidget; + playerList->setFixedWidth(100); textEdit = new QTextEdit; textEdit->setReadOnly(true); @@ -22,7 +23,6 @@ ChannelWidget::ChannelWidget(Client *_client, const QString &_name, bool readOnl QHBoxLayout *hbox = new QHBoxLayout; hbox->addLayout(vbox); hbox->addWidget(playerList); - playerList->setFixedWidth(100); setLayout(hbox); } @@ -76,6 +76,8 @@ ChatWidget::ChatWidget(Client *_client, QWidget *parent) : QWidget(parent), client(_client) { channelList = new QTreeWidget; + channelList->setRootIsDecorated(false); + channelList->setFixedWidth(200); joinButton = new QPushButton; connect(joinButton, SIGNAL(clicked()), this, SLOT(joinClicked())); @@ -103,8 +105,8 @@ void ChatWidget::retranslateUi() QTreeWidgetItem *header = channelList->headerItem(); Q_ASSERT(header != 0); header->setText(0, tr("Channel")); - header->setText(1, tr("Description")); - header->setText(2, tr("Players")); + header->setText(1, tr("Players")); + header->setTextAlignment(1, Qt::AlignRight); } void ChatWidget::enableChat() @@ -136,12 +138,17 @@ void ChatWidget::chatEvent(const ChatEventData &data) for (int i = 0; i < channelList->topLevelItemCount(); ++i) { QTreeWidgetItem *twi = channelList->topLevelItem(i); if (twi->text(0) == msg[0]) { - twi->setText(1, msg[1]); - twi->setText(2, msg[2]); + twi->setToolTip(0, msg[1]); + twi->setText(1, msg[2]); return; } } - channelList->addTopLevelItem(new QTreeWidgetItem(QStringList() << msg[0] << msg[1] << msg[2])); + QTreeWidgetItem *twi = new QTreeWidgetItem(QStringList() << msg[0] << msg[2]); + twi->setTextAlignment(1, Qt::AlignRight); + twi->setToolTip(0, msg[1]); + channelList->addTopLevelItem(twi); + channelList->resizeColumnToContents(0); + channelList->resizeColumnToContents(1); if (msg[3] == "1") joinChannel(msg[0]); break; diff --git a/cockatrice/translations/cockatrice_de.ts b/cockatrice/translations/cockatrice_de.ts index 0255789e..834020f2 100644 --- a/cockatrice/translations/cockatrice_de.ts +++ b/cockatrice/translations/cockatrice_de.ts @@ -55,22 +55,22 @@ CardInfoWidget - + Name: Name: - + Mana cost: Manakosten: - + Card type: Kartentyp: - + P / T: S/W: @@ -86,12 +86,12 @@ ChannelWidget - + %1 has joined the channel. - %1hat den Raum betreten. + %1 hat den Raum betreten. - + %1 has left the channel. %1 hat den Raum verlassen. @@ -99,22 +99,21 @@ ChatWidget - + Joi&n Teil&nehmen - + Channel Raum - Description - Beschreibung + Beschreibung - + Players Spielerzahl @@ -572,32 +571,32 @@ GameSelector - + C&reate Spiel e&rstellen - + &Join &Teilnehmen - + Error Fehler - + XXX XXX - + Join game Spiel beitreten - + Password: Passwort: @@ -695,97 +694,97 @@ MainWindow - + Error Fehler - + Server timeout Server Zeitüberschreitung - + &Connect... &Verbinden... - + &Disconnect Verbindung &trennen - + &Restart game... Spiel neu sta&rten... - + F2 F2 - + &Leave game Spiel ver&lassen - + &Deck editor &Deck-Editor - + &Full screen &Vollbild - + Ctrl+F Ctrl+F - + &Settings... &Einstellungen... - + &Exit &Beenden - + Close most recent zone view Letzte Zonenansicht schließen - + Esc Esc - + &Game Spi&el - + &Actions &Aktionen - + &Card &Karte - + &Say: &Sagen: - + Cockatrice Cockatrice diff --git a/cockatrice/translations/cockatrice_en.ts b/cockatrice/translations/cockatrice_en.ts index 63903b19..c021d286 100644 --- a/cockatrice/translations/cockatrice_en.ts +++ b/cockatrice/translations/cockatrice_en.ts @@ -32,22 +32,22 @@ CardInfoWidget - + Name: - + Mana cost: - + Card type: - + P / T: @@ -55,12 +55,12 @@ ChannelWidget - + %1 has joined the channel. - + %1 has left the channel. @@ -68,22 +68,17 @@ ChatWidget - + Joi&n - + Channel - - Description - - - - + Players @@ -478,32 +473,32 @@ GameSelector - + C&reate - + &Join - + Error - + XXX - + Join game - + Password: @@ -601,97 +596,97 @@ MainWindow - + Error - + Server timeout - + &Connect... - + &Disconnect - + &Restart game... - + F2 - + &Leave game - + &Deck editor - + &Full screen - + Ctrl+F - + &Settings... - + &Exit - + Close most recent zone view - + Esc - + &Game - + &Actions - + &Card - + &Say: - + Cockatrice