Merge lp:~jonas-drange/ubuntu-settings-components/filepicker into lp:ubuntu-settings-components
- filepicker
- Merge into trunk
Proposed by
Jonas G. Drange
on 2016-07-15
| Status: | Approved |
|---|---|
| Approved by: | Ken VanDine on 2017-01-31 |
| Approved revision: | 167 |
| Proposed branch: | lp:~jonas-drange/ubuntu-settings-components/filepicker |
| Merge into: | lp:ubuntu-settings-components |
| Diff against target: |
1665 lines (+1174/-226) 27 files modified
debian/changelog (+6/-0) debian/control (+1/-0) examples/FilePickerComponent.qml (+91/-0) plugins/Ubuntu/Settings/Components/CMakeLists.txt (+7/-0) plugins/Ubuntu/Settings/Components/FilePicker.qml (+197/-0) plugins/Ubuntu/Settings/Components/FilePickerProperties.qml (+22/-0) plugins/Ubuntu/Settings/Components/filepickerhelper.cpp (+59/-0) plugins/Ubuntu/Settings/Components/filepickerhelper.h (+36/-0) plugins/Ubuntu/Settings/Components/plugin.cpp (+7/-0) plugins/Ubuntu/Settings/Components/qmldir (+3/-0) plugins/Ubuntu/Settings/Vpn/DialogFile.qml (+0/-176) plugins/Ubuntu/Settings/Vpn/DialogFileProperties.qml (+0/-22) plugins/Ubuntu/Settings/Vpn/FileSelector.qml (+7/-1) plugins/Ubuntu/Settings/Vpn/VpnEditor.qml (+0/-7) plugins/Ubuntu/Settings/Vpn/qmldir (+0/-4) po/ubuntu-settings-components.pot (+28/-16) tests/qmltests/CMakeLists.txt (+1/-0) tests/qmltests/Components/tst_FilePicker.qml (+215/-0) tests/qmltests/mocks/CMakeLists.txt (+1/-0) tests/qmltests/mocks/Qt/CMakeLists.txt (+1/-0) tests/qmltests/mocks/Qt/labs/CMakeLists.txt (+1/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/CMakeLists.txt (+20/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.cpp (+241/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.h (+171/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.cpp (+26/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.h (+31/-0) tests/qmltests/mocks/Qt/labs/folderlistmodel/qmldir (+2/-0) |
| To merge this branch: | bzr merge lp:~jonas-drange/ubuntu-settings-components/filepicker |
| Related bugs: |
| Reviewer | Review Type | Date Requested | Status |
|---|---|---|---|
| Ken VanDine | 2016-07-15 | Approve on 2017-01-31 | |
| Lukáš Tinkl (community) | Needs Information on 2016-07-18 | ||
| PS Jenkins bot | continuous-integration | Pending | |
|
Review via email:
|
|||
Commit Message
create file picker component for export
Description of the Change
To post a comment you must log in.
| Jonas G. Drange (jonas-drange) wrote : | # |
It's scheduled to land after silo 2078.
On 27 October 2016 at 18:16, Marco Trevisan (Treviño) <mail@3v1n0.net>
wrote:
> Is this something we still want to land?
> --
> https:/
> components/
> You are the owner of lp:~jonas-drange/ubuntu-settings-components/
> filepicker.
>
lp:~jonas-drange/ubuntu-settings-components/filepicker
updated
on 2017-01-25
- 166. By Jonas G. Drange on 2017-01-24
-
bumps filepicker change
- 167. By Jonas G. Drange on 2017-01-25
-
syncs with trunk
| Ken VanDine (ken-vandine) wrote : | # |
I'll reviewed the commits since my last approval, looks fine.
review:
Approve
Unmerged revisions
- 167. By Jonas G. Drange on 2017-01-25
-
syncs with trunk
- 166. By Jonas G. Drange on 2017-01-24
-
bumps filepicker change
- 165. By Jonas G. Drange on 2017-01-24
-
sync with trunk
- 164. By Jonas G. Drange on 2016-10-19
-
bump version
- 163. By Jonas G. Drange on 2016-10-19
-
drop bump
- 162. By Jonas G. Drange on 2016-10-19
-
merge trunk
- 161. By Jonas G. Drange on 2016-07-18
-
update pot
- 160. By Jonas G. Drange on 2016-07-18
-
address comments, use glib to format size
- 159. By Jonas G. Drange on 2016-07-18
-
update pot
- 158. By Jonas G. Drange on 2016-07-15
-
make file name elide in the middle
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
| 1 | === modified file 'debian/changelog' |
| 2 | --- debian/changelog 2017-01-18 15:20:00 +0000 |
| 3 | +++ debian/changelog 2017-01-25 13:04:17 +0000 |
| 4 | @@ -1,3 +1,9 @@ |
| 5 | +ubuntu-settings-components (0.13+17.04.20170104-0ubuntu2) UNRELEASED; urgency=medium |
| 6 | + |
| 7 | + * create file picker component for export |
| 8 | + |
| 9 | + -- Jonas G. Drange <jonas.drange@canonical.com> Tue, 24 Jan 2017 15:01:25 +0100 |
| 10 | + |
| 11 | ubuntu-settings-components (0.12+17.04.20170118-0ubuntu1) zesty; urgency=medium |
| 12 | |
| 13 | [ Pete Woods ] |
| 14 | |
| 15 | === modified file 'debian/control' |
| 16 | --- debian/control 2016-12-07 17:02:20 +0000 |
| 17 | +++ debian/control 2017-01-25 13:04:17 +0000 |
| 18 | @@ -5,6 +5,7 @@ |
| 19 | Build-Depends: cmake, |
| 20 | cmake-extras (>= 0.10), |
| 21 | debhelper (>= 9), |
| 22 | + libglib2.0-dev (>= 2.37.92), |
| 23 | pkg-config, |
| 24 | python3:any, |
| 25 | qml-module-qt-labs-folderlistmodel, |
| 26 | |
| 27 | === added file 'examples/FilePickerComponent.qml' |
| 28 | --- examples/FilePickerComponent.qml 1970-01-01 00:00:00 +0000 |
| 29 | +++ examples/FilePickerComponent.qml 2017-01-25 13:04:17 +0000 |
| 30 | @@ -0,0 +1,91 @@ |
| 31 | +/* |
| 32 | + * Copyright 2016 Canonical Ltd. |
| 33 | + * |
| 34 | + * This program is free software; you can redistribute it and/or modify |
| 35 | + * it under the terms of the GNU Lesser General Public License as published by |
| 36 | + * the Free Software Foundation; version 3. |
| 37 | + * |
| 38 | + * This program is distributed in the hope that it will be useful, |
| 39 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 40 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 41 | + * GNU Lesser General Public License for more details. |
| 42 | + * |
| 43 | + * You should have received a copy of the GNU Lesser General Public License |
| 44 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 45 | + * |
| 46 | + * Authored by Jonas G. Drange <jonas.drange@canonical.com> |
| 47 | + */ |
| 48 | + |
| 49 | +import QtQuick 2.4 |
| 50 | +import Ubuntu.Components 1.3 |
| 51 | +import Ubuntu.Settings.Components 0.1 |
| 52 | +import Ubuntu.Components.Popups 1.3 |
| 53 | + |
| 54 | +MainView { |
| 55 | + id: mainView |
| 56 | + // Note! applicationName needs to match the .desktop filename |
| 57 | + applicationName: "SettingsComponents" |
| 58 | + |
| 59 | + width: units.gu(42) |
| 60 | + height: units.gu(75) |
| 61 | + |
| 62 | + property var _diag |
| 63 | + property alias _accepted: acceptedLabel.acceptedPath |
| 64 | + |
| 65 | + Component { |
| 66 | + id: fp |
| 67 | + FilePicker { |
| 68 | + onReject: { |
| 69 | + if (_diag) { |
| 70 | + PopupUtils.close(_diag) |
| 71 | + } |
| 72 | + _accepted = "" |
| 73 | + } |
| 74 | + onAccept: { |
| 75 | + _accepted = path |
| 76 | + if (_diag) { |
| 77 | + PopupUtils.close(_diag) |
| 78 | + } |
| 79 | + } |
| 80 | + } |
| 81 | + } |
| 82 | + |
| 83 | + Page { |
| 84 | + header: PageHeader { |
| 85 | + id: pageHeader |
| 86 | + title: "FilePicker" |
| 87 | + } |
| 88 | + |
| 89 | + Column { |
| 90 | + spacing: units.gu(2) |
| 91 | + anchors { |
| 92 | + top: pageHeader.bottom |
| 93 | + left: parent.left |
| 94 | + right: parent.right |
| 95 | + bottom: parent.bottom |
| 96 | + margins: units.gu(2) |
| 97 | + } |
| 98 | + |
| 99 | + Button { |
| 100 | + anchors { left: parent.left; right: parent.right } |
| 101 | + text: i18n.tr("Select dark theme") |
| 102 | + onClicked: theme.name = "Ubuntu.Components.Themes.SuruDark" |
| 103 | + } |
| 104 | + |
| 105 | + Button { |
| 106 | + anchors { left: parent.left; right: parent.right } |
| 107 | + text: i18n.tr("Open file picker") |
| 108 | + onClicked: _diag = PopupUtils.open(fp) |
| 109 | + } |
| 110 | + |
| 111 | + Label { |
| 112 | + id: acceptedLabel |
| 113 | + property string acceptedPath |
| 114 | + visible: acceptedPath |
| 115 | + anchors { left: parent.left; right: parent.right } |
| 116 | + text: i18n.tr("Accepted path: %1").arg(acceptedPath) |
| 117 | + elide: Text.ElideMiddle |
| 118 | + } |
| 119 | + } |
| 120 | + } |
| 121 | +} |
| 122 | |
| 123 | === modified file 'plugins/Ubuntu/Settings/Components/CMakeLists.txt' |
| 124 | --- plugins/Ubuntu/Settings/Components/CMakeLists.txt 2016-01-29 00:44:43 +0000 |
| 125 | +++ plugins/Ubuntu/Settings/Components/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 126 | @@ -1,9 +1,15 @@ |
| 127 | project(UbuntuSettingsComponentsQml) |
| 128 | |
| 129 | +pkg_search_module(GLIB REQUIRED glib-2.0) |
| 130 | +include_directories( |
| 131 | + ${GLIB_INCLUDE_DIRS} |
| 132 | +) |
| 133 | + |
| 134 | add_definitions(-DUBUNTUSETTINGSCOMPONENTS_LIBRARY) |
| 135 | |
| 136 | add_library(UbuntuSettingsComponentsQml MODULE |
| 137 | plugin.cpp |
| 138 | + filepickerhelper.cpp |
| 139 | serverpropertysynchroniser.cpp |
| 140 | ) |
| 141 | |
| 142 | @@ -11,6 +17,7 @@ |
| 143 | Qt5::Core |
| 144 | Qt5::Qml |
| 145 | Qt5::Quick |
| 146 | + ${GLIB_LDFLAGS} |
| 147 | ) |
| 148 | |
| 149 | add_usc_plugin(Ubuntu.Settings.Components 0.1 Ubuntu/Settings/Components TARGETS UbuntuSettingsComponentsQml) |
| 150 | |
| 151 | === added file 'plugins/Ubuntu/Settings/Components/FilePicker.qml' |
| 152 | --- plugins/Ubuntu/Settings/Components/FilePicker.qml 1970-01-01 00:00:00 +0000 |
| 153 | +++ plugins/Ubuntu/Settings/Components/FilePicker.qml 2017-01-25 13:04:17 +0000 |
| 154 | @@ -0,0 +1,197 @@ |
| 155 | +/* |
| 156 | + * Copyright (C) 2016 Canonical Ltd. |
| 157 | + * |
| 158 | + * This program is free software: you can redistribute it and/or modify it |
| 159 | + * under the terms of the GNU Lesser General Public License version 3, |
| 160 | + * as published by the Free Software Foundation. |
| 161 | + * |
| 162 | + * This program is distributed in the hope that it will be useful, |
| 163 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 164 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 165 | + * GNU Lesser General Public License for more details. |
| 166 | + * |
| 167 | + * You should have received a copy of the GNU Lesser General Public License |
| 168 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 169 | + */ |
| 170 | + |
| 171 | +import Qt.labs.folderlistmodel 2.1 |
| 172 | +import QtQuick 2.4 |
| 173 | +import QtQuick.Layouts 1.1 |
| 174 | +import Ubuntu.Components 1.3 |
| 175 | +import Ubuntu.Components.ListItems 1.3 as ListItems |
| 176 | +import Ubuntu.Components.Popups 1.3 |
| 177 | +import Ubuntu.Settings.Components 0.1 |
| 178 | + |
| 179 | +Dialog { |
| 180 | + id: root |
| 181 | + objectName: "filePicker" |
| 182 | + |
| 183 | + property string currentFilePath: "" |
| 184 | + |
| 185 | + signal accept(string path) |
| 186 | + signal reject() |
| 187 | + |
| 188 | + function hideFunc() { |
| 189 | + FilePickerProperties.lastFolder = fsModel.folder |
| 190 | + currentFilePath = "" |
| 191 | + } |
| 192 | + |
| 193 | + function rejectFunc() { |
| 194 | + hideFunc() |
| 195 | + root.reject() |
| 196 | + } |
| 197 | + |
| 198 | + function acceptFunc() { |
| 199 | + var path = currentFilePath |
| 200 | + hideFunc() |
| 201 | + root.accept(path) |
| 202 | + } |
| 203 | + |
| 204 | + property var fsModel: FolderListModel { |
| 205 | + showDirs: true |
| 206 | + showFiles: true |
| 207 | + showHidden: true |
| 208 | + showDirsFirst: true |
| 209 | + showDotAndDotDot: false |
| 210 | + showOnlyReadable: false |
| 211 | + sortField: FolderListModel.Name |
| 212 | + |
| 213 | + folder: (FilePickerProperties.lastFolder === "") ? |
| 214 | + FilePickerHelper.homeDirUrl() : |
| 215 | + FilePickerProperties.lastFolder |
| 216 | + } |
| 217 | + |
| 218 | + ColumnLayout { |
| 219 | + spacing: units.gu(1) |
| 220 | + anchors { |
| 221 | + left: parent.left |
| 222 | + right: parent.right |
| 223 | + } |
| 224 | + height: root.height - units.gu(10) |
| 225 | + |
| 226 | + RowLayout { |
| 227 | + anchors { left: parent.left; right: parent.right } |
| 228 | + spacing: units.gu(1) |
| 229 | + |
| 230 | + Icon { |
| 231 | + objectName: "filePickerBackButton" |
| 232 | + name: "back" |
| 233 | + Layout.alignment: Qt.AlignVCenter |
| 234 | + width: units.gu(2.5) |
| 235 | + height: width |
| 236 | + |
| 237 | + enabled: (FilePickerHelper.pathFromUrl(fsModel.folder) |
| 238 | + !== FilePickerHelper.rootPath()) |
| 239 | + opacity: enabled ? 1 : 0.5 |
| 240 | + |
| 241 | + MouseArea { |
| 242 | + anchors { |
| 243 | + fill: parent |
| 244 | + margins: -units.gu(2) |
| 245 | + } |
| 246 | + onClicked: { |
| 247 | + if (parent.enabled) { |
| 248 | + fsModel.folder = fsModel.parentFolder |
| 249 | + } |
| 250 | + } |
| 251 | + } |
| 252 | + } |
| 253 | + |
| 254 | + Label { |
| 255 | + objectName: "filePickerBreadcrumb" |
| 256 | + Layout.alignment: Qt.AlignVCenter |
| 257 | + text: { |
| 258 | + var prettyTree = [ |
| 259 | + i18n.dtr("ubuntu-settings-components", "Device") |
| 260 | + ]; |
| 261 | + var paths = FilePickerHelper.pathsFromUrl(fsModel.folder); |
| 262 | + for (var i = 0; i < paths.length; i++) { |
| 263 | + prettyTree.push(paths[i]); |
| 264 | + } |
| 265 | + return i18n.dtr("ubuntu-settings-components", |
| 266 | + "%1 (%2 file)", |
| 267 | + "%1 (%2 files)", |
| 268 | + fsModel.count |
| 269 | + ).arg(prettyTree.join("/")) |
| 270 | + .arg(fsModel.count) |
| 271 | + } |
| 272 | + Layout.fillWidth: true |
| 273 | + elide: Text.ElideMiddle |
| 274 | + } |
| 275 | + } |
| 276 | + |
| 277 | + Rectangle { |
| 278 | + Layout.fillWidth: true |
| 279 | + Layout.fillHeight: true |
| 280 | + color: theme.palette.normal.background |
| 281 | + |
| 282 | + border { |
| 283 | + width: 1 |
| 284 | + color: theme.palette.normal.overlaySecondaryText |
| 285 | + } |
| 286 | + |
| 287 | + ListView { |
| 288 | + id: list |
| 289 | + objectName: "filePickerList" |
| 290 | + anchors.fill: parent |
| 291 | + clip: true |
| 292 | + model: fsModel |
| 293 | + |
| 294 | + delegate: ListItem { |
| 295 | + objectName: "filePickerFileItem_" + index |
| 296 | + height: fileLayout.height + divider.height |
| 297 | + color: (filePath === currentFilePath) ? highlightColor : "transparent" |
| 298 | + |
| 299 | + onClicked: { |
| 300 | + if (fileIsDir) { |
| 301 | + fsModel.folder = fileURL |
| 302 | + } else { |
| 303 | + currentFilePath = filePath |
| 304 | + } |
| 305 | + } |
| 306 | + |
| 307 | + ListItemLayout { |
| 308 | + id: fileLayout |
| 309 | + |
| 310 | + title.text: fileName |
| 311 | + title.elide: Text.ElideMiddle |
| 312 | + title.wrapMode: Text.NoWrap |
| 313 | + subtitle.text: fileIsDir ? |
| 314 | + "" : FilePickerHelper.formatSize(fileSize) |
| 315 | + |
| 316 | + Icon { |
| 317 | + name: fileIsDir ? "folder" : "empty" |
| 318 | + SlotsLayout.position: SlotsLayout.Leading; |
| 319 | + width: units.gu(4) |
| 320 | + } |
| 321 | + } |
| 322 | + } |
| 323 | + } |
| 324 | + |
| 325 | + Scrollbar { |
| 326 | + flickableItem: list |
| 327 | + align: Qt.AlignTrailing |
| 328 | + } |
| 329 | + } |
| 330 | + |
| 331 | + RowLayout { |
| 332 | + spacing: units.gu(1) |
| 333 | + |
| 334 | + Button { |
| 335 | + objectName: "filePickerCancel" |
| 336 | + Layout.fillWidth: true |
| 337 | + text: i18n.dtr("ubuntu-settings-components", "Cancel") |
| 338 | + onClicked: rejectFunc() |
| 339 | + } |
| 340 | + |
| 341 | + Button { |
| 342 | + objectName: "filePickerAccept" |
| 343 | + Layout.fillWidth: true |
| 344 | + enabled: currentFilePath !== "" |
| 345 | + text: i18n.dtr("ubuntu-settings-components", "Accept") |
| 346 | + onClicked: acceptFunc() |
| 347 | + color: theme.palette.normal.positive |
| 348 | + } |
| 349 | + } |
| 350 | + } |
| 351 | +} |
| 352 | |
| 353 | === added file 'plugins/Ubuntu/Settings/Components/FilePickerProperties.qml' |
| 354 | --- plugins/Ubuntu/Settings/Components/FilePickerProperties.qml 1970-01-01 00:00:00 +0000 |
| 355 | +++ plugins/Ubuntu/Settings/Components/FilePickerProperties.qml 2017-01-25 13:04:17 +0000 |
| 356 | @@ -0,0 +1,22 @@ |
| 357 | +/* |
| 358 | + * Copyright (C) 2016 Canonical Ltd. |
| 359 | + * |
| 360 | + * This program is free software: you can redistribute it and/or modify it |
| 361 | + * under the terms of the GNU Lesser General Public License version 3, |
| 362 | + * as published by the Free Software Foundation. |
| 363 | + * |
| 364 | + * This program is distributed in the hope that it will be useful, |
| 365 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 366 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 367 | + * GNU Lesser General Public License for more details. |
| 368 | + * |
| 369 | + * You should have received a copy of the GNU Lesser General Public License |
| 370 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 371 | + */ |
| 372 | + |
| 373 | +pragma Singleton |
| 374 | +import QtQuick 2.4 |
| 375 | + |
| 376 | +QtObject { |
| 377 | + property string lastFolder |
| 378 | +} |
| 379 | |
| 380 | === added file 'plugins/Ubuntu/Settings/Components/filepickerhelper.cpp' |
| 381 | --- plugins/Ubuntu/Settings/Components/filepickerhelper.cpp 1970-01-01 00:00:00 +0000 |
| 382 | +++ plugins/Ubuntu/Settings/Components/filepickerhelper.cpp 2017-01-25 13:04:17 +0000 |
| 383 | @@ -0,0 +1,59 @@ |
| 384 | +/* |
| 385 | + * Copyright (C) 2016 Canonical, Ltd. |
| 386 | + * |
| 387 | + * This program is free software; you can redistribute it and/or modify |
| 388 | + * it under the terms of the GNU Lesser General Public License as published by |
| 389 | + * the Free Software Foundation; version 3. |
| 390 | + * |
| 391 | + * This program is distributed in the hope that it will be useful, |
| 392 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 393 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 394 | + * GNU Lesser General Public License for more details. |
| 395 | + * |
| 396 | + * You should have received a copy of the GNU Lesser General Public License |
| 397 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 398 | + */ |
| 399 | + |
| 400 | +#include "filepickerhelper.h" |
| 401 | + |
| 402 | +#include <glib.h> |
| 403 | + |
| 404 | +#include <QDir> |
| 405 | +#include <QDebug> |
| 406 | + |
| 407 | +FilePickerHelper::FilePickerHelper(QObject* parent) |
| 408 | + : QObject(parent) |
| 409 | +{ |
| 410 | +} |
| 411 | + |
| 412 | +QUrl FilePickerHelper::homeDirUrl() |
| 413 | +{ |
| 414 | + return QUrl::fromLocalFile(QDir::homePath()); |
| 415 | +} |
| 416 | + |
| 417 | +QString FilePickerHelper::pathFromUrl(const QUrl &url) |
| 418 | +{ |
| 419 | + return url.path(); |
| 420 | +} |
| 421 | + |
| 422 | +QString FilePickerHelper::rootPath() |
| 423 | +{ |
| 424 | + return QDir::rootPath(); |
| 425 | +} |
| 426 | + |
| 427 | +QStringList FilePickerHelper::pathsFromUrl(const QUrl &url) |
| 428 | +{ |
| 429 | + QString path = url.path(); |
| 430 | + return path.split(QDir::separator(), QString::SkipEmptyParts); |
| 431 | +} |
| 432 | + |
| 433 | +QString FilePickerHelper::formatSize(const quint64 &size) |
| 434 | +{ |
| 435 | + guint64 g_size = size; |
| 436 | + |
| 437 | + gchar * formatted_size = g_format_size (g_size); |
| 438 | + QString q_formatted_size = QString::fromLocal8Bit(formatted_size); |
| 439 | + g_free (formatted_size); |
| 440 | + |
| 441 | + return q_formatted_size; |
| 442 | +} |
| 443 | |
| 444 | === added file 'plugins/Ubuntu/Settings/Components/filepickerhelper.h' |
| 445 | --- plugins/Ubuntu/Settings/Components/filepickerhelper.h 1970-01-01 00:00:00 +0000 |
| 446 | +++ plugins/Ubuntu/Settings/Components/filepickerhelper.h 2017-01-25 13:04:17 +0000 |
| 447 | @@ -0,0 +1,36 @@ |
| 448 | +/* |
| 449 | + * Copyright (C) 2016 Canonical, Ltd. |
| 450 | + * |
| 451 | + * This program is free software; you can redistribute it and/or modify |
| 452 | + * it under the terms of the GNU Lesser General Public License as published by |
| 453 | + * the Free Software Foundation; version 3. |
| 454 | + * |
| 455 | + * This program is distributed in the hope that it will be useful, |
| 456 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 457 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 458 | + * GNU Lesser General Public License for more details. |
| 459 | + * |
| 460 | + * You should have received a copy of the GNU Lesser General Public License |
| 461 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 462 | + */ |
| 463 | + |
| 464 | +#ifndef FILEPICKERHELPER_H |
| 465 | +#define FILEPICKERHELPER_H |
| 466 | + |
| 467 | +#include <QObject> |
| 468 | +#include <QUrl> |
| 469 | +#include <QStringList> |
| 470 | + |
| 471 | +class FilePickerHelper : public QObject |
| 472 | +{ |
| 473 | + Q_OBJECT |
| 474 | +public: |
| 475 | + FilePickerHelper(QObject* parent = nullptr); |
| 476 | + Q_INVOKABLE static QUrl homeDirUrl(); |
| 477 | + Q_INVOKABLE static QString rootPath(); |
| 478 | + Q_INVOKABLE static QString pathFromUrl(const QUrl &url); |
| 479 | + Q_INVOKABLE static QStringList pathsFromUrl(const QUrl &url); |
| 480 | + Q_INVOKABLE static QString formatSize(const quint64 &size); |
| 481 | +}; |
| 482 | + |
| 483 | +#endif // FILEPICKERHELPER_H |
| 484 | |
| 485 | === modified file 'plugins/Ubuntu/Settings/Components/plugin.cpp' |
| 486 | --- plugins/Ubuntu/Settings/Components/plugin.cpp 2016-10-26 17:09:16 +0000 |
| 487 | +++ plugins/Ubuntu/Settings/Components/plugin.cpp 2017-01-25 13:04:17 +0000 |
| 488 | @@ -17,6 +17,7 @@ |
| 489 | // local |
| 490 | #include "plugin.h" |
| 491 | #include "serverpropertysynchroniser.h" |
| 492 | +#include "filepickerhelper.h" |
| 493 | |
| 494 | // Qt |
| 495 | #include <QtQml/qqml.h> |
| 496 | @@ -33,9 +34,15 @@ |
| 497 | Q_INVOKABLE QString formattedWeekNumber(const QDate &date) const { return QString("%1").arg(date.weekNumber(), 2, 10, QChar('0')); } |
| 498 | }; |
| 499 | |
| 500 | +static QObject* filepickerhelperProvider(QQmlEngine*, QJSEngine*) |
| 501 | +{ |
| 502 | + return new FilePickerHelper; |
| 503 | +} |
| 504 | + |
| 505 | void UbuntuSettingsComponentsPlugin::registerTypes(const char *uri) |
| 506 | { |
| 507 | qmlRegisterType<ServerPropertySynchroniser>(uri, 0, 1, "ServerPropertySynchroniser"); |
| 508 | + qmlRegisterSingletonType<FilePickerHelper>(uri, 0, 1, "FilePickerHelper", filepickerhelperProvider); |
| 509 | qmlRegisterSingletonType<QtDateFunctions>(uri, 0, 1, "QtDateFunctions", |
| 510 | [](QQmlEngine*, QJSEngine*) -> QObject* { return new QtDateFunctions; }); |
| 511 | } |
| 512 | |
| 513 | === modified file 'plugins/Ubuntu/Settings/Components/qmldir' |
| 514 | --- plugins/Ubuntu/Settings/Components/qmldir 2016-09-16 23:17:00 +0000 |
| 515 | +++ plugins/Ubuntu/Settings/Components/qmldir 2017-01-25 13:04:17 +0000 |
| 516 | @@ -4,5 +4,8 @@ |
| 517 | |
| 518 | ActionTextField 0.1 ActionTextField.qml |
| 519 | Calendar 0.1 Calendar.qml |
| 520 | +FilePicker 0.1 FilePicker.qml |
| 521 | MessageHeader 0.1 MessageHeader.qml |
| 522 | UbuntuShapeForItem 0.1 UbuntuShapeForItem.qml |
| 523 | + |
| 524 | +singleton FilePickerProperties 0.1 FilePickerProperties.qml |
| 525 | |
| 526 | === removed file 'plugins/Ubuntu/Settings/Vpn/DialogFile.qml' |
| 527 | --- plugins/Ubuntu/Settings/Vpn/DialogFile.qml 2016-03-14 15:01:48 +0000 |
| 528 | +++ plugins/Ubuntu/Settings/Vpn/DialogFile.qml 1970-01-01 00:00:00 +0000 |
| 529 | @@ -1,176 +0,0 @@ |
| 530 | -/* |
| 531 | - * Copyright (C) 2016 Canonical Ltd. |
| 532 | - * |
| 533 | - * This program is free software: you can redistribute it and/or modify it |
| 534 | - * under the terms of the GNU Lesser General Public License version 3, |
| 535 | - * as published by the Free Software Foundation. |
| 536 | - * |
| 537 | - * This program is distributed in the hope that it will be useful, |
| 538 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 539 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 540 | - * GNU Lesser General Public License for more details. |
| 541 | - * |
| 542 | - * You should have received a copy of the GNU Lesser General Public License |
| 543 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 544 | - */ |
| 545 | - |
| 546 | -import QtQuick 2.4 |
| 547 | -import QtQuick.Layouts 1.1 |
| 548 | -import Ubuntu.Components 1.3 |
| 549 | -import Ubuntu.Components.ListItems 1.3 as ListItems |
| 550 | -import Ubuntu.Components.Popups 1.3 |
| 551 | -import Ubuntu.Settings.Vpn 0.1 |
| 552 | -import Qt.labs.folderlistmodel 2.1 |
| 553 | - |
| 554 | -Dialog { |
| 555 | - objectName: "vpnDialogFile" |
| 556 | - id: dialog |
| 557 | - |
| 558 | - property string currentFilePath: "" |
| 559 | - |
| 560 | - signal accept(string path) |
| 561 | - signal reject |
| 562 | - |
| 563 | - function hideFunc() { |
| 564 | - DialogFileProperties.lastFolder = modelFs.folder |
| 565 | - currentFilePath = "" |
| 566 | - } |
| 567 | - |
| 568 | - function rejectFunc() { |
| 569 | - hideFunc() |
| 570 | - dialog.reject() |
| 571 | - } |
| 572 | - |
| 573 | - function acceptFunc() { |
| 574 | - var path = currentFilePath |
| 575 | - hideFunc() |
| 576 | - dialog.accept(path) |
| 577 | - } |
| 578 | - |
| 579 | - FolderListModel { |
| 580 | - id: modelFs |
| 581 | - showDirs: true |
| 582 | - showFiles: true |
| 583 | - showHidden: true |
| 584 | - showDirsFirst: true |
| 585 | - showDotAndDotDot: false |
| 586 | - showOnlyReadable: false |
| 587 | - sortField: FolderListModel.Name |
| 588 | - |
| 589 | - folder: (DialogFileProperties.lastFolder === "")? "file:///home/" : DialogFileProperties.lastFolder |
| 590 | - } |
| 591 | - |
| 592 | - ColumnLayout { |
| 593 | - height: root.height - units.gu(10) |
| 594 | - spacing: units.gu(1) |
| 595 | - |
| 596 | - Flow { |
| 597 | - spacing: units.gu(1) |
| 598 | - Layout.fillWidth: true |
| 599 | - |
| 600 | - Repeater { |
| 601 | - model: { |
| 602 | - var ret = [] |
| 603 | - var path = "file:///" |
| 604 | - ret.push({ "name" : "/", "url" : path }) |
| 605 | - var tmp = modelFs.folder.toString().replace("file:///", "").split("/") |
| 606 | - for (var idx = 0; idx < tmp.length; idx++) { |
| 607 | - var name = tmp[idx] + "/" |
| 608 | - if (name !== "/") { |
| 609 | - path += name |
| 610 | - ret.push({ "name" : name, "url" : path }) |
| 611 | - } |
| 612 | - } |
| 613 | - return ret |
| 614 | - } |
| 615 | - delegate: Row { |
| 616 | - spacing: units.gu(0.7) |
| 617 | - |
| 618 | - property bool isCurrent : Positioner.isLastItem |
| 619 | - |
| 620 | - Rectangle { |
| 621 | - width: units.gu(0.7) |
| 622 | - height: width |
| 623 | - color: "gray" |
| 624 | - rotation: 45 |
| 625 | - visible: (model.index > 0) |
| 626 | - anchors.verticalCenter: parent.verticalCenter |
| 627 | - } |
| 628 | - Label { |
| 629 | - objectName: "vpnFilePathItem_" + model.modelData["name"] |
| 630 | - text: model.modelData["name"] |
| 631 | - font.weight: (isCurrent ? Font.Bold : Font.Normal) |
| 632 | - font.underline: hoverDetector.containsMouse |
| 633 | - color: "darkblue" |
| 634 | - anchors.verticalCenter: parent.verticalCenter |
| 635 | - |
| 636 | - MouseArea { |
| 637 | - id: hoverDetector |
| 638 | - enabled: !isCurrent |
| 639 | - hoverEnabled: true |
| 640 | - anchors.fill: parent |
| 641 | - onClicked: modelFs.folder = model.modelData["url"] |
| 642 | - } |
| 643 | - } |
| 644 | - } |
| 645 | - } |
| 646 | - } |
| 647 | - |
| 648 | - Rectangle { |
| 649 | - Layout.fillWidth: true |
| 650 | - Layout.fillHeight: true |
| 651 | - |
| 652 | - border { |
| 653 | - width: 1 |
| 654 | - color: "lightgrey" |
| 655 | - } |
| 656 | - |
| 657 | - ListView { |
| 658 | - objectName: "vpnFileList" |
| 659 | - anchors.fill: parent |
| 660 | - anchors.margins: 1 |
| 661 | - clip: true |
| 662 | - model: modelFs |
| 663 | - |
| 664 | - delegate: ListItems.Standard { |
| 665 | - objectName: "vpnFileItem_" + model.fileName |
| 666 | - text: model.fileName |
| 667 | - iconFrame: false |
| 668 | - iconName: model.fileIsDir ? "folder" : "empty" |
| 669 | - |
| 670 | - selected: (model.filePath === currentFilePath) |
| 671 | - |
| 672 | - onClicked: { |
| 673 | - if (model.fileIsDir) { |
| 674 | - modelFs.folder = model.fileURL |
| 675 | - } else { |
| 676 | - currentFilePath = model.filePath |
| 677 | - } |
| 678 | - } |
| 679 | - } |
| 680 | - } |
| 681 | - } |
| 682 | - |
| 683 | - RowLayout { |
| 684 | - spacing: units.gu(1) |
| 685 | - Layout.fillWidth: true |
| 686 | - |
| 687 | - Button { |
| 688 | - objectName: "vpnFileCancel" |
| 689 | - Layout.fillWidth: true |
| 690 | - text: i18n.dtr("ubuntu-settings-components", "Cancel") |
| 691 | - onClicked: rejectFunc() |
| 692 | - color: UbuntuColors.red |
| 693 | - } |
| 694 | - |
| 695 | - Button { |
| 696 | - objectName: "vpnFileAccept" |
| 697 | - Layout.fillWidth: true |
| 698 | - enabled: currentFilePath !== "" |
| 699 | - text: i18n.dtr("ubuntu-settings-components", "Accept") |
| 700 | - onClicked: acceptFunc() |
| 701 | - color: UbuntuColors.green |
| 702 | - } |
| 703 | - } |
| 704 | - } |
| 705 | -} |
| 706 | |
| 707 | === removed file 'plugins/Ubuntu/Settings/Vpn/DialogFileProperties.qml' |
| 708 | --- plugins/Ubuntu/Settings/Vpn/DialogFileProperties.qml 2016-03-07 15:46:28 +0000 |
| 709 | +++ plugins/Ubuntu/Settings/Vpn/DialogFileProperties.qml 1970-01-01 00:00:00 +0000 |
| 710 | @@ -1,22 +0,0 @@ |
| 711 | -/* |
| 712 | - * Copyright (C) 2016 Canonical Ltd. |
| 713 | - * |
| 714 | - * This program is free software: you can redistribute it and/or modify it |
| 715 | - * under the terms of the GNU Lesser General Public License version 3, |
| 716 | - * as published by the Free Software Foundation. |
| 717 | - * |
| 718 | - * This program is distributed in the hope that it will be useful, |
| 719 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 720 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 721 | - * GNU Lesser General Public License for more details. |
| 722 | - * |
| 723 | - * You should have received a copy of the GNU Lesser General Public License |
| 724 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 725 | - */ |
| 726 | - |
| 727 | -pragma Singleton |
| 728 | -import QtQuick 2.4 |
| 729 | - |
| 730 | -QtObject { |
| 731 | - property string lastFolder |
| 732 | -} |
| 733 | |
| 734 | === modified file 'plugins/Ubuntu/Settings/Vpn/FileSelector.qml' |
| 735 | --- plugins/Ubuntu/Settings/Vpn/FileSelector.qml 2016-03-14 15:01:48 +0000 |
| 736 | +++ plugins/Ubuntu/Settings/Vpn/FileSelector.qml 2017-01-25 13:04:17 +0000 |
| 737 | @@ -19,6 +19,7 @@ |
| 738 | import Ubuntu.Components 1.3 |
| 739 | import Ubuntu.Components.Popups 1.3 |
| 740 | import Ubuntu.Components.ListItems 1.3 as ListItems |
| 741 | +import Ubuntu.Settings.Components 0.1 |
| 742 | |
| 743 | ListItems.ItemSelector { |
| 744 | property string path |
| 745 | @@ -47,7 +48,7 @@ |
| 746 | } |
| 747 | |
| 748 | function createDialog() { |
| 749 | - __dialog = PopupUtils.open(fileDialogComponent) |
| 750 | + __dialog = PopupUtils.open(filePickerComponent) |
| 751 | __dialog.accept.connect(pathAccepted) |
| 752 | __dialog.reject.connect(pathRejected) |
| 753 | } |
| 754 | @@ -91,4 +92,9 @@ |
| 755 | path = model[index]; |
| 756 | } |
| 757 | } |
| 758 | + |
| 759 | + Component { |
| 760 | + id: filePickerComponent |
| 761 | + FilePicker {} |
| 762 | + } |
| 763 | } |
| 764 | |
| 765 | === modified file 'plugins/Ubuntu/Settings/Vpn/VpnEditor.qml' |
| 766 | --- plugins/Ubuntu/Settings/Vpn/VpnEditor.qml 2016-12-16 13:32:35 +0000 |
| 767 | +++ plugins/Ubuntu/Settings/Vpn/VpnEditor.qml 2017-01-25 13:04:17 +0000 |
| 768 | @@ -68,13 +68,6 @@ |
| 769 | leadingActionBar.actions: [] |
| 770 | } |
| 771 | |
| 772 | - Component { |
| 773 | - id: fileDialogComponent |
| 774 | - DialogFile { |
| 775 | - id: fileDialog |
| 776 | - } |
| 777 | - } |
| 778 | - |
| 779 | Flickable { |
| 780 | id: scrollWidget |
| 781 | anchors { |
| 782 | |
| 783 | === modified file 'plugins/Ubuntu/Settings/Vpn/qmldir' |
| 784 | --- plugins/Ubuntu/Settings/Vpn/qmldir 2016-02-29 13:52:35 +0000 |
| 785 | +++ plugins/Ubuntu/Settings/Vpn/qmldir 2017-01-25 13:04:17 +0000 |
| 786 | @@ -1,10 +1,6 @@ |
| 787 | module Ubuntu.Settings.Vpn |
| 788 | plugin UbuntuSettingsVpn |
| 789 | |
| 790 | -singleton DialogFileProperties 0.1 DialogFileProperties.qml |
| 791 | - |
| 792 | -internal DialogFile DialogFile.qml |
| 793 | - |
| 794 | VpnList 0.1 VpnList.qml |
| 795 | VpnEditor 0.1 VpnEditor.qml |
| 796 | VpnPreviewDialog 0.1 VpnPreviewDialog.qml |
| 797 | |
| 798 | === modified file 'po/ubuntu-settings-components.pot' |
| 799 | --- po/ubuntu-settings-components.pot 2017-01-18 15:20:00 +0000 |
| 800 | +++ po/ubuntu-settings-components.pot 2017-01-25 13:04:17 +0000 |
| 801 | @@ -8,7 +8,7 @@ |
| 802 | msgstr "" |
| 803 | "Project-Id-Version: ubuntu-settings-components\n" |
| 804 | "Report-Msgid-Bugs-To: \n" |
| 805 | -"POT-Creation-Date: 2017-01-18 15:20+0000\n" |
| 806 | +"POT-Creation-Date: 2017-01-25 14:03+0100\n" |
| 807 | "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" |
| 808 | "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n" |
| 809 | "Language-Team: LANGUAGE <LL@li.org>\n" |
| 810 | @@ -16,12 +16,36 @@ |
| 811 | "MIME-Version: 1.0\n" |
| 812 | "Content-Type: text/plain; charset=UTF-8\n" |
| 813 | "Content-Transfer-Encoding: 8bit\n" |
| 814 | +"Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n" |
| 815 | |
| 816 | #: plugins/Ubuntu/Settings/Components/Calendar.qml:232 |
| 817 | msgctxt "Header text: keep it short and upper case" |
| 818 | msgid "WEEK" |
| 819 | msgstr "" |
| 820 | |
| 821 | +#: plugins/Ubuntu/Settings/Components/FilePicker.qml:105 |
| 822 | +msgid "Device" |
| 823 | +msgstr "" |
| 824 | + |
| 825 | +#: plugins/Ubuntu/Settings/Components/FilePicker.qml:112 |
| 826 | +#, qt-format |
| 827 | +msgid "%1 (%2 file)" |
| 828 | +msgid_plural "%1 (%2 files)" |
| 829 | +msgstr[0] "" |
| 830 | +msgstr[1] "" |
| 831 | + |
| 832 | +#: plugins/Ubuntu/Settings/Components/FilePicker.qml:183 |
| 833 | +#: plugins/Ubuntu/Settings/Fingerprint/Fingerprints.qml:336 |
| 834 | +#: plugins/Ubuntu/Settings/Fingerprint/Setup.qml:355 |
| 835 | +#: plugins/Ubuntu/Settings/Vpn/VpnEditor.qml:129 |
| 836 | +#: plugins/Ubuntu/Settings/Vpn/VpnPreviewDialog.qml:104 |
| 837 | +msgid "Cancel" |
| 838 | +msgstr "" |
| 839 | + |
| 840 | +#: plugins/Ubuntu/Settings/Components/FilePicker.qml:191 |
| 841 | +msgid "Accept" |
| 842 | +msgstr "" |
| 843 | + |
| 844 | #: plugins/Ubuntu/Settings/Fingerprint/Fingerprint.qml:82 |
| 845 | msgid "Fingerprint Name" |
| 846 | msgstr "" |
| 847 | @@ -37,7 +61,7 @@ |
| 848 | #: plugins/Ubuntu/Settings/Fingerprint/Fingerprint.qml:131 |
| 849 | #: plugins/Ubuntu/Settings/Fingerprint/Fingerprints.qml:362 |
| 850 | #: plugins/Ubuntu/Settings/Fingerprint/Setup.qml:138 |
| 851 | -#: plugins/Ubuntu/Settings/Vpn/VpnEditor.qml:149 |
| 852 | +#: plugins/Ubuntu/Settings/Vpn/VpnEditor.qml:142 |
| 853 | msgid "OK" |
| 854 | msgstr "" |
| 855 | |
| 856 | @@ -74,14 +98,6 @@ |
| 857 | msgid "Are you sure you want to forget all stored fingerprints?" |
| 858 | msgstr "" |
| 859 | |
| 860 | -#: plugins/Ubuntu/Settings/Fingerprint/Fingerprints.qml:336 |
| 861 | -#: plugins/Ubuntu/Settings/Fingerprint/Setup.qml:355 |
| 862 | -#: plugins/Ubuntu/Settings/Vpn/DialogFile.qml:161 |
| 863 | -#: plugins/Ubuntu/Settings/Vpn/VpnEditor.qml:136 |
| 864 | -#: plugins/Ubuntu/Settings/Vpn/VpnPreviewDialog.qml:104 |
| 865 | -msgid "Cancel" |
| 866 | -msgstr "" |
| 867 | - |
| 868 | #: plugins/Ubuntu/Settings/Fingerprint/Fingerprints.qml:343 |
| 869 | #: plugins/Ubuntu/Settings/Vpn/VpnPreviewDialog.qml:84 |
| 870 | msgid "Remove" |
| 871 | @@ -148,15 +164,11 @@ |
| 872 | msgid "Send" |
| 873 | msgstr "" |
| 874 | |
| 875 | -#: plugins/Ubuntu/Settings/Vpn/DialogFile.qml:170 |
| 876 | -msgid "Accept" |
| 877 | -msgstr "" |
| 878 | - |
| 879 | -#: plugins/Ubuntu/Settings/Vpn/FileSelector.qml:25 |
| 880 | +#: plugins/Ubuntu/Settings/Vpn/FileSelector.qml:26 |
| 881 | msgid "Choose…" |
| 882 | msgstr "" |
| 883 | |
| 884 | -#: plugins/Ubuntu/Settings/Vpn/FileSelector.qml:34 |
| 885 | +#: plugins/Ubuntu/Settings/Vpn/FileSelector.qml:35 |
| 886 | #: plugins/Ubuntu/Settings/Vpn/Openvpn/Editor.qml:431 |
| 887 | #: plugins/Ubuntu/Settings/Vpn/Openvpn/Editor.qml:513 |
| 888 | msgid "None" |
| 889 | |
| 890 | === modified file 'tests/qmltests/CMakeLists.txt' |
| 891 | --- tests/qmltests/CMakeLists.txt 2016-10-11 13:51:11 +0000 |
| 892 | +++ tests/qmltests/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 893 | @@ -2,6 +2,7 @@ |
| 894 | |
| 895 | add_usc_qmltest(Components ActionTextField) |
| 896 | add_usc_qmltest(Components Calendar) |
| 897 | +add_usc_qmltest(Components FilePicker) |
| 898 | add_usc_qmltest(Components ServerPropertySynchroniser) |
| 899 | |
| 900 | add_usc_qmltest(Menus AccessPointMenu) |
| 901 | |
| 902 | === added file 'tests/qmltests/Components/tst_FilePicker.qml' |
| 903 | --- tests/qmltests/Components/tst_FilePicker.qml 1970-01-01 00:00:00 +0000 |
| 904 | +++ tests/qmltests/Components/tst_FilePicker.qml 2017-01-25 13:04:17 +0000 |
| 905 | @@ -0,0 +1,215 @@ |
| 906 | +/* |
| 907 | + * Copyright 2016 Canonical Ltd. |
| 908 | + * |
| 909 | + * This program is free software; you can redistribute it and/or modify |
| 910 | + * it under the terms of the GNU Lesser General Public License as published by |
| 911 | + * the Free Software Foundation; version 3. |
| 912 | + * |
| 913 | + * This program is distributed in the hope that it will be useful, |
| 914 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 915 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 916 | + * GNU Lesser General Public License for more details. |
| 917 | + * |
| 918 | + * You should have received a copy of the GNU Lesser General Public License |
| 919 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 920 | + * |
| 921 | + * Authored by Jonas G. Drange <jonas.drange@canonical.com> |
| 922 | + */ |
| 923 | + |
| 924 | +import Qt.labs.folderlistmodel 2.1 |
| 925 | +import QtQuick 2.4 |
| 926 | +import QtTest 1.0 |
| 927 | +import Ubuntu.Components 1.3 |
| 928 | +import Ubuntu.Components.Popups 1.3 |
| 929 | +import Ubuntu.Settings.Components 0.1 |
| 930 | +import Ubuntu.Test 0.1 |
| 931 | + |
| 932 | +MainView { |
| 933 | + id: testRoot |
| 934 | + width: units.gu(42) |
| 935 | + height: units.gu(75) |
| 936 | + |
| 937 | + Component { |
| 938 | + id: filePickerComp |
| 939 | + |
| 940 | + FilePicker {} |
| 941 | + } |
| 942 | + |
| 943 | + Component { |
| 944 | + id: fsModelComp |
| 945 | + |
| 946 | + FolderListModel {} |
| 947 | + } |
| 948 | + |
| 949 | + SignalSpy { |
| 950 | + id: spy |
| 951 | + } |
| 952 | + |
| 953 | + UbuntuTestCase { |
| 954 | + name: "FilePicker" |
| 955 | + when: windowShown |
| 956 | + |
| 957 | + property var instance: null |
| 958 | + property var fsModel: null |
| 959 | + |
| 960 | + function init() { |
| 961 | + fsModel = fsModelComp.createObject(testRoot); |
| 962 | + } |
| 963 | + |
| 964 | + function cleanup() { |
| 965 | + PopupUtils.close(instance); |
| 966 | + tryCompareFunction(function () { |
| 967 | + return !!findChild(testRoot, "filePicker"); |
| 968 | + }, false); |
| 969 | + fsModel.destroy(); |
| 970 | + spy.clear(); |
| 971 | + spy.target = null; |
| 972 | + spy.signalName = ""; |
| 973 | + } |
| 974 | + |
| 975 | + function test_breadCrumb_data() { |
| 976 | + return [ |
| 977 | + { |
| 978 | + folder: "file:///home/user/", |
| 979 | + parentFolder: "file:///home", |
| 980 | + count: 0, |
| 981 | + targetText: i18n.dtr("ubuntu-settings-components", "%1 (%2 files)") |
| 982 | + .arg(i18n.tr("Device") + "/home/user") |
| 983 | + .arg(0) |
| 984 | + }, |
| 985 | + { |
| 986 | + folder: "file:///", |
| 987 | + parentFolder: "file:///", |
| 988 | + count: 10, |
| 989 | + targetText: i18n.dtr("ubuntu-settings-components", "%1 (%2 files)") |
| 990 | + .arg(i18n.tr("Device")) |
| 991 | + .arg(10) |
| 992 | + }, |
| 993 | + { |
| 994 | + folder: "file:///bar/baz", |
| 995 | + parentFolder: "file:///bar", |
| 996 | + count: 1, |
| 997 | + targetText: i18n.dtr("ubuntu-settings-components", "%1 (%2 file)") |
| 998 | + .arg(i18n.tr("Device") + "/bar/baz") |
| 999 | + .arg(1) |
| 1000 | + }, |
| 1001 | + ] |
| 1002 | + } |
| 1003 | + |
| 1004 | + function test_breadCrumb(data) { |
| 1005 | + fsModel.folder = data.folder; |
| 1006 | + fsModel.parentFolder = data.parentFolder; |
| 1007 | + fsModel.count = data.count; |
| 1008 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1009 | + waitForRendering(instance); |
| 1010 | + |
| 1011 | + var crumbs = findChild(instance, "filePickerBreadcrumb"); |
| 1012 | + compare(crumbs.text, data.targetText) |
| 1013 | + } |
| 1014 | + |
| 1015 | + function test_backButtonEnabled_data() { |
| 1016 | + return [ |
| 1017 | + { folder: "file:///", parentFolder: "file:///", targetEnabled: false }, |
| 1018 | + { folder: "file:///bar", parentFolder: "file:///", targetEnabled: true }, |
| 1019 | + { folder: "file:///bar/baz", parentFolder: "file:///bar", targetEnabled: true }, |
| 1020 | + ] |
| 1021 | + } |
| 1022 | + |
| 1023 | + function test_backButtonEnabled(data) { |
| 1024 | + fsModel.folder = data.folder; |
| 1025 | + fsModel.parentFolder = data.parentFolder; |
| 1026 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1027 | + waitForRendering(instance); |
| 1028 | + |
| 1029 | + var button = findChild(instance, "filePickerBackButton"); |
| 1030 | + compare(button.enabled, data.targetEnabled); |
| 1031 | + } |
| 1032 | + |
| 1033 | + function test_backButtonAction_data() { |
| 1034 | + return [ |
| 1035 | + { folder: "file:///", parentFolder: "file:///" }, |
| 1036 | + { folder: "file:///bar", parentFolder: "file:///" }, |
| 1037 | + { folder: "file:///bar/baz", parentFolder: "file:///bar" } |
| 1038 | + ] |
| 1039 | + } |
| 1040 | + |
| 1041 | + function test_backButtonAction(data) { |
| 1042 | + fsModel.folder = data.folder; |
| 1043 | + fsModel.parentFolder = data.parentFolder; |
| 1044 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1045 | + waitForRendering(instance); |
| 1046 | + |
| 1047 | + var button = findChild(instance, "filePickerBackButton"); |
| 1048 | + mouseClick(button, button.width / 2, button.height / 2); |
| 1049 | + compare(fsModel.folder, fsModel.parentFolder); |
| 1050 | + } |
| 1051 | + |
| 1052 | + function test_renderFiles_data() { |
| 1053 | + return [ |
| 1054 | + { files: [ ["fileA.txt", "/home/user/fileA.txt", "", 5000, "txt", false, true] ] }, |
| 1055 | + { files: [ |
| 1056 | + ["fileA.txt", "/home/user/fileA.txt", "", 5000, "txt", false, true], |
| 1057 | + ["fileB.txt", "/fileB.txt", "", 5000, "txt", false, true], |
| 1058 | + ["somedir", "/somedir", "somedir", 4001, "", true, false] |
| 1059 | + ]} |
| 1060 | + ] |
| 1061 | + } |
| 1062 | + |
| 1063 | + function test_renderFiles(data) { |
| 1064 | + for (var i = 0; i < data.files.length; i++) { |
| 1065 | + fsModel.mockAddFile.apply(fsModel, data.files[i]); |
| 1066 | + } |
| 1067 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1068 | + waitForRendering(instance); |
| 1069 | + |
| 1070 | + // Make sure each file was rendered. |
| 1071 | + for (var i = 0; i < data.files.length; i++) { |
| 1072 | + verify(findChild(instance, "filePickerFileItem_" + i)); |
| 1073 | + } |
| 1074 | + } |
| 1075 | + |
| 1076 | + function test_accept_data() { |
| 1077 | + var files = [ |
| 1078 | + ["fileA.txt", "file:///home/user/fileA.txt", "", 5000, "txt", false, true], |
| 1079 | + ["fileB.txt", "file:///fileB.txt", "", 5000, "txt", false, true] |
| 1080 | + ] |
| 1081 | + return [ |
| 1082 | + { "files": files, accept: 0, targetAcceptPath: "file:///home/user/fileA.txt" }, |
| 1083 | + { "files": files, accept: 1, targetAcceptPath: "file:///fileB.txt" }, |
| 1084 | + ] |
| 1085 | + } |
| 1086 | + |
| 1087 | + function test_accept(data) { |
| 1088 | + for (var i = 0; i < data.files.length; i++) { |
| 1089 | + fsModel.mockAddFile.apply(fsModel, data.files[i]); |
| 1090 | + } |
| 1091 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1092 | + waitForRendering(instance); |
| 1093 | + |
| 1094 | + var item = findChild(instance, "filePickerFileItem_" + data.accept); |
| 1095 | + mouseClick(item, item.width / 2, item.height / 2); |
| 1096 | + |
| 1097 | + spy.target = instance; |
| 1098 | + spy.signalName = "accept"; |
| 1099 | + |
| 1100 | + var btn = findChild(instance, "filePickerAccept"); |
| 1101 | + mouseClick(btn, btn.width / 2, btn.height / 2); |
| 1102 | + spy.wait(); |
| 1103 | + compare(spy.count, 1); |
| 1104 | + compare(spy.signalArguments[0][0], data.targetAcceptPath); |
| 1105 | + } |
| 1106 | + |
| 1107 | + function test_reject() { |
| 1108 | + instance = PopupUtils.open(filePickerComp, null, { "fsModel": fsModel }); |
| 1109 | + waitForRendering(instance); |
| 1110 | + |
| 1111 | + spy.target = instance; |
| 1112 | + spy.signalName = "reject"; |
| 1113 | + |
| 1114 | + var btn = findChild(instance, "filePickerCancel"); |
| 1115 | + mouseClick(btn, btn.width / 2, btn.height / 2); |
| 1116 | + spy.wait(); |
| 1117 | + compare(spy.count, 1); |
| 1118 | + } |
| 1119 | + } |
| 1120 | +} |
| 1121 | |
| 1122 | === modified file 'tests/qmltests/mocks/CMakeLists.txt' |
| 1123 | --- tests/qmltests/mocks/CMakeLists.txt 2016-12-22 14:35:38 +0000 |
| 1124 | +++ tests/qmltests/mocks/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 1125 | @@ -30,3 +30,4 @@ |
| 1126 | |
| 1127 | add_subdirectory(Biometryd) |
| 1128 | add_subdirectory(GSettings.1.0) |
| 1129 | +add_subdirectory(Qt) |
| 1130 | |
| 1131 | === added directory 'tests/qmltests/mocks/Qt' |
| 1132 | === added file 'tests/qmltests/mocks/Qt/CMakeLists.txt' |
| 1133 | --- tests/qmltests/mocks/Qt/CMakeLists.txt 1970-01-01 00:00:00 +0000 |
| 1134 | +++ tests/qmltests/mocks/Qt/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 1135 | @@ -0,0 +1,1 @@ |
| 1136 | +add_subdirectory(labs) |
| 1137 | |
| 1138 | === added directory 'tests/qmltests/mocks/Qt/labs' |
| 1139 | === added file 'tests/qmltests/mocks/Qt/labs/CMakeLists.txt' |
| 1140 | --- tests/qmltests/mocks/Qt/labs/CMakeLists.txt 1970-01-01 00:00:00 +0000 |
| 1141 | +++ tests/qmltests/mocks/Qt/labs/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 1142 | @@ -0,0 +1,1 @@ |
| 1143 | +add_subdirectory(folderlistmodel) |
| 1144 | |
| 1145 | === added directory 'tests/qmltests/mocks/Qt/labs/folderlistmodel' |
| 1146 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/CMakeLists.txt' |
| 1147 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/CMakeLists.txt 1970-01-01 00:00:00 +0000 |
| 1148 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/CMakeLists.txt 2017-01-25 13:04:17 +0000 |
| 1149 | @@ -0,0 +1,20 @@ |
| 1150 | +include_directories( |
| 1151 | + ${CMAKE_CURRENT_BINARY_DIR} |
| 1152 | + ${Qt5Core_INCLUDE_DIRS} |
| 1153 | + ${Qt5Quick_INCLUDE_DIRS} |
| 1154 | +) |
| 1155 | + |
| 1156 | +set(Qtlabs_folderlistmodel_SRCS |
| 1157 | + MockFolderListModel.cpp |
| 1158 | + plugin.cpp |
| 1159 | +) |
| 1160 | + |
| 1161 | +add_library(QtLabsFolderListModelQml MODULE ${Qtlabs_folderlistmodel_SRCS}) |
| 1162 | +target_link_libraries(QtLabsFolderListModelQml |
| 1163 | + ${Qt5Core_LIBRARIES} |
| 1164 | + ${Qt5Quick_LIBRARIES} |
| 1165 | +) |
| 1166 | + |
| 1167 | +qt5_use_modules(QtLabsFolderListModelQml Qml) |
| 1168 | + |
| 1169 | +add_usc_mock(Qt.labs.folderlistmodel 2.1 Qt.labs.folderlistmodel TARGETS QtLabsFolderListModelQml) |
| 1170 | |
| 1171 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.cpp' |
| 1172 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.cpp 1970-01-01 00:00:00 +0000 |
| 1173 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.cpp 2017-01-25 13:04:17 +0000 |
| 1174 | @@ -0,0 +1,241 @@ |
| 1175 | +/* |
| 1176 | + * Copyright (C) 2016 Canonical, Ltd. |
| 1177 | + * |
| 1178 | + * This program is free software; you can redistribute it and/or modify |
| 1179 | + * it under the terms of the GNU General Public License as published by |
| 1180 | + * the Free Software Foundation; version 3. |
| 1181 | + * |
| 1182 | + * This program is distributed in the hope that it will be useful, |
| 1183 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 1184 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 1185 | + * GNU General Public License for more details. |
| 1186 | + * |
| 1187 | + * You should have received a copy of the GNU General Public License |
| 1188 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 1189 | + */ |
| 1190 | + |
| 1191 | +#include "MockFolderListModel.h" |
| 1192 | + |
| 1193 | +#include <QDateTime> |
| 1194 | + |
| 1195 | +MockFolderListModel::MockFolderListModel(QObject *parent) |
| 1196 | + : QAbstractListModel(parent) |
| 1197 | + , m_files() |
| 1198 | +{ |
| 1199 | +} |
| 1200 | + |
| 1201 | +QUrl MockFolderListModel::folder() const { return m_folder; } |
| 1202 | +bool MockFolderListModel::caseSensitive() const { return m_caseSensitive; } |
| 1203 | +int MockFolderListModel::count() const { return m_count; } |
| 1204 | +QStringList MockFolderListModel::nameFilters() const { return m_nameFilters; } |
| 1205 | +QUrl MockFolderListModel::parentFolder() const { return m_parentFolder; } |
| 1206 | +QUrl MockFolderListModel::rootFolder() const { return m_rootFolder; } |
| 1207 | +bool MockFolderListModel::showDirs() const { return m_showDirs; } |
| 1208 | +bool MockFolderListModel::showDirsFirst() const { return m_showDirsFirst; } |
| 1209 | +bool MockFolderListModel::showDotAndDotDot() const { return m_showDotAndDotDot; } |
| 1210 | +bool MockFolderListModel::showFiles() const { return m_showFiles; } |
| 1211 | +bool MockFolderListModel::showHidden() const { return m_showHidden; } |
| 1212 | +bool MockFolderListModel::showOnlyReadable() const { return m_showOnlyReadable; } |
| 1213 | +MockFolderListModel::Sort MockFolderListModel::sortField() const { return m_sortField; } |
| 1214 | +bool MockFolderListModel::sortReversed() const { return m_sortReversed; } |
| 1215 | + |
| 1216 | +void MockFolderListModel::setCaseSensitive(const bool caseSensitive) |
| 1217 | +{ |
| 1218 | + if (caseSensitive != m_caseSensitive) { |
| 1219 | + m_caseSensitive = caseSensitive; |
| 1220 | + Q_EMIT caseSensitiveChanged(); |
| 1221 | + } |
| 1222 | +} |
| 1223 | + |
| 1224 | +void MockFolderListModel::setCount(const int &count) |
| 1225 | +{ |
| 1226 | + if (count != m_count) { |
| 1227 | + m_count = count; |
| 1228 | + Q_EMIT countChanged(); |
| 1229 | + } |
| 1230 | +} |
| 1231 | + |
| 1232 | +void MockFolderListModel::setFolder(const QUrl &folder) |
| 1233 | +{ |
| 1234 | + if (folder != m_folder) { |
| 1235 | + m_folder = folder; |
| 1236 | + Q_EMIT folderChanged(); |
| 1237 | + } |
| 1238 | +} |
| 1239 | + |
| 1240 | +void MockFolderListModel::setNameFilters(const QStringList &nameFilters) |
| 1241 | +{ |
| 1242 | + if (nameFilters != m_nameFilters) { |
| 1243 | + m_nameFilters = nameFilters; |
| 1244 | + Q_EMIT nameFiltersChanged(); |
| 1245 | + } |
| 1246 | +} |
| 1247 | + |
| 1248 | +void MockFolderListModel::setParentFolder(const QUrl &parentFolder) |
| 1249 | +{ |
| 1250 | + if (parentFolder != m_parentFolder) { |
| 1251 | + m_parentFolder = parentFolder; |
| 1252 | + Q_EMIT parentFolderChanged(); |
| 1253 | + } |
| 1254 | +} |
| 1255 | + |
| 1256 | +void MockFolderListModel::setRootFolder(const QUrl &rootFolder) |
| 1257 | +{ |
| 1258 | + if (rootFolder != m_rootFolder) { |
| 1259 | + m_rootFolder = rootFolder; |
| 1260 | + Q_EMIT rootFolderChanged(); |
| 1261 | + } |
| 1262 | +} |
| 1263 | + |
| 1264 | +void MockFolderListModel::setShowDirs(const bool showDirs) |
| 1265 | +{ |
| 1266 | + if (showDirs != m_showDirs) { |
| 1267 | + m_showDirs = showDirs; |
| 1268 | + Q_EMIT showDirsChanged(); |
| 1269 | + } |
| 1270 | +} |
| 1271 | + |
| 1272 | +void MockFolderListModel::setShowDirsFirst(const bool showDirsFirst) |
| 1273 | +{ |
| 1274 | + if (showDirsFirst != m_showDirsFirst) { |
| 1275 | + m_showDirsFirst = showDirsFirst; |
| 1276 | + Q_EMIT showDirsFirstChanged(); |
| 1277 | + } |
| 1278 | +} |
| 1279 | + |
| 1280 | +void MockFolderListModel::setShowDotAndDotDot(const bool showDotAndDotDot) |
| 1281 | +{ |
| 1282 | + if (showDotAndDotDot != m_showDotAndDotDot) { |
| 1283 | + m_showDotAndDotDot = showDotAndDotDot; |
| 1284 | + Q_EMIT showDotAndDotDotChanged(); |
| 1285 | + } |
| 1286 | +} |
| 1287 | + |
| 1288 | +void MockFolderListModel::setShowFiles(const bool showFiles) |
| 1289 | +{ |
| 1290 | + if (showFiles != m_showFiles) { |
| 1291 | + m_showFiles = showFiles; |
| 1292 | + Q_EMIT showFilesChanged(); |
| 1293 | + } |
| 1294 | +} |
| 1295 | + |
| 1296 | +void MockFolderListModel::setShowHidden(const bool showHidden) |
| 1297 | +{ |
| 1298 | + if (showHidden != m_showHidden) { |
| 1299 | + m_showHidden = showHidden; |
| 1300 | + Q_EMIT showHiddenChanged(); |
| 1301 | + } |
| 1302 | +} |
| 1303 | + |
| 1304 | +void MockFolderListModel::setShowOnlyReadable(const bool showOnlyReadable) |
| 1305 | +{ |
| 1306 | + if (showOnlyReadable != m_showOnlyReadable) { |
| 1307 | + m_showOnlyReadable = showOnlyReadable; |
| 1308 | + Q_EMIT showOnlyReadableChanged(); |
| 1309 | + } |
| 1310 | +} |
| 1311 | + |
| 1312 | +void MockFolderListModel::setSortField(const Sort &sortField) |
| 1313 | +{ |
| 1314 | + if (sortField != m_sortField) { |
| 1315 | + m_sortField = sortField; |
| 1316 | + Q_EMIT sortFieldChanged(); |
| 1317 | + } |
| 1318 | +} |
| 1319 | + |
| 1320 | +void MockFolderListModel::setSortReversed(const bool sortReversed) |
| 1321 | +{ |
| 1322 | + if (sortReversed != m_sortReversed) { |
| 1323 | + m_sortReversed = sortReversed; |
| 1324 | + Q_EMIT sortReversedChanged(); |
| 1325 | + } |
| 1326 | +} |
| 1327 | + |
| 1328 | +QHash<int, QByteArray> MockFolderListModel::roleNames() const |
| 1329 | +{ |
| 1330 | + QHash<int, QByteArray> names; |
| 1331 | + |
| 1332 | + names[Roles::FileNameRole] = "fileName"; |
| 1333 | + names[Roles::FilePathRole] = "filePath"; |
| 1334 | + names[Roles::FileURLRole] = "fileURL"; |
| 1335 | + names[Roles::FileBaseNameRole] = "fileBaseName"; |
| 1336 | + names[Roles::FileSuffixRole] = "fileSuffix"; |
| 1337 | + names[Roles::FileSizeRole] = "fileSize"; |
| 1338 | + names[Roles::FileModifiedRole] = "fileModified"; |
| 1339 | + names[Roles::FileAccessedRole] = "fileAccessed"; |
| 1340 | + names[Roles::FileIsDirRole] = "fileIsDir"; |
| 1341 | + |
| 1342 | + return names; |
| 1343 | +} |
| 1344 | + |
| 1345 | + |
| 1346 | +int MockFolderListModel::rowCount(const QModelIndex&) const |
| 1347 | +{ |
| 1348 | + return m_files.count(); |
| 1349 | +} |
| 1350 | + |
| 1351 | +QVariant MockFolderListModel::data(const QModelIndex &index, int role) const |
| 1352 | +{ |
| 1353 | + QVariant rv; |
| 1354 | + |
| 1355 | + if (index.row() >= m_files.size()) |
| 1356 | + return rv; |
| 1357 | + |
| 1358 | + switch (role) |
| 1359 | + { |
| 1360 | + case Roles::FileNameRole: |
| 1361 | + rv = m_files.at(index.row()).fileName; |
| 1362 | + break; |
| 1363 | + case Roles::FilePathRole: |
| 1364 | + rv = m_files.at(index.row()).filePath; |
| 1365 | + break; |
| 1366 | + case Roles::FileBaseNameRole: |
| 1367 | + rv = m_files.at(index.row()).baseName; |
| 1368 | + break; |
| 1369 | + case Roles::FileSuffixRole: |
| 1370 | + rv = m_files.at(index.row()).suffix; |
| 1371 | + break; |
| 1372 | + case Roles::FileSizeRole: |
| 1373 | + rv = m_files.at(index.row()).size; |
| 1374 | + break; |
| 1375 | + case Roles::FileModifiedRole: |
| 1376 | + rv = QDateTime(); |
| 1377 | + break; |
| 1378 | + case Roles::FileAccessedRole: |
| 1379 | + rv = QDateTime(); |
| 1380 | + break; |
| 1381 | + case Roles::FileIsDirRole: |
| 1382 | + rv = m_files.at(index.row()).isDir; |
| 1383 | + break; |
| 1384 | + case Roles::FileURLRole: |
| 1385 | + rv = QUrl::fromLocalFile(m_files.at(index.row()).filePath); |
| 1386 | + break; |
| 1387 | + default: |
| 1388 | + break; |
| 1389 | + } |
| 1390 | + return rv; |
| 1391 | +} |
| 1392 | + |
| 1393 | +QModelIndex MockFolderListModel::index(int row, int column, const QModelIndex&) const |
| 1394 | +{ |
| 1395 | + return createIndex(row, column); |
| 1396 | +} |
| 1397 | + |
| 1398 | +void MockFolderListModel::mockAddFile(const QString &fileName, |
| 1399 | + const QString &filePath, |
| 1400 | + const QString &baseName, |
| 1401 | + const qint64 &size, |
| 1402 | + const QString &suffix, |
| 1403 | + const bool isDir, |
| 1404 | + const bool isFile) |
| 1405 | +{ |
| 1406 | + MockFile m; |
| 1407 | + m.fileName = fileName; |
| 1408 | + m.filePath = filePath; |
| 1409 | + m.baseName = baseName; |
| 1410 | + m.size = size; |
| 1411 | + m.suffix = suffix; |
| 1412 | + m.isDir = isDir; |
| 1413 | + m.isFile = isFile; |
| 1414 | + m_files.append(m); |
| 1415 | +} |
| 1416 | |
| 1417 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.h' |
| 1418 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.h 1970-01-01 00:00:00 +0000 |
| 1419 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/MockFolderListModel.h 2017-01-25 13:04:17 +0000 |
| 1420 | @@ -0,0 +1,171 @@ |
| 1421 | +/* |
| 1422 | + * Copyright (C) 2016 Canonical, Ltd. |
| 1423 | + * |
| 1424 | + * This program is free software; you can redistribute it and/or modify |
| 1425 | + * it under the terms of the GNU General Public License as published by |
| 1426 | + * the Free Software Foundation; version 3. |
| 1427 | + * |
| 1428 | + * This program is distributed in the hope that it will be useful, |
| 1429 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 1430 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 1431 | + * GNU General Public License for more details. |
| 1432 | + * |
| 1433 | + * You should have received a copy of the GNU General Public License |
| 1434 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 1435 | + */ |
| 1436 | + |
| 1437 | +#ifndef MOCK_FOLDERLISTMODEL_H |
| 1438 | +#define MOCK_FOLDERLISTMODEL_H |
| 1439 | + |
| 1440 | +#include <QAbstractListModel> |
| 1441 | +#include <QObject> |
| 1442 | +#include <QString> |
| 1443 | +#include <QUrl> |
| 1444 | +#include <QStringList> |
| 1445 | + |
| 1446 | +struct MockFile { |
| 1447 | + QString fileName; |
| 1448 | + QString filePath; |
| 1449 | + QString baseName; |
| 1450 | + qint64 size; |
| 1451 | + QString suffix; |
| 1452 | + bool isDir; |
| 1453 | + bool isFile; |
| 1454 | +}; |
| 1455 | + |
| 1456 | +class MockFolderListModel : public QAbstractListModel |
| 1457 | +{ |
| 1458 | + Q_OBJECT |
| 1459 | + Q_ENUMS(Sort) |
| 1460 | + Q_PROPERTY(QUrl folder READ folder WRITE setFolder NOTIFY folderChanged) |
| 1461 | + Q_PROPERTY(bool caseSensitive READ caseSensitive |
| 1462 | + WRITE setCaseSensitive NOTIFY caseSensitiveChanged) |
| 1463 | + Q_PROPERTY(int count READ count |
| 1464 | + WRITE setCount NOTIFY countChanged) |
| 1465 | + Q_PROPERTY(QStringList nameFilters READ nameFilters |
| 1466 | + WRITE setNameFilters NOTIFY nameFiltersChanged) |
| 1467 | + Q_PROPERTY(QUrl parentFolder READ parentFolder |
| 1468 | + WRITE setParentFolder NOTIFY parentFolderChanged) |
| 1469 | + Q_PROPERTY(QUrl rootFolder READ rootFolder |
| 1470 | + WRITE setRootFolder NOTIFY rootFolderChanged) |
| 1471 | + Q_PROPERTY(bool showDirs READ showDirs |
| 1472 | + WRITE setShowDirs NOTIFY showDirsChanged) |
| 1473 | + Q_PROPERTY(bool showDirsFirst READ showDirsFirst |
| 1474 | + WRITE setShowDirsFirst NOTIFY showDirsFirstChanged) |
| 1475 | + Q_PROPERTY(bool showDotAndDotDot READ showDotAndDotDot |
| 1476 | + WRITE setShowDotAndDotDot NOTIFY showDotAndDotDotChanged) |
| 1477 | + Q_PROPERTY(bool showFiles READ showFiles |
| 1478 | + WRITE setShowFiles NOTIFY showFilesChanged) |
| 1479 | + Q_PROPERTY(bool showHidden READ showHidden |
| 1480 | + WRITE setShowHidden NOTIFY showHiddenChanged) |
| 1481 | + Q_PROPERTY(bool showOnlyReadable READ showOnlyReadable |
| 1482 | + WRITE setShowOnlyReadable NOTIFY showOnlyReadableChanged) |
| 1483 | + Q_PROPERTY(Sort sortField READ sortField |
| 1484 | + WRITE setSortField NOTIFY sortFieldChanged) |
| 1485 | + Q_PROPERTY(bool sortReversed READ sortReversed |
| 1486 | + WRITE setSortReversed NOTIFY sortReversedChanged) |
| 1487 | + |
| 1488 | +public: |
| 1489 | + explicit MockFolderListModel(QObject *parent = 0); |
| 1490 | + |
| 1491 | + enum Roles { |
| 1492 | + FileNameRole = Qt::DisplayRole + 1, |
| 1493 | + FilePathRole, |
| 1494 | + FileURLRole, |
| 1495 | + FileBaseNameRole, |
| 1496 | + FileSuffixRole, |
| 1497 | + FileSizeRole, |
| 1498 | + FileModifiedRole, |
| 1499 | + FileAccessedRole, |
| 1500 | + FileIsDirRole |
| 1501 | + }; |
| 1502 | + |
| 1503 | + enum class Sort : uint |
| 1504 | + { |
| 1505 | + Unsorted = 0, |
| 1506 | + Name, |
| 1507 | + Time, |
| 1508 | + Size, |
| 1509 | + Type |
| 1510 | + }; |
| 1511 | + |
| 1512 | + QUrl folder() const; |
| 1513 | + bool caseSensitive() const; |
| 1514 | + int count() const; |
| 1515 | + QStringList nameFilters() const; |
| 1516 | + QUrl parentFolder() const; |
| 1517 | + QUrl rootFolder() const; |
| 1518 | + bool showDirs() const; |
| 1519 | + bool showDirsFirst() const; |
| 1520 | + bool showDotAndDotDot() const; |
| 1521 | + bool showFiles() const; |
| 1522 | + bool showHidden() const; |
| 1523 | + bool showOnlyReadable() const; |
| 1524 | + Sort sortField() const; |
| 1525 | + bool sortReversed() const; |
| 1526 | + |
| 1527 | + void setCaseSensitive(const QUrl &folder); |
| 1528 | + void setCaseSensitive(const bool caseSensitive); |
| 1529 | + void setCount(const int &count); |
| 1530 | + void setFolder(const QUrl &folder); |
| 1531 | + void setNameFilters(const QStringList &nameFilters); |
| 1532 | + void setParentFolder(const QUrl &parentFolder); |
| 1533 | + void setRootFolder(const QUrl &rootFolder); |
| 1534 | + void setShowDirs(const bool showDirs); |
| 1535 | + void setShowDirsFirst(const bool showDirsFirst); |
| 1536 | + void setShowDotAndDotDot(const bool showDotAndDotDot); |
| 1537 | + void setShowFiles(const bool showFiles); |
| 1538 | + void setShowHidden(const bool showHidden); |
| 1539 | + void setShowOnlyReadable(const bool showOnlyReadable); |
| 1540 | + void setSortField(const Sort &sortField); |
| 1541 | + void setSortReversed(const bool sortReversed); |
| 1542 | + |
| 1543 | + int rowCount(const QModelIndex &parent = QModelIndex()) const override; |
| 1544 | + QModelIndex index(int row, int column = 0, const QModelIndex &parent = QModelIndex()) const override; |
| 1545 | + QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override; |
| 1546 | + QHash<int, QByteArray> roleNames() const override; |
| 1547 | + |
| 1548 | + Q_INVOKABLE void mockAddFile(const QString &fileName, |
| 1549 | + const QString &filePath, |
| 1550 | + const QString &baseName, |
| 1551 | + const qint64 &size, |
| 1552 | + const QString &suffix, |
| 1553 | + const bool isDir, |
| 1554 | + const bool isFile); |
| 1555 | + |
| 1556 | +Q_SIGNALS: |
| 1557 | + void caseSensitiveChanged(); |
| 1558 | + void countChanged(); |
| 1559 | + void folderChanged(); |
| 1560 | + void nameFiltersChanged(); |
| 1561 | + void parentFolderChanged(); |
| 1562 | + void rootFolderChanged(); |
| 1563 | + void showDirsChanged(); |
| 1564 | + void showDirsFirstChanged(); |
| 1565 | + void showDotAndDotDotChanged(); |
| 1566 | + void showFilesChanged(); |
| 1567 | + void showHiddenChanged(); |
| 1568 | + void showOnlyReadableChanged(); |
| 1569 | + void sortFieldChanged(); |
| 1570 | + void sortReversedChanged(); |
| 1571 | + |
| 1572 | +private: |
| 1573 | + QUrl m_folder = QUrl(); |
| 1574 | + bool m_caseSensitive = false; |
| 1575 | + int m_count = false; |
| 1576 | + QStringList m_nameFilters = QStringList(); |
| 1577 | + QUrl m_parentFolder = QUrl(); |
| 1578 | + QUrl m_rootFolder = QUrl(); |
| 1579 | + bool m_showDirs = false; |
| 1580 | + bool m_showDirsFirst = false; |
| 1581 | + bool m_showDotAndDotDot = false; |
| 1582 | + bool m_showFiles = false; |
| 1583 | + bool m_showHidden = false; |
| 1584 | + bool m_showOnlyReadable = false; |
| 1585 | + Sort m_sortField = Sort::Unsorted; |
| 1586 | + bool m_sortReversed = false; |
| 1587 | + |
| 1588 | + QList<MockFile> m_files; |
| 1589 | +}; |
| 1590 | + |
| 1591 | +#endif // MOCK_FOLDERLISTMODEL_H |
| 1592 | |
| 1593 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.cpp' |
| 1594 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.cpp 1970-01-01 00:00:00 +0000 |
| 1595 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.cpp 2017-01-25 13:04:17 +0000 |
| 1596 | @@ -0,0 +1,26 @@ |
| 1597 | +/* |
| 1598 | + * Copyright (C) 2016 Canonical, Ltd. |
| 1599 | + * |
| 1600 | + * This program is free software; you can redistribute it and/or modify |
| 1601 | + * it under the terms of the GNU General Public License as published by |
| 1602 | + * the Free Software Foundation; version 3. |
| 1603 | + * |
| 1604 | + * This program is distributed in the hope that it will be useful, |
| 1605 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 1606 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 1607 | + * GNU General Public License for more details. |
| 1608 | + * |
| 1609 | + * You should have received a copy of the GNU General Public License |
| 1610 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 1611 | + */ |
| 1612 | + |
| 1613 | +#include "plugin.h" |
| 1614 | +#include "MockFolderListModel.h" |
| 1615 | + |
| 1616 | +#include <QtQml/qqml.h> |
| 1617 | + |
| 1618 | +void MockQtLabsFolderListModelPlugin::registerTypes(const char *uri) |
| 1619 | +{ |
| 1620 | + Q_ASSERT(uri == QLatin1String("Qt.labs.folderlistmodel")); |
| 1621 | + qmlRegisterType<MockFolderListModel>(uri, 2, 1, "FolderListModel"); |
| 1622 | +} |
| 1623 | |
| 1624 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.h' |
| 1625 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.h 1970-01-01 00:00:00 +0000 |
| 1626 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/plugin.h 2017-01-25 13:04:17 +0000 |
| 1627 | @@ -0,0 +1,31 @@ |
| 1628 | +/* |
| 1629 | + * Copyright (C) 2016 Canonical, Ltd. |
| 1630 | + * |
| 1631 | + * This program is free software; you can redistribute it and/or modify |
| 1632 | + * it under the terms of the GNU General Public License as published by |
| 1633 | + * the Free Software Foundation; version 3. |
| 1634 | + * |
| 1635 | + * This program is distributed in the hope that it will be useful, |
| 1636 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 1637 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 1638 | + * GNU General Public License for more details. |
| 1639 | + * |
| 1640 | + * You should have received a copy of the GNU General Public License |
| 1641 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 1642 | + */ |
| 1643 | + |
| 1644 | +#ifndef QTLABS_FOLDERLISTMODEL_PLUGIN_H |
| 1645 | +#define QTLABS_FOLDERLISTMODEL_PLUGIN_H |
| 1646 | + |
| 1647 | +#include <QtQml/QQmlExtensionPlugin> |
| 1648 | + |
| 1649 | +class MockQtLabsFolderListModelPlugin : public QQmlExtensionPlugin |
| 1650 | +{ |
| 1651 | + Q_OBJECT |
| 1652 | + Q_PLUGIN_METADATA(IID "org.qt-project.Qt.QQmlExtensionInterface") |
| 1653 | + |
| 1654 | +public: |
| 1655 | + void registerTypes(const char *uri) override; |
| 1656 | +}; |
| 1657 | + |
| 1658 | +#endif // QTLABS_FOLDERLISTMODEL_PLUGIN_H |
| 1659 | |
| 1660 | === added file 'tests/qmltests/mocks/Qt/labs/folderlistmodel/qmldir' |
| 1661 | --- tests/qmltests/mocks/Qt/labs/folderlistmodel/qmldir 1970-01-01 00:00:00 +0000 |
| 1662 | +++ tests/qmltests/mocks/Qt/labs/folderlistmodel/qmldir 2017-01-25 13:04:17 +0000 |
| 1663 | @@ -0,0 +1,2 @@ |
| 1664 | +module Qt.labs.folderlistmodel |
| 1665 | +plugin QtLabsFolderListModelQml |

One copyright question inline