~dpm/ubuntu-filemanager-app/run-ap-from-out-of-source-build

« back to all changes in this revision

Viewing changes to FolderListPage.qml

  • Committer: Michael Spencer
  • Date: 2014-02-19 00:00:15 UTC
  • mto: This revision was merged to the branch mainline in revision 132.
  • Revision ID: sonrisesoftware@gmail.com-20140219000015-3ogzcc7roicfqbyi
Refactored files into sub-directories

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*
2
 
 * Copyright (C) 2013 Canonical Ltd
3
 
 *
4
 
 * This program is free software: you can redistribute it and/or modify
5
 
 * it under the terms of the GNU General Public License version 3 as
6
 
 * published by the Free Software Foundation.
7
 
 *
8
 
 * This program is distributed in the hope that it will be useful,
9
 
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10
 
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
 
 * GNU General Public License for more details.
12
 
 *
13
 
 * You should have received a copy of the GNU General Public License
14
 
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
15
 
 *
16
 
 * Authored by: Arto Jalkanen <ajalkane@gmail.com>
17
 
 */
18
 
import QtQuick 2.0
19
 
import Ubuntu.Components 0.1
20
 
import Ubuntu.Components.Popups 0.1
21
 
import Ubuntu.Components.ListItems 0.1
22
 
import org.nemomobile.folderlistmodel 1.0
23
 
 
24
 
Page {
25
 
    id: folderListPage
26
 
 
27
 
    title: folderName(folder)
28
 
 
29
 
    property variant fileView: folderListPage
30
 
 
31
 
    property bool showHiddenFiles: false
32
 
 
33
 
    property bool showingListView: folderListView.visible
34
 
 
35
 
    onShowHiddenFilesChanged: {
36
 
        pageModel.showHiddenFiles = folderListPage.showHiddenFiles
37
 
    }
38
 
 
39
 
    property string sortingMethod: "Name"
40
 
 
41
 
    onSortingMethodChanged: {
42
 
        console.log("Sorting by: " + sortingMethod)
43
 
        if (sortingMethod === "Name") {
44
 
            pageModel.sortBy = FolderListModel.SortByName
45
 
        } else if (sortingMethod === "Date") {
46
 
            pageModel.sortBy = FolderListModel.SortByDate
47
 
        } else {
48
 
            // Something fatal happened!
49
 
            console.log("ERROR: Invalid sort type:", sortingMethod)
50
 
        }
51
 
    }
52
 
 
53
 
    property bool sortAccending: true
54
 
 
55
 
    onSortAccendingChanged: {
56
 
        console.log("Sorting accending: " + sortAccending)
57
 
 
58
 
        if (sortAccending) {
59
 
            pageModel.sortOrder = FolderListModel.SortAscending
60
 
        } else {
61
 
            pageModel.sortOrder = FolderListModel.SortDescending
62
 
        }
63
 
    }
64
 
 
65
 
    // This stores the location using ~ to represent home
66
 
    property string folder
67
 
    property string homeFolder: "~"
68
 
 
69
 
    // This replaces ~ with the actual home folder, since the
70
 
    // plugin doesn't recognize the ~
71
 
    property string path: folder.replace("~", pageModel.homePath())
72
 
 
73
 
    function goHome() {
74
 
        goTo(folderListPage.homeFolder)
75
 
    }
76
 
 
77
 
    function goTo(location) {
78
 
        // Since the FolderListModel returns paths using the actual
79
 
        // home folder, this replaces with ~ before actually going
80
 
        // to the specified folder
81
 
        while (location !== '/' && location.substring(location.lastIndexOf('/')+1) === "") {
82
 
            location = location.substring(0, location.length - 1)
83
 
        }
84
 
 
85
 
        folderListPage.folder = location.replace(pageModel.homePath(), "~")
86
 
        refresh()
87
 
    }
88
 
 
89
 
    function refresh() {
90
 
        pageModel.refresh()
91
 
    }
92
 
 
93
 
    function pathAccessedDate() {
94
 
        console.log("calling method pageModel.curPathAccessedDate()")
95
 
        return pageModel.curPathAccessedDate()
96
 
    }
97
 
 
98
 
    function pathModifiedDate() {
99
 
        console.log("calling method pageModel.curPathModifiedDate()")
100
 
        return pageModel.curPathModifiedDate()
101
 
    }
102
 
 
103
 
    function pathIsWritable() {
104
 
        console.log("calling method pageModel.curPathIsWritable()")
105
 
        return pageModel.curPathIsWritable()
106
 
    }
107
 
 
108
 
    // FIXME: hard coded path for icon, assumes Ubuntu desktop icon available.
109
 
    // Nemo mobile has icon provider. Have to figure out what's the proper way
110
 
    // to get "system wide" icons in Ubuntu Touch, or if we have to use
111
 
    // icons packaged into the application. Both folder and individual
112
 
    // files will need an icon.
113
 
    // TODO: Remove isDir parameter and use new model functions
114
 
    function fileIcon(file, isDir) {
115
 
        file = file.replace(pageModel.homePath(), "~")
116
 
        var iconPath = isDir ? "/usr/share/icons/Humanity/places/48/folder.svg"
117
 
                             : "/usr/share/icons/Humanity/mimes/48/empty.svg"
118
 
 
119
 
        if (file === "~") {
120
 
            iconPath = "icons/folder-home.svg"
121
 
        } else if (file === i18n.tr("~/Desktop")) {
122
 
            iconPath = "/usr/share/icons/Humanity/places/48/user-desktop.svg"
123
 
        } else if (file === i18n.tr("~/Documents")) {
124
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-documents.svg"
125
 
        } else if (file === i18n.tr("~/Downloads")) {
126
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-downloads.svg"
127
 
        } else if (file === i18n.tr("~/Music")) {
128
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-music.svg"
129
 
        } else if (file === i18n.tr("~/Pictures")) {
130
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-pictures.svg"
131
 
        } else if (file === i18n.tr("~/Public")) {
132
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-publicshare.svg"
133
 
        } else if (file === i18n.tr("~/Programs")) {
134
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-system.svg"
135
 
        } else if (file === i18n.tr("~/Templates")) {
136
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-templates.svg"
137
 
        } else if (file === i18n.tr("~/Videos")) {
138
 
            iconPath = "/usr/share/icons/Humanity/places/48/folder-videos.svg"
139
 
        } else if (file === "/") {
140
 
            iconPath = "/usr/share/icons/Humanity/devices/48/drive-harddisk.svg"
141
 
        }
142
 
 
143
 
        return Qt.resolvedUrl(iconPath)
144
 
    }
145
 
 
146
 
    function folderName(folder) {
147
 
        folder = folder.replace(pageModel.homePath(), "~")
148
 
 
149
 
        if (folder === folderListPage.homeFolder) {
150
 
            return i18n.tr("Home")
151
 
        } else if (folder === "/") {
152
 
            return i18n.tr("File System")
153
 
        } else {
154
 
            return folder.substr(folder.lastIndexOf('/') + 1)
155
 
        }
156
 
    }
157
 
 
158
 
    function pathName(folder) {
159
 
        if (folder === "/") {
160
 
            return "/"
161
 
        } else {
162
 
            return folder.substr(folder.lastIndexOf('/') + 1)
163
 
        }
164
 
    }
165
 
 
166
 
    function pathExists(path) {
167
 
        path = path.replace("~", pageModel.homePath())
168
 
 
169
 
        if (path === '/')
170
 
            return true
171
 
 
172
 
        if(path.charAt(0) === '/') {
173
 
            console.log("Directory: " + path.substring(0, path.lastIndexOf('/')+1))
174
 
            repeaterModel.path = path.substring(0, path.lastIndexOf('/')+1)
175
 
            console.log("Sub dir: " + path.substring(path.lastIndexOf('/')+1))
176
 
            if (path.substring(path.lastIndexOf('/')+1) !== "" && !repeaterModel.cdIntoPath(path.substring(path.lastIndexOf('/')+1))) {
177
 
                return false
178
 
            } else {
179
 
                return true
180
 
            }
181
 
        } else {
182
 
            return false
183
 
        }
184
 
    }
185
 
 
186
 
    property bool loading: pageModel.awaitingResults
187
 
 
188
 
    FolderListModel {
189
 
        id: pageModel
190
 
 
191
 
        path: folderListPage.path
192
 
 
193
 
        enableExternalFSWatcher: true
194
 
 
195
 
        // Properties to emulate a model entry for use by FileDetailsPopover
196
 
        property bool isDir: true
197
 
        property string fileName: pathName(pageModel.path)
198
 
        property string fileSize: (folderListView.count === 1
199
 
                                   ? i18n.tr("1 file")
200
 
                                   : i18n.tr("%1 files").arg(folderListView.count))       
201
 
        property bool isReadable: true
202
 
        property bool isExecutable: true
203
 
    }
204
 
 
205
 
    FolderListModel {
206
 
        id: repeaterModel
207
 
        path: folderListPage.folder
208
 
 
209
 
        onPathChanged: {
210
 
            console.log("Path: " + repeaterModel.path)
211
 
        }
212
 
    }
213
 
 
214
 
    Component {
215
 
        id: tabsPopover
216
 
        ActionSelectionPopover {
217
 
            objectName: "tabsPopover"
218
 
 
219
 
            property var tab
220
 
 
221
 
            grabDismissAreaEvents: true
222
 
 
223
 
            actions: ActionList {
224
 
                Action {
225
 
                    text: i18n.tr("Open in a new tab")
226
 
                    onTriggered: {
227
 
                        openTab(folderListPage.folder)
228
 
                    }
229
 
                }
230
 
 
231
 
                // The current tab can be closed as long as there is at least one tab remaining
232
 
                Action {
233
 
                    text: i18n.tr("Close this tab")
234
 
                    onTriggered: {
235
 
                        closeTab(tab.index)
236
 
                    }
237
 
                    enabled: tabs.count > 1
238
 
                }
239
 
            }
240
 
        }
241
 
    }
242
 
 
243
 
    Component {
244
 
        id: folderActionsPopoverComponent
245
 
        ActionSelectionPopover {
246
 
            id: folderActionsPopover
247
 
            objectName: "folderActionsPopover"
248
 
 
249
 
            grabDismissAreaEvents: true
250
 
 
251
 
            actions: ActionList {
252
 
                Action {
253
 
                    text: i18n.tr("Create New Folder")
254
 
                    onTriggered: {
255
 
                        print(text)
256
 
 
257
 
                        PopupUtils.open(createFolderDialog, folderListPage)
258
 
                    }
259
 
                }
260
 
 
261
 
                // TODO: Disabled until backend supports creating files
262
 
    //            Action {
263
 
    //                text: i18n.tr("Create New File")
264
 
    //                onTriggered: {
265
 
    //                    print(text)
266
 
 
267
 
    //                    PopupUtils.open(createFileDialog, root)
268
 
    //                }
269
 
    //            }
270
 
 
271
 
                Action {
272
 
                    text: pageModel.clipboardUrlsCounter === 0
273
 
                          ? i18n.tr("Paste")
274
 
                          : pageModel.clipboardUrlsCounter === 1
275
 
                            ? i18n.tr("Paste %1 File").arg(pageModel.clipboardUrlsCounter)
276
 
                            : i18n.tr("Paste %1 Files").arg(pageModel.clipboardUrlsCounter)
277
 
                    onTriggered: {
278
 
                        console.log("Pasting to current folder items of count " + pageModel.clipboardUrlsCounter)
279
 
                        fileOperationDialog.startOperation(i18n.tr("Paste files"))
280
 
                        pageModel.paste()
281
 
                    }
282
 
 
283
 
                    // FIXME: This property is depreciated and doesn't seem to work!
284
 
                    //visible: pageModel.clipboardUrlsCounter > 0
285
 
 
286
 
                    enabled: pageModel.clipboardUrlsCounter > 0
287
 
                }
288
 
 
289
 
                // TODO: Disabled until support for opening apps is added
290
 
                Action {
291
 
                    text: i18n.tr("Open in Terminal")
292
 
                    onTriggered: {
293
 
                        print(text)
294
 
 
295
 
                        // Is this the way it will work??
296
 
                        Qt.openUrlExternally("app://terminal")
297
 
                    }
298
 
 
299
 
                    enabled: showAdvancedFeatures && false
300
 
                }
301
 
 
302
 
                Action {
303
 
                    text: i18n.tr("Properties")
304
 
                    onTriggered: {
305
 
                        print(text)
306
 
                        PopupUtils.open(Qt.resolvedUrl("FileDetailsPopover.qml"),
307
 
                                        folderListPage,
308
 
                                            { "model": pageModel
309
 
                                            }
310
 
                                        )
311
 
                    }
312
 
                }
313
 
            }
314
 
        }
315
 
    }
316
 
 
317
 
    Component {
318
 
        id: createFolderDialog
319
 
        ConfirmDialogWithInput {
320
 
            title: i18n.tr("Create folder")
321
 
            text: i18n.tr("Enter name for new folder")
322
 
 
323
 
            onAccepted: {
324
 
                console.log("Create folder accepted", inputText)
325
 
                if (inputText !== '') {
326
 
                    pageModel.mkdir(inputText)
327
 
                } else {
328
 
                    console.log("Empty directory name, ignored")
329
 
                }
330
 
            }
331
 
        }
332
 
    }
333
 
 
334
 
    Component {
335
 
        id: createFileDialog
336
 
        ConfirmDialogWithInput {
337
 
            title: i18n.tr("Create file")
338
 
            text: i18n.tr("Enter name for new file")
339
 
 
340
 
            onAccepted: {
341
 
                console.log("Create file accepted", inputText)
342
 
                if (inputText !== '') {
343
 
                    //FIXME: Actually create a new file!
344
 
                } else {
345
 
                    console.log("Empty file name, ignored")
346
 
                }
347
 
            }
348
 
        }
349
 
    }
350
 
 
351
 
    function openFile(filePath) {
352
 
        if (!pageModel.openPath(filePath)) {
353
 
            error(i18n.tr("File operation error"), i18n.tr("Unable to open '%11").arg(filePath))
354
 
        }
355
 
    }
356
 
 
357
 
    tools: ToolbarItems {
358
 
        id: toolbar
359
 
        locked: showToolbar
360
 
        opened: showToolbar
361
 
 
362
 
        onLockedChanged: opened = locked
363
 
 
364
 
        back: ToolbarButton {
365
 
            objectName: "up"
366
 
            text: "Up"
367
 
            iconSource: getIcon("keyboard-caps")
368
 
            enabled: folder != "/"
369
 
            onTriggered: {
370
 
                goTo(pageModel.parentPath)
371
 
            }
372
 
        }
373
 
 
374
 
        Item {
375
 
            id: pathItem
376
 
            width: folderListPage.width - units.gu(37)
377
 
            height: units.gu(5)
378
 
            anchors.verticalCenter: parent.verticalCenter
379
 
            PathBar {
380
 
                height: units.gu(5)
381
 
                width: Math.min(pathItem.width, implicitWidth)
382
 
                visible: sidebar.expanded
383
 
            }
384
 
        }
385
 
 
386
 
        Item {
387
 
            width: units.gu(1)
388
 
            height: parent.height
389
 
        }
390
 
 
391
 
        ToolbarButton {
392
 
            id: actionsButton
393
 
            objectName: "actions"
394
 
            text: i18n.tr("Actions")
395
 
            iconSource: getIcon("navigation-menu")
396
 
 
397
 
            onTriggered: {
398
 
                print(text)
399
 
                PopupUtils.open(folderActionsPopoverComponent, actionsButton)
400
 
            }
401
 
        }
402
 
 
403
 
        ToolbarButton {
404
 
            text: i18n.tr("View")
405
 
            iconSource: getIcon("properties")
406
 
            id: optionsButton
407
 
 
408
 
            onTriggered: {
409
 
                print(text)
410
 
 
411
 
                PopupUtils.open(Qt.resolvedUrl("ViewPopover.qml"), optionsButton)
412
 
            }
413
 
        }
414
 
 
415
 
        ToolbarButton {
416
 
            id: placesButton
417
 
            visible: !sidebar.expanded
418
 
            objectName: "places"
419
 
            text: i18n.tr("Places")
420
 
            iconSource: getIcon("location")
421
 
            onTriggered: {
422
 
                print(text)
423
 
 
424
 
                PopupUtils.open(Qt.resolvedUrl("PlacesPopover.qml"), placesButton)
425
 
            }
426
 
        }
427
 
 
428
 
        ToolbarButton {
429
 
            id: tabsButton
430
 
            objectName: "tabs"
431
 
            text: i18n.tr("Tabs")
432
 
            iconSource: getIcon("browser-tabs")
433
 
 
434
 
            onTriggered: {
435
 
                print(text)
436
 
 
437
 
                PopupUtils.open(tabsPopover, tabsButton, {
438
 
                                    tab: folderListPage.parent
439
 
                                })
440
 
            }
441
 
        }
442
 
 
443
 
        ToolbarButton {
444
 
            id: settingsButton
445
 
            visible: sidebar.expanded
446
 
            objectName: "settings"
447
 
            action: settingsAction
448
 
        }
449
 
    }
450
 
 
451
 
    flickable: !sidebar.expanded ? folderListView.visible ? folderListView : folderIconView.flickable : null
452
 
 
453
 
    onFlickableChanged: {
454
 
        if (flickable === null) {
455
 
            folderListView.topMargin = 0
456
 
            folderIconView.flickable.topMargin = 0
457
 
        } else {
458
 
            folderListView.topMargin = units.gu(9.5)
459
 
            folderIconView.flickable.topMargin = units.gu(9.5)
460
 
        }
461
 
    }
462
 
 
463
 
    PlacesSidebar {
464
 
        id: sidebar
465
 
        objectName: "placesSidebar"
466
 
 
467
 
//        anchors {
468
 
//            top: parent.top
469
 
//            bottom: parent.bottom
470
 
//            bottomMargin: units.gu(-2)
471
 
//        }
472
 
 
473
 
        expanded: showSidebar
474
 
    }
475
 
 
476
 
    FolderIconView {
477
 
        id: folderIconView
478
 
 
479
 
        clip: true
480
 
 
481
 
        folderListModel: pageModel
482
 
        anchors {
483
 
            top: parent.top
484
 
            bottom: parent.bottom
485
 
            left: sidebar.right
486
 
            right: parent.right
487
 
        }
488
 
        smallMode: !sidebar.expanded
489
 
        visible: viewMethod === i18n.tr("Icons")
490
 
    }
491
 
 
492
 
    FolderListView {
493
 
        id: folderListView
494
 
 
495
 
        clip: true
496
 
 
497
 
        folderListModel: pageModel
498
 
        anchors {
499
 
            top: parent.top
500
 
            bottom: parent.bottom
501
 
            left: sidebar.right
502
 
            right: parent.right
503
 
        }
504
 
        smallMode: !sidebar.expanded
505
 
        visible: viewMethod === i18n.tr("List")
506
 
    }
507
 
 
508
 
    Item {
509
 
        id: contents
510
 
 
511
 
        anchors {
512
 
            top: parent.top
513
 
            bottom: parent.bottom
514
 
            left: sidebar.right
515
 
            right: parent.right
516
 
        }
517
 
 
518
 
 
519
 
        Label {
520
 
            text: i18n.tr("No files")
521
 
            fontSize: "large"
522
 
            opacity: 0.5
523
 
            anchors.centerIn: parent
524
 
            visible: folderListView.count == 0 && !pageModel.awaitingResults
525
 
        }
526
 
 
527
 
        ActivityIndicator {
528
 
            running: pageModel.awaitingResults
529
 
            width: units.gu(8)
530
 
            height: units.gu(8)
531
 
            anchors.centerIn: parent
532
 
        }
533
 
    }
534
 
 
535
 
    Component {
536
 
        id: confirmSingleDeleteDialog
537
 
        ConfirmDialog {
538
 
            property string filePath
539
 
            property string fileName
540
 
            title: i18n.tr("Delete")
541
 
            text: i18n.tr("Are you sure you want to permanently delete '%1'?").arg(fileName)
542
 
 
543
 
            onAccepted: {
544
 
                console.log("Delete accepted for filePath, fileName", filePath, fileName)
545
 
 
546
 
                fileOperationDialog.startOperation("Deleting files")
547
 
                console.log("Doing delete")
548
 
                pageModel.rm(filePath)
549
 
            }
550
 
        }
551
 
    }
552
 
 
553
 
    Component {
554
 
        id: confirmRenameDialog
555
 
        ConfirmDialogWithInput {
556
 
            // IMPROVE: this does not seem good: the backend excepts row and new name.
557
 
            // But what if new files are added/deleted in the background while user is
558
 
            // entering the new name? The indices change and wrong file is renamed.
559
 
            // Perhaps the backend should take as parameters the "old name" and "new name"?
560
 
            // This is not currently a problem since the backend does not poll changes in
561
 
            // the filesystem, but may be a problem in the future.
562
 
            property int modelRow
563
 
 
564
 
            title: i18n.tr("Rename")
565
 
            text: i18n.tr("Enter a new name")
566
 
 
567
 
            onAccepted: {
568
 
                console.log("Rename accepted", inputText)
569
 
                if (inputText !== '') {
570
 
                    console.log("Rename commensed, modelRow/inputText", modelRow, inputText)
571
 
                    if (pageModel.rename(modelRow, inputText) === false) {
572
 
                        PopupUtils.open(Qt.resolvedUrl("NotifyDialog.qml"), delegate,
573
 
                                        {
574
 
                                            title: i18n.tr("Could not rename"),
575
 
                                            text: i18n.tr("Insufficient permissions or name already exists?")
576
 
                                         })
577
 
 
578
 
                    }
579
 
                } else {
580
 
                    console.log("Empty new name given, ignored")
581
 
                }
582
 
            }
583
 
        }
584
 
    }
585
 
 
586
 
    Component {
587
 
        id: actionSelectionPopoverComponent
588
 
 
589
 
        ActionSelectionPopover {
590
 
            id: actionSelectionPopover
591
 
            objectName: "fileActionsPopover"
592
 
 
593
 
            grabDismissAreaEvents: true
594
 
 
595
 
            property var model
596
 
            actions: ActionList {
597
 
                Action {
598
 
                    text: i18n.tr("Cut")
599
 
                    // TODO: temporary
600
 
                    iconSource: "/usr/share/icons/Humanity/actions/48/edit-cut.svg"
601
 
                    onTriggered: {
602
 
                        console.log("Cut on row called for", actionSelectionPopover.model.fileName, actionSelectionPopover.model.index)
603
 
                        pageModel.cutIndex(actionSelectionPopover.model.index)
604
 
                        console.log("CliboardUrlsCounter after copy", pageModel.clipboardUrlsCounter)
605
 
                    }
606
 
                }
607
 
 
608
 
                Action {
609
 
                    text: i18n.tr("Copy")
610
 
                    // TODO: temporary.
611
 
                    iconSource: "/usr/share/icons/Humanity/actions/48/edit-copy.svg"
612
 
 
613
 
                    onTriggered: {
614
 
                        console.log("Copy on row called for", actionSelectionPopover.model.fileName, actionSelectionPopover.model.index)
615
 
                        pageModel.copyIndex(actionSelectionPopover.model.index)
616
 
                        console.log("CliboardUrlsCounter after copy", pageModel.clipboardUrlsCounter)
617
 
                    }
618
 
                }
619
 
 
620
 
                Action {
621
 
                    text: i18n.tr("Delete")
622
 
                    // TODO: temporary
623
 
                    iconSource: "/usr/share/icons/Humanity/actions/48/edit-delete.svg"
624
 
                    onTriggered: {
625
 
                        print(text)
626
 
                        PopupUtils.open(confirmSingleDeleteDialog, actionSelectionPopover.caller,
627
 
                                        { "filePath" : actionSelectionPopover.model.filePath,
628
 
                                          "fileName" : actionSelectionPopover.model.fileName }
629
 
                                        )
630
 
                    }
631
 
                }
632
 
 
633
 
                Action {
634
 
                    text: i18n.tr("Rename")
635
 
                    // TODO: temporary
636
 
                    iconSource: "/usr/share/icons/Humanity/actions/48/rotate.svg"
637
 
                    onTriggered: {
638
 
                        print(text)
639
 
                        PopupUtils.open(confirmRenameDialog, actionSelectionPopover.caller,
640
 
                                        { "modelRow"  : actionSelectionPopover.model.index,
641
 
                                          "inputText" : actionSelectionPopover.model.fileName
642
 
                                        })
643
 
                    }
644
 
                }
645
 
 
646
 
                Action {
647
 
                    text: i18n.tr("Properties")
648
 
                    onTriggered: {
649
 
                        print(text)
650
 
                        PopupUtils.open(Qt.resolvedUrl("FileDetailsPopover.qml"),
651
 
                                        actionSelectionPopover.caller,
652
 
                                            { "model": actionSelectionPopover.model
653
 
                                            }
654
 
                                        )
655
 
                    }
656
 
                }
657
 
            }
658
 
        }
659
 
    }
660
 
 
661
 
    // Errors from model
662
 
    Connections {
663
 
        target: pageModel
664
 
        onError: {
665
 
            console.log("FolderListModel Error Title/Description", errorTitle, errorMessage)
666
 
            error(i18n.tr("File operation error"), errorTitle + ": " + errorMessage)
667
 
        }
668
 
    }
669
 
 
670
 
    FileOperationProgressDialog {
671
 
        id: fileOperationDialog
672
 
 
673
 
        page: folderListPage
674
 
        model: pageModel
675
 
    }
676
 
 
677
 
    function itemClicked(model) {
678
 
        if (model.isDir) {
679
 
            if (model.isReadable && model.isExecutable) {
680
 
                console.log("Changing to dir", model.filePath)
681
 
                goTo(model.filePath)
682
 
            } else {
683
 
                PopupUtils.open(Qt.resolvedUrl("NotifyDialog.qml"), delegate,
684
 
                                {
685
 
                                    title: i18n.tr("Folder not accessible"),
686
 
                                    text: i18n.tr("Can not access ") + model.fileName
687
 
 
688
 
                                 })
689
 
            }
690
 
        } else {
691
 
            console.log("Non dir clicked")
692
 
            openFile(model.fileName)
693
 
//            PopupUtils.open(Qt.resolvedUrl("FileActionDialog.qml"), root,
694
 
//                            {
695
 
//                                fileName: model.fileName,
696
 
//                                filePath: model.filePath,
697
 
//                                folderListModel: root.folderListModel
698
 
//                            })
699
 
        }
700
 
    }
701
 
 
702
 
    function itemLongPress(delegate, model) {
703
 
        console.log("FolderListDelegate onPressAndHold")
704
 
        PopupUtils.open(actionSelectionPopoverComponent, delegate,
705
 
                        {
706
 
                            model: model
707
 
                        })
708
 
    }
709
 
 
710
 
    function keyPressed(key, modifiers) {
711
 
        if (key === Qt.Key_L && modifiers & Qt.ControlModifier) {
712
 
            PopupUtils.open(Qt.resolvedUrl("GoToDialog.qml"), goToButton)
713
 
            return true;
714
 
        }
715
 
 
716
 
        return false;
717
 
    }
718
 
 
719
 
    Component.onCompleted: forceActiveFocus()
720
 
}