Search code examples
c++qtqtgui

Qt creator multiple definition within build folder


I am getting a weird error message with Qt creator which makes no sense why it is occuring at all.. I am at the moment programming an ai player for a ludo simulator, which has been written as a QT gui. I've creates a C++ class named player_q_learning, but for some reason is moc_player_q_learning.cpp created within the build folder, and create a multiple definition of the function which i already defined in player_q_learning... Why am I running into this error?

/home/Vato/Desktop/ludo-gui/build-ludo-Desktop-Debug/moc_player_q_learning.cpp:116: error: multiple definition of `player_q_learning::calc_input(float*, int, int)'

ludo.pro

#-------------------------------------------------
#
# Project created by QtCreator 2016-03-15T10:40:30
#
#-------------------------------------------------

QT       += core gui

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

TARGET = ludo
TEMPLATE = app


SOURCES += main.cpp\
        dialog.cpp \
    game.cpp \
    ludo_player.cpp \
    ludo_player_random.cpp \
    player_q_learning.cpp

HEADERS  += dialog.h \
    game.h \
    ludo_player.h \
    positions_and_dice.h \
    ludo_player_random.h \
    player_q_learning.h

FORMS    += dialog.ui

CONFIG += object_with_source

QMAKE_CXXFLAGS += -std=c++11 -Wall -Wextra -Wshadow -Wnon-virtual-dtor -pedantic -Wunused

main.cpp

#include "dialog.h"
#include <QApplication>
#include "game.h"
#include <vector>
#include "ludo_player.h"
#include "ludo_player_random.h"
#include "positions_and_dice.h"

Q_DECLARE_METATYPE( positions_and_dice )

using namespace std;

int main(int argc, char *argv[]){
    QApplication a(argc, argv);
    qRegisterMetaType<positions_and_dice>();

    //instanciate the players here
    ludo_player p1, p2;
    ludo_player_random p3, p4;

    game g;
    g.setGameDelay(010); //if you want to see the game, set a delay

    // Add a GUI <-- remove the '/' to uncomment block
//    Dialog w;
//    QObject::connect(&g,SIGNAL(update_graphics(std::vector<int>)),&w,SLOT(update_graphics(std::vector<int>)));
//    QObject::connect(&g,SIGNAL(set_color(int)),                   &w,SLOT(get_color(int)));
//    QObject::connect(&g,SIGNAL(set_dice_result(int)),             &w,SLOT(get_dice_result(int)));
//    QObject::connect(&g,SIGNAL(declare_winner(int)),              &w,SLOT(get_winner(int)));
//    w.show();
    //Or don't add the GUI
    //QObject::connect(&g,SIGNAL(close()),&a,SLOT(quit()));
    //*/

    //set up for each player
    QObject::connect(&g, SIGNAL(player1_start(positions_and_dice)),&p1,SLOT(start_turn(positions_and_dice)));
    QObject::connect(&p1,SIGNAL(select_piece(int)),                &g, SLOT(movePiece(int)));
    QObject::connect(&g, SIGNAL(player1_end(std::vector<int>)),    &p1,SLOT(post_game_analysis(std::vector<int>)));
    QObject::connect(&p1,SIGNAL(turn_complete(bool)),              &g, SLOT(turnComplete(bool)));

    QObject::connect(&g, SIGNAL(player2_start(positions_and_dice)),&p2,SLOT(start_turn(positions_and_dice)));
    QObject::connect(&p2,SIGNAL(select_piece(int)),                &g, SLOT(movePiece(int)));
    QObject::connect(&g, SIGNAL(player2_end(std::vector<int>)),    &p2,SLOT(post_game_analysis(std::vector<int>)));
    QObject::connect(&p2,SIGNAL(turn_complete(bool)),              &g, SLOT(turnComplete(bool)));

    QObject::connect(&g, SIGNAL(player3_start(positions_and_dice)),&p3,SLOT(start_turn(positions_and_dice)));
    QObject::connect(&p3,SIGNAL(select_piece(int)),                &g, SLOT(movePiece(int)));
    QObject::connect(&g, SIGNAL(player3_end(std::vector<int>)),    &p3,SLOT(post_game_analysis(std::vector<int>)));
    QObject::connect(&p3,SIGNAL(turn_complete(bool)),              &g, SLOT(turnComplete(bool)));

    QObject::connect(&g, SIGNAL(player4_start(positions_and_dice)),&p4,SLOT(start_turn(positions_and_dice)));
    QObject::connect(&p4,SIGNAL(select_piece(int)),                &g, SLOT(movePiece(int)));
    QObject::connect(&g, SIGNAL(player4_end(std::vector<int>)),    &p4,SLOT(post_game_analysis(std::vector<int>)));
    QObject::connect(&p4,SIGNAL(turn_complete(bool)),              &g, SLOT(turnComplete(bool)));

    g.start();


    return a.exec();
}

dialog.cpp

#include "dialog.h"
#include "ui_dialog.h"

Dialog::Dialog(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::Dialog)
{
    ui->setupUi(this);

    scene = new QGraphicsScene(this);
    ui->graphicsView->setScene(scene);
    ui->graphicsView->setBackgroundBrush(QBrush(QColor(240,240,239)));

    diceBG = scene->addRect(0,-150,100,100,QPen(Qt::black,3,Qt::SolidLine,Qt::RoundCap, Qt::RoundJoin),QBrush(Qt::green));
    diceRoll = scene->addSimpleText(QString::number(0),QFont("Courier", 72, QFont::Bold, true));
    diceRoll->setPos(25,-150);
    // Colors
    std::vector<std::pair<QColor,QColor> >base_colors {
        std::make_pair(QColor(92,170,119),QColor(185,219,125)), //G
        std::make_pair(QColor(237,235,89),QColor(237,234,138)),  //Y
        std::make_pair(QColor(92,93,170),QColor(111,111,170)),  //B
        std::make_pair(QColor(237,57,60),QColor(237,114,125))   //R
    };

    QBrush white(Qt::white);
    QPen blackPen(Qt::black);
    blackPen.setWidth(1);


    // Cross
    scene->addRect(415,-155,160,960,blackPen,QBrush(QColor(195,195,194)));
    scene->addRect(15,245,960,160,blackPen,QBrush(QColor(195,195,194)));
    scene->addRect(415,245,160,160,QPen(QColor(195,195,194)),QBrush(QColor(195,195,194))); //clean center

    // Goal stretch
    scene->addRect(50,290,350,70,blackPen,QBrush(base_colors[0].first));
    scene->addRect(460,-120,70,350,blackPen,QBrush(base_colors[1].first));
    scene->addRect(590,290,350,70,blackPen,QBrush(base_colors[2].first));
    scene->addRect(460,420,70,350,blackPen,QBrush(base_colors[3].first));

    int x_pos = -10; //start place for green
    int y_pos = 220;
    int offset = 70;
    int small_offset = 50;
    int large_offset = 80;

    //home fields
    home_fields.push_back(QPointF(0,0));
    home_fields.push_back(QPointF(630,-170));
    home_fields.push_back(QPointF(800,445));
    home_fields.push_back(QPointF(190,630));
    for(size_t f = 0; f < home_fields.size(); ++f){
        addHomeField(home_fields[f].x(),home_fields[f].y(),QBrush(base_colors[f].first));
    }

    // Playing fields
    std::vector<std::pair<char,char> > directions{std::make_pair(1,-1),std::make_pair(1,1),std::make_pair(-1,1),std::make_pair(-1,-1) };
    for(size_t d =0; d < directions.size(); ++d){
        for(int i=0; i<5;++i){
            if(d % 2 == 0)
                x_pos += directions[d].first * offset;
            else
                y_pos += directions[d].second * offset;
            fieldPos.push_back(QPointF(x_pos,y_pos));
        }
        x_pos += directions[d].first * small_offset;
        y_pos += directions[d].second * small_offset;
        for(int i=0; i<5;++i){
            fieldPos.push_back(QPointF(x_pos,y_pos));
            if(d % 2 == 0)
                y_pos += directions[d].second * offset;
            else
                x_pos += directions[d].first * offset;
        }
        for(int i=0; i<2;++i){
            fieldPos.push_back(QPointF(x_pos,y_pos));
            if(d % 2 == 0)
                x_pos += directions[d].first * large_offset;
            else
                y_pos += directions[d].second * large_offset;
        }
        fieldPos.push_back(QPointF(x_pos,y_pos));
    }

    //goal stretches
    for(int x=60; x<=340; x+=offset)
        fieldPos.push_back(QPointF(x,300));
    for(int y=-110; y<=170; y+=offset)
        fieldPos.push_back(QPointF(470,y));
    for(int x=880; x>=600; x-=offset)
        fieldPos.push_back(QPointF(x,300));
    for(int y=710; y>=430; y-=offset)
        fieldPos.push_back(QPointF(470,y));

    QImage globe_img("../globe.png");//http://www.clker.com/clipart-world-black-and-white.html
    QImage star_img("../star.png");  //http://www.clker.com/clipart-2568.html
//    QGraphicsPixmapItem globe( QPixmap::fromImage(QImage("../globe.png")));
//    QGraphicsPixmapItem star( QPixmap::fromImage(QImage("../star.png")));
    for(size_t c = 0; c < base_colors.size(); ++c){
        scene->addEllipse(fieldPos[0+13*c].x(),fieldPos[0+13*c].y(),50,50,QPen(base_colors[c].first),QBrush(base_colors[c].second));
        for(int i=1; i < 13; ++i){
            if(i == 8){
                QGraphicsPixmapItem * globe = new QGraphicsPixmapItem( QPixmap::fromImage(globe_img));
                globe->setPos(fieldPos[i+13*c]);
                globe->setScale(0.5);
                scene->addItem(globe);
            } else if(i == 5 || i == 11){
                QGraphicsPixmapItem * star = new QGraphicsPixmapItem( QPixmap::fromImage(star_img));
                star->setPos(fieldPos[i+13*c]);
                star->setScale(0.5);
                scene->addItem(star);
            } else {
                scene->addEllipse(fieldPos[i+13*c].x(),fieldPos[i+13*c].y(),50,50,blackPen,white);
            }
        }
    }
    for(size_t g = 52; g < fieldPos.size(); ++g){
        scene->addEllipse(fieldPos[g].x(),fieldPos[g].y(),50,50,blackPen,white);
    }
    create_graphic_players();
    std::vector<int> init_pos(16,-1);
    update_graphics(init_pos);
}

void Dialog::update_graphics(std::vector<int> player_positions){
    QPointF p;
    for(size_t i = 0; i < player_positions.size(); ++i){
        if(player_positions[i] == -1){
            p = home_fields[i / 4];
            if(i % 4 == 0)
                graphic_player[i]->setPos(p.x()+65 ,p.y()+15 );
            else if(i % 4 == 1)
                graphic_player[i]->setPos(p.x()+65 ,p.y()+115);
            else if(i % 4 == 2)
                graphic_player[i]->setPos(p.x()+15 ,p.y()+65 );
            else if(i % 4 == 3)
                graphic_player[i]->setPos(p.x()+115,p.y()+65 );

        } else if(player_positions[i] == 99){
            if(i/4 == 0){
                if(i % 4 == 0)      graphic_player[i]->setPos(405,300); //left
                else if(i % 4 == 1) graphic_player[i]->setPos(405,270);
                else if(i % 4 == 2) graphic_player[i]->setPos(405,330);
                else if(i % 4 == 3) graphic_player[i]->setPos(435,300);
            } else if(i/4 == 1){
                if(i % 4 == 0)      graphic_player[i]->setPos(470,235); //up
                else if(i % 4 == 1) graphic_player[i]->setPos(440,235);
                else if(i % 4 == 2) graphic_player[i]->setPos(500,235);
                else if(i % 4 == 3) graphic_player[i]->setPos(470,265);
            } else if(i/4 == 2){
                if(i % 4 == 0)      graphic_player[i]->setPos(535,300); //right
                else if(i % 4 == 1) graphic_player[i]->setPos(535,270);
                else if(i % 4 == 2) graphic_player[i]->setPos(535,330);
                else if(i % 4 == 3) graphic_player[i]->setPos(505,300);
            } else if(i/4 == 3){
                if(i % 4 == 0)      graphic_player[i]->setPos(470,365); //down
                else if(i % 4 == 1) graphic_player[i]->setPos(440,365);
                else if(i % 4 == 2) graphic_player[i]->setPos(500,365);
                else if(i % 4 == 3) graphic_player[i]->setPos(470,335);
            }
        } else {
            graphic_player[i]->setPos(fieldPos[player_positions[i]]);
        }
    }
    ui->graphicsView->repaint();
}

void Dialog::create_graphic_players(){
    graphic_player.clear();
    QBrush piece;
    QPen blackPen(Qt::black);
    blackPen.setWidth(1);
    for(int c = 0; c<4; ++c){
        if(c == 0){
            piece = QBrush(QColor(Qt::green));
        } else if(c == 1){
            piece = QBrush(QColor(Qt::yellow));
        } else if(c == 2){
            piece = QBrush(QColor(Qt::blue));
        } else if(c == 3){
            piece = QBrush(QColor(Qt::red));
        }
        for(int i = 0; i<4; ++i){
            graphic_player.push_back(scene->addEllipse(5,5,40,40,blackPen,piece));
        }
    }
}


Dialog::~Dialog()
{
    delete ui;
}

void Dialog::showEvent(QShowEvent *) {
    ui->graphicsView->fitInView(scene->itemsBoundingRect(),Qt::KeepAspectRatio);
}

void Dialog::resizeEvent(QResizeEvent *){
    ui->graphicsView->fitInView(scene->itemsBoundingRect(),Qt::KeepAspectRatio);
}

void Dialog::get_winner(int color){
    scene->addRect(0,500,1000,200,QPen(Qt::black,3,Qt::SolidLine,Qt::RoundCap, Qt::RoundJoin),QBrush(active_color));
    QGraphicsSimpleTextItem * win = scene->addSimpleText(QString("Winner is found!"),QFont("Courier", 72, QFont::Bold, true));
    win->setPos(50,550);
}

void Dialog::get_color(int color){
    switch(color){
        case 0:
            active_color = Qt::green;
            break;
        case 1:
            active_color = Qt::yellow;
            break;
        case 2:
            active_color = Qt::blue;
            break;
        case 3:
            active_color = Qt::red;
        default:
            break;
    }
}

void Dialog::get_dice_result(int dice){
    current_dice_roll = dice;
    diceBG->setBrush(active_color);
    diceRoll->setText(QString::number(current_dice_roll));
    ui->graphicsView->repaint();
}

void Dialog::addHomeField(int x, int y,QBrush brush){
    QBrush whiteBrush(Qt::white);
    QPen blackPen(Qt::black);
    blackPen.setWidth(1);

    scene->addEllipse(x,y,180,180,blackPen,brush);
    scene->addEllipse(x+65 ,y+15 ,50,50,blackPen,whiteBrush);
    scene->addEllipse(x+65 ,y+115,50,50,blackPen,whiteBrush);
    scene->addEllipse(x+15 ,y+65 ,50,50,blackPen,whiteBrush);
    scene->addEllipse(x+115,y+65 ,50,50,blackPen,whiteBrush);
}

game.cpp

#include "game.h"
#define DEBUG 0

game::game(){
    game_delay = 1000;
    game_complete = false;
    turn_complete = true;
    for(int i = 0; i < 16; ++i){
         player_positions.push_back(-1);
    }
    color = 3;
}

void game::reset(){
    game_complete = false;
    turn_complete = true;
    for(auto i : player_positions){
        i = -1;
    }
    color = 3;
}


int game::rel_to_fixed(int relative_piece_index){
    return relative_piece_index + color * 4;
}

int game::isStar(int index){
    if(index == 5  ||
       index == 18 ||
       index == 31 ||
       index == 44){
        return 6;
    } else if(index == 11 ||
              index == 24 ||
              index == 37 ||
              index == 50){
        return 7;
    }
    return 0;
}

int game::isOccupied(int index){ //returns number of people of another color
    int number_of_people = 0;

    if(index != 99){
        for(size_t i = 0; i < player_positions.size(); ++i){
            if(i < color*4 || i >= color*4 + 4){        //Disregard own players
                if(player_positions[i] == index){
                    ++number_of_people;
                }
            }
        }
    }
    return number_of_people;
}

bool game::isGlobe(int index){
    if(index < 52){     //check only the indexes on the board, not in the home streak
        if(index % 13 == 0 || (index - 8) % 13 == 0 || isOccupied(index) > 1){  //if more people of the same team stand on the same spot it counts as globe
            return true;
        }
    }
    return false;
}

void game::send_them_home(int index){
    for(size_t i = 0; i < player_positions.size(); ++i){
        if(i < color*4 || i >= color*4 + 4){        //this way we don't skip one player position
            if(player_positions[i] == index){
                player_positions[i] = -1;
            }
        }
    }
}

void game::move_start(int fixed_piece){
    if(dice_result == 6 && player_positions[fixed_piece] < 0){
        player_positions[fixed_piece] = color*13; //move me to start
        send_them_home(color*13); //send pieces home if they are on our start
    }
}

int game::next_turn(unsigned int delay = 0){
    if(game_complete){
        return 0;
    }
    switch(color){
        case 0:
        case 1:
        case 2:
            ++color;
            break;
        case 3:
        default:
            color = 0;
            break;
    }
    global_color = color;
    rollDice();
    relative.dice = getDiceRoll();
    relative.pos = relativePosition();
    emit set_color(color);
    emit set_dice_result(dice_result);

    msleep(delay);
    switch(color){
        case 0:
            emit player1_start(relative);
            break;
        case 1:
            emit player2_start(relative);
            break;
        case 2:
            emit player3_start(relative);
            break;
        case 3:
            emit player4_start(relative);
        default:
            break;
    }

    return 0;
}

void game::movePiece(int relative_piece){
    int fixed_piece = rel_to_fixed(relative_piece);     //index of the piece in player_positions
    int modifier = color * 13;
    int relative_pos = player_positions[fixed_piece];
    int target_pos = 0;
    if(player_positions[fixed_piece] == -1){        //if the selected piece is in the safe house, try to move it to start
        move_start(fixed_piece);
    } else {
        //convert to relative position
        if(relative_pos == 99){
            std::cout << "I tought this would be it ";
        } else if(relative_pos < modifier) {
            relative_pos = relative_pos + 52 - modifier;
        } else if( relative_pos > 50) {
            relative_pos = relative_pos - color * 5 - 1;
        } else {//if(relative >= modifier)
            relative_pos = relative_pos - modifier;
        }
        if(DEBUG) std::cout << "color: " << color << " pos: " << relative_pos << " + " << dice_result << " = " << relative_pos + dice_result;
        //add dice roll
        relative_pos += dice_result;    //this is relative position of the selected token + the dice number

        int jump = isStar(relative_pos); //return 0 | 6 | 7
        if(jump){
            if(jump + relative_pos == 57){
                relative_pos = 56;
            } else {
                relative_pos += jump;
            }
        }
        //special case checks
        if(relative_pos > 56 && relative_pos < 72){ // go back
            target_pos = 56-(relative_pos-56) + color * 5 + 1; //If the player moves over the goal, it should move backwards
        }else if(relative_pos == 56 || relative_pos >= 99){
            target_pos = 99;
        }else if(relative_pos > 50){ // goal stretch
            target_pos = relative_pos + color * 5 + 1;
        } else {
            int new_pos = relative_pos + color * 13;
            if(new_pos < 52){
                target_pos = new_pos;
            } else { //wrap around
                target_pos = new_pos - 52;  //this is the global position wrap around at the green entry point
            }
        }
        //check for game stuff

        if(isOccupied(target_pos)){
            if(isGlobe(target_pos)){
                target_pos = -1; //send me home
            } else {
                send_them_home(target_pos);
            }
        }
        if(DEBUG) std::cout << " => " << target_pos << std::endl;
        player_positions[fixed_piece] = target_pos;
    }
    std::vector<int> new_relative = relativePosition();
    switch(color){
        case 0:
            emit player1_end(new_relative);
            break;
        case 1:
            emit player2_end(new_relative);
            break;
        case 2:
            emit player3_end(new_relative);
            break;
        case 3:
            emit player4_end(new_relative);
        default:
            break;
    }
    emit update_graphics(player_positions);
}

std::vector<int> game::relativePosition(){
    std::vector<int> relative_positons;
    int modifier = color * 13;

    //from start id to end
    for(int i = color*4; i < player_positions.size(); ++i){
        relative_positons.push_back(player_positions[i]);
    }
    //from 0 to start id
    for(int i = 0; i < color*4; ++i){
        relative_positons.push_back(player_positions[i]);
    }


    for(size_t i = 0; i < relative_positons.size(); ++i){
        if(relative_positons[i] == 99 || relative_positons[i] == -1){
            relative_positons[i] = (relative_positons[i]);
        } else if(relative_positons[i] < modifier) {
            relative_positons[i] = (relative_positons[i]+52-modifier);
        } else if(relative_positons[i] > 50) {
            relative_positons[i] = (relative_positons[i]-color*5-1);
        } else if(relative_positons[i] > modifier) {
            relative_positons[i] = (relative_positons[i]-modifier);
        }
    }
    return std::move(relative_positons);
}

void game::turnComplete(bool win){
    game_complete = win;
    turn_complete = true;
    if(game_complete){
        std::cout << "player: " << color << " won" << std::endl;
        emit declare_winner(color);
    }
}

void game::run() {
    if(DEBUG) std::cout << "color:     relative pos => fixed\n";
    while(!game_complete){
        if(turn_complete){
            turn_complete = false;
            msleep(game_delay/4);
            next_turn(game_delay - game_delay/4);
        }
    }
    emit close();
    QThread::exit();
}

ludo_player.cpp

    #include "ludo_player.h"
#include <random>


ludo_player::ludo_player(){
}

int ludo_player::make_decision(){
    if(dice_roll == 6){
        for(int i = 0; i < 4; ++i){
            if(pos_start_of_turn[i]<0){
                return i;
            }
        }
        for(int i = 0; i < 4; ++i){
            if(pos_start_of_turn[i]>=0 && pos_start_of_turn[i] != 99){
                return i;
            }
        }
    } else {
        for(int i = 0; i < 4; ++i){
            if(pos_start_of_turn[i]>=0 && pos_start_of_turn[i] != 99){
                return i;
            }
        }
        for(int i = 0; i < 4; ++i){ //maybe they are all locked in
            if(pos_start_of_turn[i]<0){
                return i;
            }
        }
    }
    return -1;
}

void ludo_player::start_turn(positions_and_dice relative){
    pos_start_of_turn = relative.pos;
    dice_roll = relative.dice;
    int decision = make_decision();
    emit select_piece(decision);
}

void ludo_player::post_game_analysis(std::vector<int> relative_pos){
    pos_end_of_turn = relative_pos;
    bool game_complete = true;
    for(int i = 0; i < 4; ++i){
        if(pos_end_of_turn[i] < 99){
            game_complete = false;
        }
    }
    emit turn_complete(game_complete);
}

ludo_player_random.cpp

#include "ludo_player_random.h"

ludo_player_random::ludo_player_random(){
}

int ludo_player_random::make_decision(){
    std::vector<int> valid_moves;
    if(dice_roll == 6){
        for(int i = 0; i < 4; ++i){
            if(pos_start_of_turn[i]<0){
                valid_moves.push_back(i);
            }
        }
    }
    for(int i = 0; i < 4; ++i){
        if(pos_start_of_turn[i]>=0 && pos_start_of_turn[i] != 99){
            valid_moves.push_back(i);
        }
    }
    if(valid_moves.size()==0){
        for(int i = 0; i < 4; ++i){
            if(pos_start_of_turn[i] != 99){
                valid_moves.push_back(i);
            }
        }
    }
    std::random_device rd;
    std::mt19937 gen(rd());
    std::uniform_int_distribution<> piece(0, valid_moves.size()-1);
    int select = piece(gen);
    return valid_moves[select];
}

void ludo_player_random::start_turn(positions_and_dice relative){
    pos_start_of_turn = relative.pos;
    dice_roll = relative.dice;
    int decision = make_decision();
    emit select_piece(decision);
}

void ludo_player_random::post_game_analysis(std::vector<int> relative_pos){
    pos_end_of_turn = relative_pos;
    bool game_complete = true;
    for(int i = 0; i < 4; ++i){
        if(pos_end_of_turn[i] < 99){
            game_complete = false;
        }
    }
    emit turn_complete(game_complete);
}

player_q_learning.cpp

http://pastebin.com/bjwFDLgj

player_q_learning.h

http://pastebin.com/zUrnvdsL

I can't add the .h due to body character limit upto 30000 chars. I hope the .cpp gives an idea of how the .h files are constructed..


Solution

  • You declared calc_input to be a signal, so you must not implement it. It's Qt that provides its implementation (in the MOC-generated file), such that when it is emitted it calls the slots that have been connected to it.

    If you didn't intend it to be a signal (as it seems to me, given that you never connect nor emit it), move its declaration outside the signals: section, so that it becomes a "regular" method.