I’m posting my partial solution here, just so any n00b people can also take a look at it. I’m still implementing the rest of the stuff I want to add. Like Loading, Deleting, Insert-new-directory, Move (copy and Paste) and so on…
Header:
[code]
class FileTreeComponentEx : public FileTreeComponent
{
public:
FileTreeComponentEx (DirectoryContentsList& listToShow);
const File getSelectedFile (const int index) const throw();
};[/code]
Cpp
[code]#define MessageBox(dd,ds) AlertWindow::showMessageBox(AlertWindow::WarningIcon, dd,ds)
//-----------------------------------------------------------------------------------------------------------
class FileListTreeItemEx : public TreeViewItem,
public TimeSliceClient,
public AsyncUpdater,
public ChangeListener
{
public:
//-----------------------------------------------------------------------------------------------------------
FileListTreeItemEx (FileTreeComponentEx& owner_,
DirectoryContentsList* const parentContentsList_,
const int indexInContentsList_,
const File& file_,
TimeSliceThread& thread_) throw()
: file (file_),
owner (owner_),
parentContentsList (parentContentsList_),
indexInContentsList (indexInContentsList_),
subContentsList (0),
canDeleteSubContentsList (false),
thread (thread_),
icon (0)
{
DirectoryContentsList::FileInfo fileInfo;
if (parentContentsList_ != 0
&& parentContentsList_->getFileInfo (indexInContentsList_, fileInfo))
{
fileSize = File::descriptionOfSizeInBytes (fileInfo.fileSize);
modTime = fileInfo.modificationTime.formatted (T("%d %b '%y %H:%M"));
isDirectory = fileInfo.isDirectory;
}
else
{
isDirectory = true;
}
}
//-----------------------------------------------------------------------------------------------------------
~FileListTreeItemEx() throw()
{
thread.removeTimeSliceClient (this);
clearSubItems();
ImageCache::release (icon);
if (canDeleteSubContentsList)
delete subContentsList;
}
bool mightContainSubItems() { return isDirectory; }
const String getUniqueName() const { return file.getFullPathName(); }
int getItemHeight() const { return 22; }
const String getDragSourceDescription() { return owner.getDragAndDropDescription(); }
//-----------------------------------------------------------------------------------------------------------
void itemOpennessChanged (bool isNowOpen)
{
if (isNowOpen)
{
clearSubItems();
isDirectory = file.isDirectory();
if (isDirectory)
{
if (subContentsList == 0)
{
jassert (parentContentsList != 0);
DirectoryContentsList* const l = new DirectoryContentsList (parentContentsList->getFilter(), thread);
l->setDirectory (file, true, true);
setSubContentsList (l);
canDeleteSubContentsList = true;
}
changeListenerCallback (0);
}
}
}
//-----------------------------------------------------------------------------------------------------------
void setSubContentsList (DirectoryContentsList* newList) throw()
{
jassert (subContentsList == 0);
subContentsList = newList;
newList->addChangeListener (this);
}
//-----------------------------------------------------------------------------------------------------------
void changeListenerCallback (void*)
{
clearSubItems();
if (isOpen() && subContentsList != 0)
{
for (int i = 0; i < subContentsList->getNumFiles(); ++i)
{
FileListTreeItemEx* const item
= new FileListTreeItemEx (owner, subContentsList, i, subContentsList->getFile(i), thread);
addSubItem (item);
}
}
}
//-----------------------------------------------------------------------------------------------------------
void paintItem (Graphics& g, int width, int height)
{
if (file != File::nonexistent && ! isDirectory)
{
updateIcon (true);
if (icon == 0)
thread.addTimeSliceClient (this);
}
owner.getLookAndFeel()
.drawFileBrowserRow (g, width, height,
file.getFileName(),
icon,
fileSize, modTime,
isDirectory, isSelected(),
indexInContentsList);
}
//-----------------------------------------------------------------------------------------------------------
void itemClicked (const MouseEvent& e)
{
owner.sendMouseClickMessage (file, e);
if (e.mods.isPopupMenu())
{
MessageBox(owner.getSelectedFile(0).getFullPathName(),"!");
}
}
//-----------------------------------------------------------------------------------------------------------
void itemDoubleClicked (const MouseEvent& e)
{
TreeViewItem::itemDoubleClicked (e);
owner.sendDoubleClickMessage (file);
if (!owner.getSelectedFile(0).isDirectory()) MessageBox(owner.getSelectedFile(0).getFullPathName(),"!");
}
//-----------------------------------------------------------------------------------------------------------
void itemSelectionChanged (bool)
{
owner.sendSelectionChangeMessage();
}
//-----------------------------------------------------------------------------------------------------------
bool useTimeSlice()
{
updateIcon (false);
thread.removeTimeSliceClient (this);
return false;
}
//-----------------------------------------------------------------------------------------------------------
void handleAsyncUpdate()
{
owner.repaint();
}
const File file;
juce_UseDebuggingNewOperator
private:
FileTreeComponentEx& owner;
DirectoryContentsList* parentContentsList;
int indexInContentsList;
DirectoryContentsList* subContentsList;
bool isDirectory, canDeleteSubContentsList;
TimeSliceThread& thread;
Image* icon;
String fileSize;
String modTime;
void updateIcon (const bool onlyUpdateIfCached) throw() { }
};
//-----------------------------------------------------------------------------------------------------------
FileTreeComponentEx::FileTreeComponentEx (DirectoryContentsList& listToShow)
: FileTreeComponent (listToShow)
{
FileListTreeItemEx* const root
= new FileListTreeItemEx (*this, 0, 0, listToShow.getDirectory(),
listToShow.getTimeSliceThread());
root->setSubContentsList (&listToShow);
setRootItemVisible (false);
setRootItem (root);
}
//-----------------------------------------------------------------------------------------------------------
/FileTreeComponentEx::~FileTreeComponentEx()
{
TreeViewItem const root = getRootItem();
setRootItem (0);
delete root;
}
//-----------------------------------------------------------------------------------------------------------
const File FileTreeComponentEx::getSelectedFile() const
{
return getSelectedFile (0);
}*/
//-----------------------------------------------------------------------------------------------------------
const File FileTreeComponentEx::getSelectedFile (const int index) const throw()
{
const FileListTreeItemEx* const item = dynamic_cast <const FileListTreeItemEx*> (getSelectedItem (index));
if (item != 0)
return item->file;
return File::nonexistent;
}
//-----------------------------------------------------------------------------------------------------------
/*void FileTreeComponentEx::scrollToTop()
{
getViewport()->getVerticalScrollBar()->setCurrentRangeStart (0);
}
//-----------------------------------------------------------------------------------------------------------
void FileTreeComponentEx::setDragAndDropDescription (const String& description) throw()
{
dragAndDropDescription = description;
}*/[/code]
I’m not using the whole code yet. And I couldn’t really override some of the stuff as the FileListTreeItem class is NOT in the Juce .h files. At least I couldn’t find it… still, since I will do a lot of changes, I don’t mind copying the whole code.
Wk