QObject::connect: No such signal progressbarV::keyReleaseEvent() - c++

I am trying to create a project in which I have a progressbarV class which creates a QProgressBar. I am calling this class in my mainWindow. My aim is to navigate to another screen when I click on the progressbar. I tried to implement KeyRleaseEvent for this purpose, but no matter what I do, I keep getting the error "QObject::connect: No such signal progressbarV::keyReleaseEvent()". I would much appreciate any help I could get to resolve this issue.
Please find my code below:-
mainwindow.h
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include <QWidget>
#include <QProgressBar>
#include <QLabel>
#include <QPixmap>
#include <QPushButton>
#include <QtWidgets>
#include <QProcess>
#include "headerfiles/progressbarV.h"
#include "headerfiles/redzonesettingsscreen.h"
class progressbarH;
class redZoneSettingsScreen;
class MainWindow : public QMainWindow//,public QProcess
{
Q_OBJECT
private:
progressbarV *progressbar_V_left;
public:
MainWindow();
~MainWindow();
void GetObjects(redZoneSettingsScreen *);
private slots:
void handleSettingsButtonPressed();
/*protected:
virtual void keyReleaseEvent(QKeyEvent *); //Q_DECL_OVERRIDE;*/
};
#endif // MAINWINDOW_H
mainwindow.cpp
#include "headerfiles/mainwindow.h"
redZoneSettingsScreen *gotoSettingsScreen;
MainWindow::MainWindow()
{
progressbar_V_left = new progressbarV;
progressbar_V_left->setParent(this);
progressbar_V_left->setGeometry(350,200,90,450);
progressbar_V_left->setTitle("Height");
progressbar_V_left->setData(labelCurHeight->getDataValue());
progressbar_V_left->setMinVal(0);
progressbar_V_left->setMaxVal(labelMaxHeight->getDataValue());
connect(progressbar_V_left, SIGNAL (keyReleaseEvent()), this, SLOT
(handleSettingsButtonPressed()));
}
MainWindow::~MainWindow()
{
delete progressbar_V_left;
}
void MainWindow::GetObjects(redZoneSettingsScreen *button)
{
gotoSettingsScreen = button;
}
void MainWindow::handleSettingsButtonPressed()
{
gotoSettingsScreen->hide();
gotoSettingsScreen->show();
this->hide();
}
/*void MainWindow::keyReleaseEvent(QKeyEvent *event)
{
}*/
progressbarV.h
#ifndef PROGRESSBARV_H
#define PROGRESSBARV_H
#include <QWidget>
#include <QProgressBar>
#include <QLabel>
#include <QPixmap>
class progressbarV: public QWidget
{
Q_OBJECT
private:
QProgressBar *progressbar_V;
QLabel *labelRedDanger, *labelYellowWarning;
float maxScaledHeight, redZoneScaledHeight, yellowZoneScaledHeight;
int spn, spn_value;
QString title;
int data;
short minVal;
short maxVal;
public:
progressbarV();
~progressbarV();
void setSPN(int);
int getSPN();
void setSPN_Value(int);
int getSPN_Value();
void setTitle(QString);
QString getTitle();
void setData(int);
int getData();
void setMinVal(short);
short getMinVal();
void setMaxVal(short);
short getMaxVal();
/*void setLowError(short);
short getLowError();
void setLowWarning(short);
short getLowWarning();
void setHighError(short);
short getHighError();
void setHighWarning(short);
short getHighWarning();*/
QProgressBar* getProgressBarV();
protected:
void keyReleaseEvent(QKeyEvent *); //Q_DECL_OVERRIDE;
};
#endif // PROGRESSBARH_H
progressbarV.cpp
#include "headerfiles/progressbarV.h"
progressbarV::progressbarV()
{
progressbar_V = new QProgressBar;
progressbar_V->setParent(this);
progressbar_V->setStyleSheet("QProgressBar{ border: solid grey; border-
width: 6; border-radius: 12; text-align: center;},
QProgressBar::chunk{background-color: limegreen; width: 0px; margin:
0px;}");
progressbar_V->setGeometry(2,0,50,200);
progressbar_V->setOrientation(Qt::Vertical);
maxScaledHeight = (200*100)/120;
redZoneScaledHeight = 200 - ((maxScaledHeight*105)/100);
yellowZoneScaledHeight = 200 - ((maxScaledHeight*90)/100);
QPixmap mypixRed(":/images/images/redZone.png");
labelRedDanger = new QLabel;
labelRedDanger->setParent(this);
labelRedDanger->setGeometry(8,redZoneScaledHeight,38,3);
labelRedDanger->setPixmap(mypixRed);
QPixmap mypixYellow(":/images/images/yellowZone.png");
labelYellowWarning = new QLabel;
labelYellowWarning->setParent(this);
labelYellowWarning->setGeometry(8,yellowZoneScaledHeight,38,3);
labelYellowWarning->setPixmap(mypixYellow);
}
progressbarV::~progressbarV()
{
delete progressbar_V;
delete labelRedDanger;
delete labelYellowWarning;
}
void progressbarV::setSPN(int val)
{
spn = val;
}
int progressbarV::getSPN()
{
return spn;
}
void progressbarV::setSPN_Value(int val)
{
spn_value = val;
}
int progressbarV::getSPN_Value()
{
return spn_value;
}
void progressbarV::setTitle(QString mTitle)
{
title = mTitle;
}
QString progressbarV::getTitle()
{
return title;
}
void progressbarV::setData(int mData)
{
data = mData;
progressbar_V->setValue(data);
}
int progressbarV::getData()
{
return data;
}
void progressbarV::setMinVal(short mMinVal)
{
minVal = mMinVal;
progressbar_V->setMinimum(minVal);
}
short progressbarV::getMinVal()
{
return minVal;
}
void progressbarV::setMaxVal(short mMaxVal)
{
maxVal = mMaxVal;
progressbar_V->setMaximum(maxVal);
}
short progressbarV::getMaxVal()
{
return maxVal;
}
QProgressBar *progressbarV::getProgressBarV()
{
return progressbar_V;
}
void progressbarV::keyReleaseEvent(QKeyEvent *event)
{
}
Since I am new to QT, kindly give me solutions in the form of code snippets
Thanks in advance,
Sam

you need to declare keyReleaseEvent as a public SLOT
public slots:
void keyReleaseEvent(QKeyEvent *); //Q_DECL_OVERRIDE;
so that QT can connect to it using the old connection style.

Related

Segfault on clicking on QFrame

This topic might be little lengthy since I have to explain the premise before procceding with the probleme at hand.Firstly my main goal is to have this application in which the user is capable of drag-n-dropping commands from a toolbar in order to form workflows which are send and executed on a remote server.Currently i am working on the client part in qt and it is driving me nuts.
This is my code:
draglabel.h
#ifndef DRAGLABEL_H
#define DRAGLABEL_H
#include <QLabel>
class QDragEnterEvent;
class QDragMoveEvent;
class QFrame;
class DragLabel : public QLabel
{
public:
DragLabel(const QString &text, QWidget *parent);
QString labelText() const;
private:
QString m_labelText;
};
#endif // DRAGLABEL_H
draglabel.c
#include "draglabel.h"
#include <QtWidgets>
DragLabel::DragLabel(const QString &text, QWidget *parent)
: QLabel(parent)
{
QFontMetrics metric(font());
QSize size = metric.size(Qt::TextSingleLine, text);
QImage image(size.width() + 12, size.height() + 12, QImage::Format_ARGB32_Premultiplied);
image.fill(qRgba(0, 0, 0, 0));
QFont font;
font.setStyleStrategy(QFont::ForceOutline);
QLinearGradient gradient(0, 0, 0, image.height()-1);
gradient.setColorAt(0.0, Qt::white);
gradient.setColorAt(0.2, QColor(200, 200, 255));
gradient.setColorAt(0.8, QColor(200, 200, 255));
gradient.setColorAt(1.0, QColor(127, 127, 200));
QPainter painter;
painter.begin(&image);
painter.setRenderHint(QPainter::Antialiasing);
painter.setBrush(gradient);
painter.drawRoundedRect(QRectF(0.5, 0.5, image.width()-1, image.height()-1),
25, 25, Qt::RelativeSize);
painter.setFont(font);
painter.setBrush(Qt::black);
painter.drawText(QRect(QPoint(6, 6), size), Qt::AlignCenter, text);
painter.end();
setPixmap(QPixmap::fromImage(image));
m_labelText = text;
}
QString DragLabel::labelText() const
{
return m_labelText;
}
dragwidget.h
#ifndef DRAGWIDGET_H
#define DRAGWIDGET_H
#include <QWidget>
#include <QFrame>
#include <vector>
#include <set>
#include "draglabel.h"
using namespace std;
class QDragEnterEvent;
class QDropEvent;
class DragWidget : public QFrame
{
public:
DragWidget(QWidget *parent = nullptr);
void setMode(int desiredMode);
void changePairingMode();
void showAvailableCommands();
void initDrawingLayout();
vector<tuple<QString,QString>> actCommands;
vector<tuple<QString,QString>> execCommands;
vector<pair<int,int>>waitingForPair;
int pairingMode=0;
QFrame*drawingCon;
private:
int widgetMode=1;
protected:
void dragEnterEvent(QDragEnterEvent *event) Q_DECL_OVERRIDE;
void dragMoveEvent(QDragMoveEvent *event) Q_DECL_OVERRIDE;
void dropEvent(QDropEvent *event) Q_DECL_OVERRIDE;
void mousePressEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
};
#endif // DRAGWIDGET_H
dragwidget.cpp
#include "draglabel.h"
#include "dragwidget.h"
#include "arrowhead.h"
#include <QtWidgets>
#include <QWidget>
#include <QFrame>
#include <QColor>
#include <tuple>
using namespace std;
static inline QString dndProcMimeType() { return QStringLiteral("application/x-fridgemagnet"); }
DragWidget::DragWidget(QWidget *parent)
: QFrame(parent)
{
drawingCon=new QFrame(this);
QPalette newPalette = palette();
newPalette.setColor(QPalette::Window, Qt::white);
setPalette(newPalette);
setWindowTitle(tr("Drag-and-Drop"));
setMinimumSize(300,300);
setAcceptDrops(true);
setFrameStyle(QFrame::Sunken | QFrame::StyledPanel);
drawingCon->setPalette(newPalette);
drawingCon->setWindowTitle(tr("Drag-and-Drop"));
drawingCon->setMinimumSize(350,350);
drawingCon->setAcceptDrops(false);
drawingCon->show();
}
void DragWidget::dragEnterEvent(QDragEnterEvent *event)
{
if (event->mimeData()->hasFormat(dndProcMimeType())) {
if (children().contains(event->source())) {
event->setDropAction(Qt::MoveAction);
event->accept();
} else {
event->acceptProposedAction();
}
} else if (event->mimeData()->hasText()) {
event->acceptProposedAction();
} else {
event->ignore();
}
}
void DragWidget::dragMoveEvent(QDragMoveEvent *event)
{
if (event->mimeData()->hasFormat(dndProcMimeType())) {
if (children().contains(event->source())) {
if(widgetMode==1)
{
event->setDropAction(Qt::MoveAction);
event->accept();
}
else {
event->ignore();
}
} else {
if(widgetMode==1)
{
event->acceptProposedAction();
}
else
{
if(widgetMode==1)
{
event->accept();
}
else {
event->ignore();
}
}
}
} else if (event->mimeData()->hasText()) {
event->acceptProposedAction();
} else {
event->ignore();
}
}
void DragWidget::dropEvent(QDropEvent *event)
{
if (event->mimeData()->hasFormat(dndProcMimeType())) {
const QMimeData *mime = event->mimeData();
QByteArray itemData = mime->data(dndProcMimeType());
QDataStream dataStream(&itemData, QIODevice::ReadOnly);
QString text;
QPoint offset;
dataStream >> text >> offset;
DragLabel *newLabel = new DragLabel(text, this);
newLabel->move(event->pos() - offset);
newLabel->show();
newLabel->setAttribute(Qt::WA_DeleteOnClose);
if (event->source() == this) {
event->setDropAction(Qt::MoveAction);
event->accept();
} else {
tuple<QString,QString> addTest;
addTest=make_tuple(text,"");
actCommands.push_back(make_tuple(text,""));
for(auto it:actCommands)
qDebug()<<get<0>(it)<<" "<<get<1>(it);
event->acceptProposedAction();
}
} else {if (event->mimeData()->hasText()) {
if(widgetMode==1)
{
event->accept();
}
else {
event->ignore();
}
event->acceptProposedAction();
}
}
}
void DragWidget::mousePressEvent(QMouseEvent *event)
{
DragLabel *child = static_cast<DragLabel*>(childAt(event->pos()));
if(!pairingMode){
if (!child)
return;
QPoint hotSpot = event->pos() - child->pos();
if(widgetMode==1)
qDebug()<<child->labelText();
QByteArray itemData;
QDataStream dataStream(&itemData, QIODevice::WriteOnly);
dataStream << child->labelText() << QPoint(hotSpot);
QMimeData *mimeData = new QMimeData;
mimeData->setData(dndProcMimeType(), itemData);
mimeData->setText(child->labelText());
QDrag *drag = new QDrag(this);
drag->setMimeData(mimeData);
drag->setPixmap(*child->pixmap());
drag->setHotSpot(hotSpot);
child->hide();
if (drag->exec(Qt::MoveAction | Qt::CopyAction, Qt::CopyAction) == Qt::MoveAction)
child->close();
else {
child->show();
}
}
else {
if(widgetMode==1)
{
DragLabel *child = static_cast<DragLabel*>(childAt(event->pos()));
if (!child)
return;
qDebug()<<"Facem pair cu:"<<child->labelText();
waitingForPair.push_back(make_pair(child->x(),child->y()));
if(waitingForPair.size()==2) {
ArrowHead *line=new ArrowHead(waitingForPair.at(0).first,waitingForPair.at(0).second,waitingForPair.at(1).first,waitingForPair.at(1).second,drawingCon);
line->show();
waitingForPair.erase(waitingForPair.begin(),waitingForPair.begin()+1);
qDebug()<<"Tragem linie";
}
}
}
}
void DragWidget::setMode(int desiredMode)
{
widgetMode=desiredMode;
}
void DragWidget::showAvailableCommands()
{
DragLabel*grep=new DragLabel("grep",this);
grep->move(this->x(),this->y());
grep->show();
DragLabel*cat=new DragLabel("cat",this);
grep->move(this->x()+40,this->y());
cat->show();
DragLabel*wc=new DragLabel("wc",this);
wc->move(this->x()+90,this->y());
wc->show();
}
void DragWidget::changePairingMode()
{
if(pairingMode==1)
pairingMode=0;
else {
pairingMode=1;
}
}
mainWindow.h
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include <QPushButton>
#include <QTextEdit>
#include "dragwidget.h"
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = nullptr);
protected:
virtual void closeEvent(QCloseEvent *event) override;
private slots:
void handleButton();
void closeAppButton();
void pairButton();
private:
QPushButton *executeCode;
QPushButton *pairCommands;
QPushButton *closeApp;
QTextEdit *inputUser;
QTextEdit *outputServer;
DragWidget * commandLayout=new DragWidget();
DragWidget * availableLayout=new DragWidget();
};
#endif // MAINWINDOW_H
mainWindow.cpp
#include "mainwindow.h"
#include "draglabel.h"
#include "dragwidget.h"
#include <QCoreApplication>
#include <QApplication>
#include <QHBoxLayout>
#include <QPushButton>
#include <QCloseEvent>
#include <QTextEdit>
#include <QFrame>
#include <QDebug>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
executeCode=new QPushButton("Execute");
closeApp=new QPushButton("Close");
pairCommands=new QPushButton("Pair");
connect(closeApp, SIGNAL (released()), this, SLOT (closeAppButton()));
connect(pairCommands, SIGNAL (released()), this, SLOT (pairButton()));
void pairButton();
QHBoxLayout * horizontalLayout=new QHBoxLayout();
commandLayout->setMode(1);
availableLayout->setMode(2);
horizontalLayout->addWidget(commandLayout);
horizontalLayout->addWidget(availableLayout);
availableLayout->showAvailableCommands();
QVBoxLayout*inputBoxes=new QVBoxLayout();
inputUser=new QTextEdit();
outputServer=new QTextEdit();
inputBoxes->addWidget(inputUser);
inputBoxes->addWidget(outputServer);
horizontalLayout->addLayout(inputBoxes);
QVBoxLayout*withButtons=new QVBoxLayout();
withButtons->addLayout(horizontalLayout);
withButtons->addWidget(pairCommands);
withButtons->addWidget(executeCode);
withButtons->addWidget(closeApp);
withButtons->addWidget(new QFrame());
setCentralWidget(new QWidget);
centralWidget()->setLayout(withButtons);
}
void MainWindow::handleButton()
{
}
void MainWindow::closeEvent(QCloseEvent *event)
{
event->accept();
}
void MainWindow::closeAppButton()
{
exit(EXIT_SUCCESS);
}
void MainWindow::pairButton()
{
commandLayout->changePairingMode();
qDebug()<<commandLayout->pairingMode;
}
Note:It might seem idiotic but i have the same class for the "toolbar",from where you're supposed to drag commands and also for part where you are supposed to drag commands and pair them.
This is mostly modified code of the fridge-magnets example on the qt website.
The problem that is giving headaches is drawing lines between dragwidget, I have tried drawing everything in the same QFrame but that proved to be disastrous since the whole pixelMap of the instance dragWidget is overwritten at every draw.The solution with which i came up is to overlay a supplimentary QFrame over my dragWidget in order to draw lines there and everyone to be happy,but as always misfortune strikes at every step.When i am trying to click on the command widget everything's fine but clicking on anything other than a DragLabel results in a segfault due to clicking on the QFrame due to childAt() returning the address of the QFrame overlayed on the first instance of dragWdiget();
My main question is: How can i overcome this obstacle
You should use qobject_cast instead of static_cast.
Add Q_OBJECT macro in each class declaration:
class DragLabel : public QLabel
{
Q_OBJECT
public:
//... class declaration ...
}
class DragWidget : public QFrame
{
Q_OBJECT
public:
//... class declaration ...
}
Then use qobject_cast instead of static_cast for childAt(), for example :
DragLabel *child = qobject_cast<DragLabel*>(childAt(event->pos()));
if(!child){
....
}

Passing QImage to QML, problemr with Image Provider

I'm trying to pass QImage to QML using Image Provider but all the time I'm getting error:
Failed to get image from provider: image://provider/im.
I'm writing a simple Media Player app, and I want to display cover image from Media Player metadata:
QVariant variant = _cpp_player->metaData(QMediaMetaData::CoverArtImage);
QImage image = variant.value();
I'm sending that QImage by signal, which is connected with slot in Image Provider class. That signal also invokes reload function in main.qml.
Here is the entire code:
main.cpp
#include <QUrl>
#include "player.h"
#include "imageprovider.h"
#include "imageprocessor.h"
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QApplication app(argc, argv);
Player player;
QQmlApplicationEngine engine;
ImageProvider *imageProvider = new ImageProvider();
engine.rootContext()->setContextProperty("player", &player);
engine.addImageProvider("provider", imageProvider);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;
return app.exec();
}
imageprovider.h
#ifndef IMAGEPROVIDER_H
#define IMAGEPROVIDER_H
#include <QObject>
#include <QImage>
#include <QQuickImageProvider>
class ImageProvider : public QObject, public QQuickImageProvider
{
Q_OBJECT
public:
explicit ImageProvider(): QQuickImageProvider(QQuickImageProvider::Image) {}
QImage requestImage(const QString &id, QSize *size, const QSize &requestedSize);
public slots:
void imageChanged(QImage image);
private:
QImage _image;
};
#endif // IMAGEPROVIDER_H
imageprovider.cpp
#include "imageprovider.h"
#include <QDebug>
QImage ImageProvider::requestImage(const QString &id, QSize *size, const QSize &requestedSize)
{
if(_image.isNull())
{
qDebug() << "Image is null";
}
return _image;
}
void ImageProvider::imageChanged(QImage image)
{
_image = image;
}
player.h
#ifndef PLAYER_H
#define PLAYER_H
#include <QObject>
#include <QMediaPlayer>
#include <QMediaPlaylist>
#include <QMediaObject>
#include <QMediaMetaData>
#include <QList>
#include <QStringList>
#include "imageprovider.h"
class Player : public QObject
{
Q_OBJECT
Q_PROPERTY(QString songName READ songName WRITE setSongName NOTIFY songNameChanged)
Q_PROPERTY(QStringList list READ list NOTIFY playListUpdated)
QMediaPlayer *_cpp_player;
QMediaPlaylist *_cpp_playlist;
QString _songName;
QStringList strList;
ImageProvider *_cpp_provider;
public:
explicit Player(QObject *parent = nullptr);
QString songName() const;
QStringList list() const;
void setSongName(const QString &songName);
void addToPlayList(const QList<QUrl> &url);
Q_INVOKABLE void openFileDialog();
Q_INVOKABLE void positionChangedFromQML(const int &val);
Q_INVOKABLE void playListPositionChanged(const int &index);
public slots:
void playButtonClicked();
void pauseButtonClicked();
void stopButtonClicked();
void nextButtonClicked();
void previousButtonClicked();
void currentPlayListPosition(int index);
void positionChanged(qint64 pos);
void durationChanged(qint64 dur);
void stateChanged(QMediaPlayer::MediaStatus state);
signals:
void songNameChanged();
void posChanged(qint64 pos);
void songDuration(qint64 dur);
void songTime1(QString tim);
void songTime2(QString tim2);
void playListIsNotEmpty();
void playListUpdated();
void imageChanged(QImage image);
};
#endif // PLAYER_H
player.cpp
#include "player.h"
#include <QMediaPlayer>
#include <QMediaPlaylist>
#include <QMediaContent>
#include <QtDebug>
#include <QDateTime>
#include <QFileDialog>
class QMediaPlaylist;
class QMediaPlayer;
Player::Player(QObject *parent) : QObject(parent)
{
_cpp_player = new QMediaPlayer;
_cpp_playlist = new QMediaPlaylist;
_cpp_provider = new ImageProvider;
_cpp_player->setPlaylist(_cpp_playlist);
connect(_cpp_player, &QMediaPlayer::durationChanged, this, &Player::durationChanged);
connect(_cpp_player, &QMediaPlayer::positionChanged, this, &Player::positionChanged);
connect(this, &Player::imageChanged, _cpp_provider, &ImageProvider::imageChanged);
}
void Player::addToPlayList(const QList<QUrl> &url)
{
for (auto &el: url) {
_cpp_playlist->addMedia(el);
}
}
Q_INVOKABLE void Player::openFileDialog()
{
QFileDialog fileDialog;
fileDialog.setFileMode(QFileDialog::ExistingFiles);
fileDialog.setDirectory("/home");
QStringList formatList = {"*.mp3", "*.flac", "*.wav"};
fileDialog.setNameFilters(formatList);
if (fileDialog.exec() == QDialog::Accepted)
{
addToPlayList(fileDialog.selectedUrls());
for(int i = 0; i<fileDialog.selectedUrls().size(); ++i){
strList.append(fileDialog.selectedUrls().at(i).fileName());
emit playListIsNotEmpty();
emit playListUpdated();
}
}
}
QString Player::songName() const
{
return _songName;
}
QStringList Player::list() const
{
return strList;
}
void Player::setSongName(const QString &songName)
{
_songName = songName;
emit songNameChanged();
}
void Player::currentPlayListPosition(int index)
{
if(index!=-1){
setSongName(_cpp_player->metaData(QMediaMetaData::Title).toString());
}
}
void Player::durationChanged(qint64 dur)
{
stateChanged(QMediaPlayer::LoadedMedia);
emit songDuration(dur);
}
void Player::stateChanged(QMediaPlayer::MediaStatus state)
{
if (state == QMediaPlayer::LoadedMedia){
if (_cpp_player->isMetaDataAvailable())
{
setSongName(_cpp_player->metaData(QMediaMetaData::Title).toString());
QVariant variant = _cpp_player->metaData(QMediaMetaData::CoverArtImage);
QImage image = variant.value<QImage>();
emit imageChanged(image);
}
else
{
qDebug() << "No metadata.";
}
}
}
Q_INVOKABLE void Player::positionChangedFromQML(const int &val)
{
_cpp_player->setPosition(val);
}
void Player::playListPositionChanged(const int &index)
{
_cpp_playlist->setCurrentIndex(index);
}
void Player::positionChanged(qint64 pos)
{
emit posChanged(pos);
emit songTime1(QDateTime::fromTime_t((uint)pos/1000).toUTC().toString("mm:ss"));
emit songTime2((QDateTime::fromTime_t((uint)((_cpp_player->duration()/1000) - pos/1000))).toUTC().toString("mm:ss"));
}
void Player::playButtonClicked()
{
if(!_cpp_playlist->isEmpty()){
_cpp_player->play();
}
}
void Player::pauseButtonClicked()
{
_cpp_player->pause();
}
void Player::stopButtonClicked()
{
_cpp_player->stop();
}
void Player::nextButtonClicked()
{
if(_cpp_playlist->nextIndex()!=-1){
_cpp_playlist->next();
}
else
{
_cpp_player->stop();
_cpp_player->play();
}
}
void Player::previousButtonClicked()
{
if(_cpp_playlist->previousIndex()!=-1){
_cpp_playlist->previous();
}
else{
_cpp_player->stop();
_cpp_player->play();
}
}
main.qml
import QtQuick 2.9
import QtQuick.Window 2.2
import QtQuick.Layouts 1.3
Window {
Connections{
target: player
onPosChanged:{
newSlider.value = pos
}
onSongDuration:{
newSlider.stepSize = 1000
newSlider.to = dur
}
onSongTime1: {
newSlider.time1 = tim;
}
onSongTime2:{
newSlider.time2 = tim2;
}
onPlayListIsNotEmpty:{
toolBar.playState = "playClicked"
}
onImageChanged:{
cover.reload();
}
}
visible: true
width: 900
height: 600
title: "Media Player"
ToolBar {
id: toolBar
}
PlayListView{
id: playList
visible: false
}
AnotherSlider{
id:newSlider
anchors.bottom: toolBar.top
anchors.bottomMargin: 40
anchors.horizontalCenter: parent.horizontalCenter
sliderWidth: toolBar.width - 40
onMoved: {
player.positionChangedFromQML(value)
}
}
Rectangle{
id: albumImage
width: newSlider.width/2 - 10
height: newSlider.width/2 - 10
property int imageId: 0
Image {
id: cover
anchors.fill:albumImage
source: "image://provider/im"
function reload(){
var oldSource = source;
source = ""
source = oldSource
}
}
color: "white"
border.color: "black"
border.width: 5
radius: 5
anchors.left: newSlider.left
anchors.bottom: newSlider.top
anchors.bottomMargin: 40
}
}
What is wrong? How can I solve that?

Dynamic QLabel misplacing in UI

I'm trying to create a program that accepts images through drag and drop and shows those images on my UI, then I want to rename them and save them.
I got the drag and drop to work, but I have some issues with my Image placement and I can't seem to find where I'm making my mistake.
In the image you see my UI during runtime, in the top left you can see a part of the image I dragged into the green zone(this is my drag and drop zone that accepts images). The position I actually want it to be in should be the red square. The green zone is a Dynamic created object called Imagehandler that I created to handle the drag and drop of the images. The Red square is my own class that inherits from QLabel, I called it myiconclass. This class should hold the actual image data.
I think my mistake has to do with the layouts, but I can't see it.
Could I get some help with this please?
Imagehandler.h
#ifndef IMAGEHANDLER_H
#define IMAGEHANDLER_H
#include <QObject>
#include <QWidget>
#include <QLabel>
#include <QDrag>
#include <QDragEnterEvent>
#include <QMimeData>
#include <QList>
#include <QDebug>
//this class is designed to help me take in the images with drag and drop
class ImageHandler : public QWidget
{
Q_OBJECT
public:
explicit ImageHandler(QWidget *parent = nullptr);
QList<QImage> getImageListMemory() const;
void setImageListMemory(const QList<QImage> &value);
QList<QUrl> getUrlsMemory() const;
void setUrlsMemory(const QList<QUrl> &value);
private:
//QWidget Icon;
QLabel Icon;
QList <QImage> imageListMemory;
QList <QUrl> urlsMemory;
protected:
void dragEnterEvent(QDragEnterEvent * event);
void dragLeaveEvent(QDragLeaveEvent * event);
void dragMoveEvent(QDragMoveEvent * event);
void dropEvent(QDropEvent * event);
signals:
void transferImageSignal(QList <QImage>);
public slots:
};
#endif // IMAGEHANDLER_H
mainwindow.h
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include <QImageReader>
#include <QList>
#include <QWidget>
#include <QLabel>
#include <myiconclass.h>
#include <imagehandler.h>
#include <QGridLayout>
#include <QDebug>
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
~MainWindow();
QList<QImage> getImageListMemory() const;
void setImageListMemory(const QList<QImage> &value);
private:
Ui::MainWindow *ui;
QLabel Icon;
QList <QImage> imageListMemory;
QList <QUrl> urlsMemory;
QList<QWidget *> labelList;
ImageHandler * ImageHandlerMemory;
QGridLayout * grid2;
QList <MyIconClass *> memory;
signals:
public slots:
void setIconSlot(QList <QImage>);
};
#endif // MAINWINDOW_H
myiconclass.h
#ifndef MYICONCLASS_H
#define MYICONCLASS_H
#include <QWidget>
#include <QLabel>
//this class is based on a Qlabel and is only made so it can help me with the actual images, gives me more members if I need it
class MyIconClass : public QLabel
{
Q_OBJECT
public:
explicit MyIconClass(QWidget *parent = nullptr);
int getMyNumber() const;
void setMyNumber(int value);
private:
int myNumber;
signals:
public slots:
};
#endif // MYICONCLASS_H
imagehandler.cpp
#include "imagehandler.h"
ImageHandler::ImageHandler(QWidget *parent) : QWidget(parent)
{
setAcceptDrops(true);
}
QList<QImage> ImageHandler::getImageListMemory() const
{
return imageListMemory;
}
void ImageHandler::setImageListMemory(const QList<QImage> &value)
{
imageListMemory = value;
}
QList<QUrl> ImageHandler::getUrlsMemory() const
{
return urlsMemory;
}
void ImageHandler::setUrlsMemory(const QList<QUrl> &value)
{
urlsMemory = value;
}
void ImageHandler::dragEnterEvent(QDragEnterEvent * event)
{
event->accept();
}
void ImageHandler::dragLeaveEvent(QDragLeaveEvent * event)
{
event->accept();
}
void ImageHandler::dragMoveEvent(QDragMoveEvent * event)
{
event->accept();
}
void ImageHandler::dropEvent(QDropEvent * event)
{
QList <QImage> imageList2;
QList <QUrl> urls;
QList <QUrl>::iterator i;
urls = event->mimeData()->urls();
//imageList.append(event->mimeData()->imageData());
foreach (const QUrl &url, event->mimeData()->urls())
{
QString fileName = url.toLocalFile();
qDebug() << "Dropped file:" << fileName;
qDebug()<<url.toString();
QImage img;
if(img.load(fileName))
{
imageList2.append(img);
}
}
emit transferImageSignal(imageList2);
this->setUrlsMemory(urls);
this->setImageListMemory(imageList2);
}
mainwindow.cpp
#include "mainwindow.h"
#include "ui_mainwindow.h"
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
ImageHandler * handler = new ImageHandler(this);
handler->show();
QGridLayout *grid = new QGridLayout;
grid->addWidget(handler, 0, 0);
ui->groupBoxIcon->setLayout(grid);
ImageHandlerMemory = handler;
//connect(handler,SIGNAL(handler->transferImageSignal(QList <QUrl>)),this,SLOT(setIconSlot(QList <QUrl>)));
connect(handler,SIGNAL(transferImageSignal(QList<QImage>)),this,SLOT(setIconSlot(QList<QImage>)));
}
MainWindow::~MainWindow()
{
delete ui;
}
QList<QImage> MainWindow::getImageListMemory() const
{
return imageListMemory;
}
void MainWindow::setImageListMemory(const QList<QImage> &value)
{
imageListMemory = value;
}
void MainWindow::setIconSlot(QList<QImage> images)
{
printf("succes!");
this->setImageListMemory(images); //save the images to memory
QGridLayout *grid = new QGridLayout; //create the grid layout I want my images to be in
// create counters to remember the row and column in the grid
int counterRow =0;
int counterColumn =0;
int counter3 =0;
int counterImages = 0;
//iterate over each image in the list
QList <QImage>::iterator x;
for(x = imageListMemory.begin(); x != imageListMemory.end(); x++)
{
MyIconClass * myLabel = new MyIconClass(this); //create an object of my own class (which is a Qlabel with an int member)
QPixmap pixmap(QPixmap::fromImage(*x)); //create a pixmap from the image in the iteration
myLabel->setPixmap(pixmap); //set the pixmap on my label object
myLabel->show();
memory.append(myLabel); //add it to the memory so I can recal it
counterImages++;
}
while(counter3 < images.count())
{
grid2->addWidget(memory.value(counter3), counterRow, counterColumn);
counterColumn++;
counter3++;
if(counterColumn >= 5)
{
counterRow++;
counterColumn =0;
}
}
if(ImageHandlerMemory->layout() == 0)
{
ImageHandlerMemory->setLayout(grid2);
}
}
myiconclass.cpp
#include "myiconclass.h"
MyIconClass::MyIconClass(QWidget *parent) : QLabel(parent)
{
}
int MyIconClass::getMyNumber() const
{
return myNumber;
}
void MyIconClass::setMyNumber(int value)
{
myNumber = value;
}
As Benjamin T said I had to change this:
MyIconClass * myLabel = new MyIconClass(this);
into this:
MyIconClass * myLabel = new MyIconClass(ImageHandlerMemory);
Thanks Benjamin!
PS, I also had to add this line in my mainwindow constructor:
grid2 = new QGridLayout;

Qt Unresolved External Symbol

I have classes, ImageLabel, and ChoiceLabel. ChoiceLabel inherits from ImageLabel. When I try to make a new ChoiceLabel, I get an Unresolved External Symbol error. Here are the relevant files:
imagelabel.h
#ifndef IMAGELABEL_H
#define IMAGELABEL_H
#include <QLabel>
class QPixmap;
class QStringList;
class QFileDialog;
class QResizeEvent;
class ImageLabel : public QLabel
{
Q_OBJECT
public:
explicit ImageLabel(QWidget *parent = 0);
protected:
virtual int heightForWidth( int width ) const;
virtual QSize sizeHint() const;
QPixmap scaledPixmap() const;
void setPixmap ( const QPixmap & );
void resizeEvent(QResizeEvent *);
private:
QPixmap pix;
};
#endif // IMAGELABEL_H
choicelabel.h
#ifndef CHOICELABEL_H
#define CHOICELABEL_H
class QStringList;
class ChoiceLabel : public ImageLabel
{
Q_OBJECT
public:
ChoiceLabel();
private:
QStringList *imageFiles;
void mousePressEvent(QMouseEvent *);
void keyPressEvent(QKeyEvent *);
void focusInEvent(QFocusEvent *);
void focusOutEvent(QFocusEvent *);
};
#endif // CHOICELABEL_H
mainwindow.cpp
#include "mainwindow.h"
#include "imagelabel.h"
#include "choicelabel.h"
#include <QGridLayout>
#include <qDebug>
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent)
{
choiceLabelA = new ChoiceLabel; //the problem occurs here
resultLabel = new ImageLabel;
centralWidget = new QWidget(this);
this->setCentralWidget(centralWidget);
gridLayout = new QGridLayout(centralWidget);
gridLayout->addWidget(resultLabel);
}
EDIT:
imagelabel.cpp
#include "imagelabel.h"
#include <QDebug>
ImageLabel::ImageLabel(QWidget *parent) :
QLabel(parent)
{
setMinimumSize(250,250);
setAlignment(Qt::AlignCenter | Qt::AlignCenter);
setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Ignored);
QPixmap initialPixmap(250, 250);
initialPixmap.fill(Qt::black);
setPixmap(initialPixmap);
}
void ImageLabel::setPixmap ( const QPixmap & p)
{
pix = p;
QLabel::setPixmap(scaledPixmap());
}
QPixmap ImageLabel::scaledPixmap() const
{
return pix.scaled(this->size(), Qt::KeepAspectRatio, Qt::SmoothTransformation);
}
int ImageLabel::heightForWidth( int width ) const
{
return pix.isNull() ? this->height() : ((qreal)pix.height()*width)/pix.width();
}
QSize ImageLabel::sizeHint() const
{
int w = this->width();
return QSize( w, heightForWidth(w) );
}
void ImageLabel::resizeEvent(QResizeEvent *)
{
if(!pix.isNull())
QLabel::setPixmap(scaledPixmap());
}
choicelabel.cpp
#include "choicelabel.h"
#include <QStringList>
#include <QFileDialog>
#include <QFrame>
ChoiceLabel::ChoiceLabel():
imageFiles()
{
setFocusPolicy(Qt::StrongFocus);
}
void ChoiceLabel::mousePressEvent(QMouseEvent *)
{
QFileDialog dialog(this);
dialog.setFileMode(QFileDialog::ExistingFiles);
dialog.setNameFilter("Images (*.png *.jpg)");
dialog.setDirectory("C:/Users/FrankFritz/Desktop/qt/uglypictures");
if (dialog.exec()){
imageFiles = dialog.selectedFiles();
QPixmap pixmap = imageFiles->first();
setPixmap(pixmap);
}
}
void ChoiceLabel::keyPressEvent(QKeyEvent *ev)
{
static int index(0);
if (ev->key() == Qt::Key_Right){
index = (index + 1) % imageFiles->length();
setPixmap( QPixmap(imageFiles->at(index)) );
}
if (ev->key() == Qt::Key_Left){
if (index == 0){
index = imageFiles->length() - 1;
}
else{
index = (index - 1) % imageFiles->length();
}
setPixmap( QPixmap(imageFiles->at(index)) );
}
}
void ChoiceLabel::focusInEvent(QFocusEvent *)
{
setFrameStyle(QFrame::StyledPanel);
}
void ChoiceLabel::focusOutEvent(QFocusEvent *)
{
setFrameStyle(QFrame::NoFrame);
}
Most probably
ChoiceLabel::ChoiceLabel():
imageFiles()
{
setFocusPolicy(Qt::StrongFocus);
}
ChoiceLabel::ChoiceLabel(QWidget *parent): ImageLabel(parent)
{
setFocusPolicy(Qt::StrongFocus);
}
Forgot to call the base class' constructor. Also forgot to specify a parent QWidget * for ChoiceLabel in its own constructor.
See What are the rules for calling the superclass constructor? for reference.

Qt: Subclassed spinbox does not count

I try to subclass a Qt spinbox so i can get the mouse event. The code compiles, the events are working, but the spinbox doesn't count up or down. I have set the min value to -9999 and max value to 9999, default value is 100. But if i click the up or down button, nothing happens.
NewSpinBox.h:
#ifndef NEWSPINBOX_H
#define NEWSPINBOX_H
#include <QObject>
#include <QWidget>
#include <QEvent>
#include <QMouseEvent>
#include <QSpinBox>
class NewSpinBox : public QSpinBox
{
Q_OBJECT
public:
NewSpinBox(QWidget *parent = 0);
~NewSpinBox();
public slots:
void mousePressEvent(QMouseEvent *mouseEvent);
void mouseReleaseEvent(QMouseEvent *mouseEvent);
};
#endif // NEWSPINBOX_H
NewSpinBox.cpp:
#include "newspinbox.h"
NewSpinBox::NewSpinBox(QWidget *parent) : QSpinBox(parent)
{
}
NewSpinBox::~NewSpinBox()
{
}
void NewSpinBox::mousePressEvent(QMouseEvent *mouseEvent)
{
if(mouseEvent->type() == QMouseEvent::MouseButtonRelease)
{
int i = 0;
i++;
}
}
void NewSpinBox::mouseReleaseEvent(QMouseEvent *mouseEvent)
{
if(mouseEvent->type() == QMouseEvent::MouseButtonRelease)
{
int i = 0;
i++;
}
}
Do I have to reimplement the count functions?
You must call the base class handler to get the default behavior:
void NewSpinBox::mousePressEvent(QMouseEvent *mouseEvent)
{
QSpinBox::mousePressEvent(mouseEvent);
// ... your code
}
void NewSpinBox::mouseReleaseEvent(QMouseEvent *mouseEvent)
{
QSpinBox::mouseReleaseEvent(mouseEvent);
// ... your code
}