1

I am trying to build a simple media player in QML . I can't use QFile Dialog as its a single window application running on EGLFS . I managed so far to build a simple file browser for QML and can play a mp3 from a fixed location. But here is where I am stuck:

  1. How do I set the current selected file from the treeview as source for my audio ?

  2. How can I get the Audio play each file with file ending mp3 from the selected folder?

Thanks for your help

.pro file

QT += qml quick multimedia widgets
CONFIG += c++11
SOURCES += main.cpp
RESOURCES += qml.qrc
QML_IMPORT_PATH =
QML_DESIGNER_IMPORT_PATH =
DEFINES += QT_DEPRECATED_WARNING
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target

main.cpp:

#include <QApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
#include <QtQml>
#include <QFileSystemModel>


int main(int argc, char *argv[])
{
QApplication app(argc, argv);
app.setOrganizationName("Power-Tune");
app.setOrganizationDomain("power-tune.org");
app.setApplicationName("PowerTune");

QQmlApplicationEngine engine;
//
QFileSystemModel model;
model.setRootPath("/");
engine.rootContext()->setContextProperty("my_model", &model);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));


return app.exec();

}

my main.qml :

import QtQuick 2.8
import QtQuick.Controls 2.1
import QtQuick.Layouts 1.1 
import QtQuick.Controls 1.4
import QtMultimedia 5.8

ApplicationWindow {
    visible: true
    width: 800
    height: 480
    minimumWidth: 800
    minimumHeight: 480
    title: qsTr("PowerTune ")
    // visibility: "FullScreen"
    color: "black"
    Rectangle {
        width: parent.width
        height: parent.height
        property bool playing: false
        Audio {
            id: playMusic
            //source: currently selected file in TreeView 
        }
        Button {
            id: previous
            text: "previous"
            width: 100
            anchors.right: playpause.left
            //  onClicked: select previous item in current folder
        }
        Button {
            id: playpause
            text: "play/pause" //playing ? "Stop music" : "Start music"
            width: 100
            anchors.right: next.left
            onClicked: {
                if(playing == true) {
                    playMusic.stop()
                    playing = false
                } else {
                    playMusic.play()
                    playing = true
                }
            }
        }
        Button {
            id: next
            text: "next"
            width: 100
            anchors.right: parent.right
        }
        TreeView {
            id:mp3selector
            width: parent.width/2
            height: parent.height
            TableViewColumn {
                title: "Name"
                role: "fileName"
                width: 300
            }
            model: my_model
        }
    }
}
Mohammad Kanan
  • 4,452
  • 10
  • 23
  • 47
Markus
  • 319
  • 5
  • 18
  • Sorry my code has actually a previous and next button. I just pasted the relevant portions of the code as previous and next don’t do anything at the moment. Corrected it just now – Markus Apr 09 '18 at 05:02
  • Hi , sorry i was driving to work . I made the code example now executable as stand alone . I would like to show only the files with extension *.mp3 in the Treeview and then set the source of playmusic to the current selected path with the selected file name – Markus Apr 09 '18 at 06:36
  • yes thats also a good idea. – Markus Apr 09 '18 at 07:12
  • It just needs to be able show folders and drives as i plan to use this on my raspberry pi and the music will 99% of the time be on a external USB stick – Markus Apr 09 '18 at 07:17

1 Answers1

2

Couple of notes:

property bool playing: false

Properties are better to be defined at top of hierarchy so that they accessible in all children, so prefer to put it directly in ApplicationWindow not in Rectangle element.

And, I think TreeView is not a suitable choice (Its a Quick Controls 1.0 element not available in Quick Controls 2.0 , and for mixing check this post);

You can do the model directly from QML, using a ListView with FolderListModel, you only need an additional of decorations for highlighting and selecting of files with mouse .. that's all, TreeView could be replaced with below code, it works and fancy!

...
import QtQuick.Controls 2.2
import Qt.labs.folderlistmodel 2.1
...

    ListView {
        id: list
        width: parent.width/2
        height: parent.height
        model: folderModel
        onCurrentIndexChanged: {
            // This will handle changing playlist with all possible selection methods
            playMusic.source = folderModel.get(currentIndex, "fileURL")
        }
        FolderListModel {
            id: folderModel
            folder: "file:///MP3/"
            showDirs: false
            nameFilters: ["*.mp3"]
        }
        delegate: Component {
            Item {
                width: parent.width
                height: 40
                Column {
                    Text { text: fileName }
                }
                MouseArea {
                    anchors.fill: parent
                    onClicked: {
                        list.currentIndex = index
                    }
                }
            }
        }
        highlight: Rectangle {
            color: 'grey'
        }
        focus: true
    }

For your buttons onClicked just handle currentIndex of the ListView , for example in the next button add:

onClicked: list.currentIndex += 1

you also need to add some code to avoid getting index out of range or -1 ...etc.

Mohammad Kanan
  • 4,452
  • 10
  • 23
  • 47