I used to add a feature in my app based on treewidget.
When right click on an item, I can create a folder on the FS over USB is used.
That mainly say that when selecting an item on the TreeWidget, I get its name and check if it's a folder, if yes, I create a child and add a new folder and file the name.
The make the folder creation done on the FS, I'm using this :
void TreeView::onAddFolderAction() {
char *parent_folder_name;
QList<QTreeWidgetItem *> item;
bool isFolder;
item = this->selectedItems();
if (item.empty())
parent_folder_name = NULL;
else {
QString str = item[0]->text(0);
QByteArray latin_str = str.toLatin1();
parent_folder_name = latin_str.data();
}
setParentFolder(parent_folder_name);
if(!item.empty())
isFolder = m_device.isParentFolder(parent_folder_name);
if(isFolder == false)
return;
QTreeWidgetItem* child = new QTreeWidgetItem();
child->setText(0, "New Folder");
child->setText(1, "--");
child->setText(2, "--");
child->setFlags(child->flags() | Qt::ItemIsEditable);
if(!item.empty()) {
item[0]->addChild(child);
item[0]->setExpanded(true);
}
else
addTopLevelItem(child);
this->editItem(child);
this->setCurrentItem(child);
connect(this, SIGNAL(itemChanged(QTreeWidgetItem*, int)), this, SLOT(onTreeItemChanged()));
}
this code is connected to a CONNECT when left click action and add folder is selected.
I have done this to avoid the use of a dialog box when renaming. what I'm doing in add an item named New Folder, make it editable and allow the user to change it. when user press enter, the itemChanged signal is triggered and I start onTreeItemChanged.
QList<QTreeWidgetItem *> items;
bool isFolderCreated;
items = this->selectedItems();
QString str = items[0]->text(0);
QByteArray latin_str = str.toLatin1();
char *newFolder = latin_str.data();
char *parent = getParentFolder();
isFolderCreated = m_device.CreateFolder(newFolder, parent);
My issue is that parent do not contain the rigth name.
I'm backuping it in the onAddFolderAction using
setParentFolder(parent_folder_name);
and get it back using
getParentFolder();
Both are declared as below
void TreeView::setParentFolder(char *name) {
this->ParentFolder = name;
}
char *TreeView::getParentFolder() {
return this->ParentFolder;
}
when using the getParent, the value return is not correct. but it seems that what the value is corrupted earlier.
in the on AddFolderACtion(), I had:
else {
QString str = item[0]->text(0);
QByteArray latin_str = str.toLatin1();
parent_folder_name = latin_str.data();
}
setParentFolder(parent_folder_name);
parent_folder_name contain "BLABLA" but when moving step-by-step on setParentFolder, the parent_folder_name change to "XFZV" strange caracters.
Any idea why ?
In the code
else {
QString str = item[0]->text(0);
QByteArray latin_str = str.toLatin1();
parent_folder_name = latin_str.data();
}
setParentFolder(parent_folder_name);
the variable latin_str
is local inside the else
block, and will go out of scope and get destructed once the else
block end. This leaves you with a stray pointer, pointing to now destructed and unallocated memory, leading to undefined behavior when you dereference it.
My recommendation is to use QString
as much as possible, and only convert to pointer when actually needed (even if you need to do it multiple times). Either that, or change the rest of the code to accept QString
(which would be a better solution IMO).