This is a basic example that I need to get to work to use it in my project.
I need someone to help to destroy and rebuild an object on a button click. What I mean is:
//mainwindow.cpp
{//constructor
ui->setupUi(this);
/*private*/frame = new QFrame(ui->centralWidget);
/*private*/temp = new QPushButton(frame);
QPushButton ok = new QPushButton(ui->centralWidget);
ok->setGeometry(100,100,50,50);
connect(ok, SIGNAL(clicked()), SLOT(des()));
}
{//slot des()
temp->~QPuhsButton();
temp = new QPushButton(frame);
}
See, all I need is temp to be destroyed and rebuilt.
The line temp = new QPushButton(frame); is not working because with or without it, temp disappears from the layout, meaning temp->~QPuhsButton(); is working.
Now, the reason this is bothering me is because this works:
{//constructor
ui->setupUi(this);
frame = new QFrame(ui->centralWidget);
temp = new QPushButton(frame);
temp->~QPuhsButton();
temp = new QPushButton(frame);
/*QPushButton ok = new QPushButton(ui->centralWidget);
ok->setGeometry(100,100,50,50);
connect(ok, SIGNAL(clicked()), SLOT(des()));*/
}
I tried this last piece of code to see if it was possible to destroy and rebuild the object the way I was trying to with a button being clicked. Turns out it is, this time temp = new QPushButton(frame); is working and the button stays there.
EDIT:
thanks for the answer and the comment, but I am sorry because I didnĀ“t realize something before asking the question.
The buttons were being deleted/destroyed, they were just not being "repainted" inside the frame when I write temp = new QPushButton(frame); again, actually they still are not. Help regarding this new problem and again sorry.
Don't manually call destructors, unless you are using memory pools and placement new.
In Qt it is best to use delateLater() in order to avoid errors from unprocessed events. Also, widgets are by default created hidden, so you need to show() the widget.
So your code should be:
{//slot des()
if (temp) temp->deleteLater();
temp = new QPushButton(frame);
temp->show();
}
you can use delete to destroy objects. destroy method can only be called by the object itself. and qwidgets can be automatically recycled by the application. use pointer to point to the new memory space.
Related
Im a student developer using Qt to build a GUI to help users plot specific columns of data located in multiple files. The feature I'm setting up allows users to select a file using a button in each row. So the button originally would say browse and then user clicks it to open a dialog to select a file then the button text is replaced with the file name selected. Sorry for the story; my simple attempt to add some clarity.
The problem I'm having is I'm not sure how to set a policy up for the button clicked. I'd imagine that I'd have to extend the functionality of each of the QPushButtons but I don't really know how to do that. So far I am using the following to set the cell widget.
//with row count set dimensions are set becasue column count is static
//begin bulding custom widgets/QTableWidgetItems into cells
for(int x = 0; x < ui->tableWidgetPlotLineList->rowCount(); x++)
{
for(int y = 0; y < ui->tableWidgetPlotLineList->columnCount(); y++)
{
if(y == 1)
{
//install button widget for file selection
QPushButton *fileButton = new QPushButton();
if(setDataStruct.plotLineListData.at(rowCount).lineFileName != "");
{
fileButton->setText(setDataStruct.plotLineListData.at(rowCount).lineFileName);
}
else
{
fileButton->setText("Browse...");
}
ui->tableWidgetPlotLineList->setCellWidget(x, y, fileButton);
}
I was thinking that
connect(ui->tableWidgetPlotLineList->row(x), SIGNAL(fileButton->clicked()), this, SLOT(selectPlotLineFile(x));
might do the trick but I think I'm probably going in the wrong direction here. Honestly I'm not even too sure as to where it would go...
Thanks so much for reading my post. Please let me know if there is anything lacking from this post and I will update it immediately. I'd also like to thank any contributions to this post in advance!
connect(ui->tableWidgetPlotLineList->row(x), SIGNAL(fileButton->clicked()), this, SLOT(selectPlotLineFile(x));
Is not syntactically correct for a signal/slot connection. Something like this would be more appropriate:
connect(fileButton, SIGNAL(clicked()), this, SLOT(selectPlotLineFile(x));
...
If you need access to the specific button that emited the clicked() signal than you could use the sender() function in your slot:
void selectPlotLineFile() {
QPushButton *button = dynamic_cast<QPushButton*>( sender() )
}
Now you may be wondering how you know which row to operate on. There are several different approaches, one of the easier ones being to maintain a QMap<QPushButton*, int> member variable that you can use to lookup which button belongs to which row.
A widget called Tachometer will update accordingly when a signal is sent from its corresponding model, but it will not respond at all when I add the widget to a layout. What might account for this? Without showing the internals of the model or the view (which would be exhaustive), I will attempt to point out where it is not working:
void MainWindow::setupWidgets()
{
QHBoxLayout *horiz1 = new QHBoxLayout();
QHBoxLayout *horiz2 = new QHBoxLayout();
odometer = new Odometer(ui->dashFrame);
fuelGauge = new FuelGauge(ui->dashFrame);
tripometer = new Tripometer(ui->dashFrame);
tachometer = new Tachometer(ui->dashFrame);
temperatureGauge = new TemperatureGauge(ui->dashFrame);
oilPressureGauge = new OilPressureGauge();
QVBoxLayout *vertOPG = new QVBoxLayout();
if ( oilPressureGauge->getTitle() != "" )
{
QLabel *OPGLabel = new QLabel(oilPressureGauge->getTitle());
vertOPG->addWidget(OPGLabel);
}
vertOPG->addWidget(oilPressureGauge);
speedometer = new Speedometer(ui->dashFrame);
horiz1->addWidget(tachometer);
horiz1->addWidget(speedometer);
horiz2->addWidget(fuelGauge);
horiz2->addWidget(temperatureGauge);
horiz2->addLayout(vertOPG);
horiz2->addWidget(tripometer);
horiz2->addWidget(odometer); // will NOT update when added to layout
QVBoxLayout *vert1 = new QVBoxLayout(ui->dashFrame);
vert1->addLayout(horiz1);
vert1->addLayout(horiz2);
this->ui->dashFrame->setLayout(vert1);
}
I am perplexed that the other Widgets will update as expected, but not the object named tachometer. As I said before, if I don't add it to the layout, e.g.
// ...
tachometer = new Tachometer(ui->dashFrame);
// ...
it appears to work just fine. Furthermore, by debugging on the console I see that the RPM value for the tachometer is being sent to the appropriate slot that updates the view for the tachometer (I just noticed the tachometer finally responded to the update, but it isn't updating after every timeout as it should). It seems like some latency issues are clearly involved here.
If anyone might have an idea as to why this might be, I would greatly appreciate some clarification.
Here's some code,
k.Bind<IGame>().To<Game>().Named("A")
.WithConstructorArgument("ColorChoiceCount", 12);
iGame = k.Get<IGame>("A");
((Game)iGame).SelectedColor = new GameColor(System.Drawing.Color.Red);
iGame = k.Get<IGame>("A");
On the first iGame = k.Get<IGame>("A"); I get a new instance of Game.
Next line: I change one of it's properties.
Next line (iGame = k.Get<IGame>("A"); again) I get a new instance again.
What I would like is to be able to retrieve instances I've already used.
But I'm totally new to this kind of tools so I guess I'm missing something.
Thank you if you can help me.
You need to specify the lifetime of your object - by default the container will create a new instance.
The available methods are as follows:
InScope
InTransientScope
InThreadScope
InSingletonScope
InRequestScope
http://blog.bobcravens.com/2010/03/ninject-life-cycle-management-or-scoping/
You probably want a singleton (single instance of the game):
k.Bind<IGame>().To<Game>().InSingletonScope().Named("A")
.WithConstructorArgument("ColorChoiceCount", 12);
I need to play a sound when a button is clicked, I have this:
Phonon::MediaObject *clickObject = new Phonon::MediaObject(this);
clickObject->setCurrentSource(Phonon::MediaSource("Click/sound.wav");
Phonon::AudioOutput *clickOutput = new Phonon::AudioOutput(Phonon::MusicCategory, this);
Phonon::createPath(clickObject, clickOutput);
and
void MainWindow::on_pushButton_clicked()
{
clickObject->play();
}
but no sound is played?
Where am I wrong?
Thanks.
EDIT: It works now, it was the wrong path.
Probably the file path "Click/sound.wav" doesn't point where you think it points.
Try this before calling the setCurrentSource()-function:
bool exists = QFile::exists("Click/sound.wav");
If the Click directory is supposed to be in the same directory as your exe, create the path like this:
QString filePath = QCoreApplication::applicationDirPath() + "/Click/sound.wav";
clickObject->setCurrentSource(Phonon::MediaSource(filePath));
And I would suggest using Qt resource system. Then you would point to the sound file like this:
clickObject->setCurrentSource(Phonon::MediaSource(":/Click/sound.wav"));
You should at least connect the signal stateChanged(Phonon::State, Phonon::State) from your MediaObject object to a custom slot to detect errors: if the state changes to Phonon::ErrorState the reason of the error might be accessible through QMediaObject::errorString().
HI..
i want to add elements dynamically to listview in QT for symbian OS, i have set of delegate methods associated with listview.
if i add elements statically, the control comes to delegate methods, and view is perfect.
but if i add dynamically, control is not at all coming to delegate methods.
i don't no how to do it. ill place here some sample code, that how i am adding elements.
this is how i am setting the view,
MylistView = new QListView();
QDesktopWidget* desktopWidget = QApplication::desktop();
QRect clientRect = desktopWidget->geometry();
MylistView->setMinimumSize(QSize(clientRect.width()-7,clientRect.height()-1));
MylistView->setViewMode(QListView::ListMode);
MylistView->setMovement(QListView::Free);
MylistView->setItemDelegate(new ItemDeligate(MylistView));
MylistView->setSelectionMode(QAbstractItemView::SingleSelection);
bool val =GreenPixmap.load(":/new/prefix1/temp/test.png");
ListModel = new QStandardItemModel();
ListModel->appendColumn(ItemList);
MylistView->setModel(ListModel);
Listlayout.addWidget(MylistView);
Listlayout.addWidget(MylistView);
this->setLayout(&Listlayout);
AddItemMenu = new QAction("Add",this);
menuBar()->addAction(AddItemMenu);
val = connect(AddItemMenu,SIGNAL(triggered()),this,SLOT(addItem()));
This is how i am adding dynamically when the click event occurs, (i.e dynamically adding items)
QStandardItem *Items = new QStandardItem(QIcon(GreenPixmap),"Avatar");
Items->setData("WAKE UP",ItemDeligate::SubTextRole);
ItemList.append(Items);
ListModel->appendColumn(ItemList);
please suggest me, what mistake i am doing in adding elemetns
I just made this quick example in my app, it's working, maybe it will gibe you an hint :
QStandardItem* Items = new QStandardItem("Avatar");
QStandardItemModel* ListModel = new QStandardItemModel();
ListModel->appendRow(Items);
listView->setModel(ListModel);
In summary, you should simply append a row on your model ! It should fix your problem !
If I missed something, let me know !