void NinjamRoomWindow::handleChordProgressionMessage(const Ninjam::User &user, const QString &message)
{
    Q_UNUSED(user)
    ChatChordsProgressionParser parser;
    try{
        ChordProgression chordProgression = parser.parse(message);
        chatPanel->addChordProgressionConfirmationMessage(chordProgression);
    }
    catch (const std::runtime_error &e) {
        qCCritical(jtNinjamGUI) << e.what();
    }
}
void NinjamRoomWindow::showLastChordsInChat()
{
    Login::LoginService *loginService = mainController->getLoginService();
    QString lastChordProgression = loginService->getChordProgressionFor(roomInfo);
    ChatChordsProgressionParser parser;
    if (parser.containsProgression(lastChordProgression)) {
        ChordProgression progression = parser.parse(lastChordProgression);
        QString title = tr("Last chords used");
        chatPanel->addLastChordsMessage(title, progression.toString());
        chatPanel->addChordProgressionConfirmationMessage(parser.parse(lastChordProgression));

    }
}
void NinjamRoomWindow::addChatMessage(const Ninjam::User &user, const QString &message)
{
    QString userName = user.getName();

    bool isSystemVoteMessage = Gui::Chat::parseSystemVotingMessage(message).isValidVotingMessage();

    bool isChordProgressionMessage = false;
    if (!isSystemVoteMessage) {
        ChatChordsProgressionParser chordsParser;
        isChordProgressionMessage = chordsParser.containsProgression(message);
    }

    bool showBlockButton = canShowBlockButtonInChatMessage(userName);
    bool showTranslationButton = !isChordProgressionMessage;
    chatPanel->addMessage(userName, message, showTranslationButton, showBlockButton);

    static bool localUserWasVotingInLastMessage = false;

    if (isSystemVoteMessage) {
        Gui::Chat::SystemVotingMessage voteMessage = Gui::Chat::parseSystemVotingMessage(message);

        QTimer *expirationTimer = voteMessage.isBpiVotingMessage() ? bpiVotingExpiratonTimer : bpmVotingExpirationTimer;

        bool isFirstSystemVoteMessage = Gui::Chat::isFirstSystemVotingMessage(userName, message);
        if (isFirstSystemVoteMessage) { //starting a new votation round
            if (!localUserWasVotingInLastMessage) {  //don't create the vote button if local user is proposing BPI or BPM change
                createVoteButton(voteMessage);
            }
            else{ //if local user is proposing a bpi/bpm change the combos are disabled until the voting reach majority or expire
                if (voteMessage.isBpiVotingMessage())
                    ninjamPanel->setBpiComboPendingStatus(true);
                else
                    ninjamPanel->setBpmComboPendingStatus(true);
                if (QApplication::focusWidget()) //clear comboboxes focus when disabling
                    QApplication::focusWidget()->clearFocus();
            }
        }

        //timer is restarted in every vote
        expirationTimer->start(voteMessage.getExpirationTime() * 1000); //QTimer::start will cancel a previous voting expiration timer
    }
    else if (isChordProgressionMessage) {
        handleChordProgressionMessage(user, message);
    }

    localUserWasVotingInLastMessage = Gui::Chat::isLocalUserVotingMessage(message) && user.getName() == mainController->getUserName();
}
void NinjamRoomWindow::addChatMessage(const Ninjam::User &user, const QString &message)
{
    bool isVoteMessage = !message.isNull() && message.toLower().startsWith(
        "[voting system] leading candidate:");
    bool isChordProgressionMessage = false;
    try{
        ChatChordsProgressionParser chordsParser;
        isChordProgressionMessage = chordsParser.containsProgression(message);
    }
    catch (...) {
        isChordProgressionMessage = false;// just in case
    }

    bool showTranslationButton = !isChordProgressionMessage;
    chatPanel->addMessage(user.getName(), message, showTranslationButton);

    if (isVoteMessage)
        handleVoteMessage(user, message);
    else if (isChordProgressionMessage)
        handleChordProgressionMessage(user, message);
}