diff --git a/CMakeLists.txt b/CMakeLists.txt index e12cd79a..bcce066f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,160 +1,160 @@ cmake_minimum_required(VERSION 3.5) set(KF5_VERSION "5.69.0") # handled by release scripts set(KF5_DEP_VERSION "5.68.0") # handled by release scripts project(KNewStuff VERSION ${KF5_VERSION}) # Require at least C++14 set(CMAKE_CXX_STANDARD 14) set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_EXTENSIONS OFF) include(FeatureSummary) find_package(ECM 5.68.0 NO_MODULE) set_package_properties(ECM PROPERTIES TYPE REQUIRED DESCRIPTION "Extra CMake Modules." URL "https://commits.kde.org/extra-cmake-modules") feature_summary(WHAT REQUIRED_PACKAGES_NOT_FOUND FATAL_ON_MISSING_REQUIRED_PACKAGES) set(CMAKE_MODULE_PATH ${ECM_MODULE_PATH}) include(ECMQtDeclareLoggingCategory) include(KDEInstallDirs) include(KDECMakeSettings) include(KDEFrameworkCompilerSettings NO_POLICY_SCOPE) set(REQUIRED_QT_VERSION 5.12.0) find_package(Qt5 ${REQUIRED_QT_VERSION} NO_MODULE REQUIRED COMPONENTS Widgets Xml) find_package(Qt5 ${REQUIRED_QT_VERSION} NO_MODULE COMPONENTS Qml Quick) find_package(KF5Archive ${KF5_DEP_VERSION} REQUIRED) find_package(KF5Completion ${KF5_DEP_VERSION} REQUIRED) find_package(KF5Config ${KF5_DEP_VERSION} REQUIRED) find_package(KF5CoreAddons ${KF5_DEP_VERSION} REQUIRED) find_package(KF5I18n ${KF5_DEP_VERSION} REQUIRED) find_package(KF5IconThemes ${KF5_DEP_VERSION} REQUIRED) find_package(KF5KIO ${KF5_DEP_VERSION} REQUIRED) find_package(KF5ItemViews ${KF5_DEP_VERSION} REQUIRED) find_package(KF5Service ${KF5_DEP_VERSION} REQUIRED) find_package(KF5TextWidgets ${KF5_DEP_VERSION} REQUIRED) find_package(KF5WidgetsAddons ${KF5_DEP_VERSION} REQUIRED) find_package(KF5XmlGui ${KF5_DEP_VERSION} REQUIRED) include(ECMGenerateExportHeader) include(ECMSetupVersion) include(ECMGenerateHeaders) include(ECMAddQch) find_package(KF5Attica ${KF5_DEP_VERSION} CONFIG REQUIRED) set_package_properties(KF5Attica PROPERTIES DESCRIPTION "A Qt library that implements the Open Collaboration Services API" PURPOSE "Support for Get Hot New Stuff in KNewStuff" URL "https://commits.kde.org/attica" TYPE REQUIRED ) -find_package(KF5Kirigami2 2.1.0) +find_package(KF5Kirigami2 2.12.0) set_package_properties(KF5Kirigami2 PROPERTIES DESCRIPTION "KDE's lightweight user interface framework for mobile and convergent applications" URL "https://techbase.kde.org/Kirigami" PURPOSE "Required by KNewStuffQuick's qml components" TYPE RUNTIME) option(BUILD_QCH "Build API documentation in QCH format (for e.g. Qt Assistant, Qt Creator & KDevelop)" OFF) add_feature_info(QCH ${BUILD_QCH} "API documentation in QCH format (for e.g. Qt Assistant, Qt Creator & KDevelop)") ecm_setup_version(PROJECT VARIABLE_PREFIX KNEWSTUFF VERSION_HEADER "${CMAKE_CURRENT_BINARY_DIR}/knewstuff_version.h" PACKAGE_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffConfigVersion.cmake" SOVERSION 5) ecm_setup_version(PROJECT VARIABLE_PREFIX KNEWSTUFFCORE VERSION_HEADER "${CMAKE_CURRENT_BINARY_DIR}/knewstuffcore_version.h" PACKAGE_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffCoreConfigVersion.cmake" SOVERSION 5) ecm_setup_version(PROJECT VARIABLE_PREFIX KNEWSTUFFQUICK VERSION_HEADER "${CMAKE_CURRENT_BINARY_DIR}/knewstuffquick_version.h" PACKAGE_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffQuickConfigVersion.cmake" SOVERSION 5) add_definitions(-DTRANSLATION_DOMAIN=\"knewstuff5\") add_definitions(-DQT_DISABLE_DEPRECATED_BEFORE=0x050d00) add_definitions(-DKF_DISABLE_DEPRECATED_BEFORE_AND_AT=0x054400) add_definitions(-DQT_NO_FOREACH) if (IS_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/po") ki18n_install(po) endif() add_subdirectory(data) add_subdirectory(src) if (BUILD_TESTING) add_subdirectory(autotests) add_subdirectory(tests) endif() set(CMAKECONFIG_INSTALL_DIR "${KDE_INSTALL_CMAKEPACKAGEDIR}/KF5NewStuff") set(CMAKECONFIGCORE_INSTALL_DIR "${KDE_INSTALL_CMAKEPACKAGEDIR}/KF5NewStuffCore") set(CMAKECONFIGQUICK_INSTALL_DIR "${KDE_INSTALL_CMAKEPACKAGEDIR}/KF5NewStuffQuick") if (BUILD_QCH) ecm_install_qch_export( TARGETS KF5NewStuff_QCH FILE KF5NewStuffQchTargets.cmake DESTINATION "${CMAKECONFIG_INSTALL_DIR}" COMPONENT Devel ) set(PACKAGE_INCLUDE_QCHTARGETS "include(\"\${CMAKE_CURRENT_LIST_DIR}/KF5NewStuffQchTargets.cmake\")") ecm_install_qch_export( TARGETS KF5NewStuffCore_QCH FILE KF5NewStuffCoreQchTargets.cmake DESTINATION "${CMAKECONFIGCORE_INSTALL_DIR}" COMPONENT Devel ) set(PACKAGE_INCLUDE_CORE_QCHTARGETS "include(\"\${CMAKE_CURRENT_LIST_DIR}/KF5NewStuffCoreQchTargets.cmake\")") # TODO: KF5NewStuffQuick endif() include(CMakePackageConfigHelpers) configure_package_config_file( "${CMAKE_CURRENT_SOURCE_DIR}/KF5NewStuffConfig.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffConfig.cmake" INSTALL_DESTINATION ${CMAKECONFIG_INSTALL_DIR} ) configure_package_config_file( "${CMAKE_CURRENT_SOURCE_DIR}/KF5NewStuffCoreConfig.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffCoreConfig.cmake" INSTALL_DESTINATION ${CMAKECONFIGCORE_INSTALL_DIR} ) configure_package_config_file( "${CMAKE_CURRENT_SOURCE_DIR}/KF5NewStuffQuickConfig.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffQuickConfig.cmake" INSTALL_DESTINATION ${CMAKECONFIGQUICK_INSTALL_DIR} ) install(FILES "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffConfig.cmake" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffConfigVersion.cmake" DESTINATION "${CMAKECONFIG_INSTALL_DIR}" COMPONENT Devel ) install(FILES "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffCoreConfig.cmake" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffCoreConfigVersion.cmake" DESTINATION "${CMAKECONFIGCORE_INSTALL_DIR}" COMPONENT Devel ) install(FILES "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffQuickConfig.cmake" "${CMAKE_CURRENT_BINARY_DIR}/KF5NewStuffQuickConfigVersion.cmake" DESTINATION "${CMAKECONFIGQUICK_INSTALL_DIR}" COMPONENT Devel ) install(EXPORT KF5NewStuffTargets DESTINATION "${CMAKECONFIG_INSTALL_DIR}" FILE KF5NewStuffTargets.cmake NAMESPACE KF5:: ) install(EXPORT KF5NewStuffCoreTargets DESTINATION "${CMAKECONFIGCORE_INSTALL_DIR}" FILE KF5NewStuffCoreTargets.cmake NAMESPACE KF5:: ) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/knewstuff_version.h ${CMAKE_CURRENT_BINARY_DIR}/knewstuffcore_version.h ${CMAKE_CURRENT_BINARY_DIR}/knewstuffquick_version.h DESTINATION ${KDE_INSTALL_INCLUDEDIR_KF5} COMPONENT Devel ) feature_summary(WHAT ALL FATAL_ON_MISSING_REQUIRED_PACKAGES) diff --git a/src/qtquick/qml/private/EntryScreenshots.qml b/src/qtquick/qml/private/EntryScreenshots.qml index 067d5578..8e1ff52c 100644 --- a/src/qtquick/qml/private/EntryScreenshots.qml +++ b/src/qtquick/qml/private/EntryScreenshots.qml @@ -1,177 +1,176 @@ /* * Copyright (C) 2012 Aleix Pol Gonzalez * Copyright (C) 2019 Dan Leinir Turthra Jensen * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU Library/Lesser General Public License * version 2, or (at your option) any later version, as published by the * Free Software Foundation * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details * * You should have received a copy of the GNU Library/Lesser General Public * License along with this program; if not, write to the * Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ import QtQuick 2.11 import QtQuick.Controls 2.11 import QtQuick.Layouts 1.11 import QtGraphicalEffects 1.11 -import org.kde.kirigami 2.5 as Kirigami +import org.kde.kirigami 2.12 as Kirigami Flickable { id: root property alias screenshotsModel: screenshotsRep.model readonly property alias count: screenshotsRep.count property int currentIndex: -1 property Item currentItem: screenshotsRep.itemAt(currentIndex) Layout.preferredHeight: Kirigami.Units.gridUnit * 13 contentHeight: height contentWidth: screenshotsLayout.width Popup { id: overlay parent: applicationWindow().overlay modal: true clip: false x: (parent.width - width)/2 y: (parent.height - height)/2 readonly property real proportion: overlayImage.sourceSize.width>1 ? overlayImage.sourceSize.height/overlayImage.sourceSize.width : 1 height: overlayImage.status == Image.Loading ? Kirigami.Units.gridUnit * 5 : Math.min(parent.height * 0.9, (parent.width * 0.9) * proportion, overlayImage.sourceSize.height) width: height/proportion BusyIndicator { id: indicator visible: running running: overlayImage.status == Image.Loading anchors.fill: parent } Image { id: overlayImage anchors.fill: parent source: root.currentItem ? root.currentItem.imageSource : "" fillMode: Image.PreserveAspectFit smooth: true } Button { anchors { right: parent.left verticalCenter: parent.verticalCenter } visible: leftAction.visible icon.name: leftAction.iconName onClicked: leftAction.triggered(null) } Button { anchors { left: parent.right verticalCenter: parent.verticalCenter } visible: rightAction.visible icon.name: rightAction.iconName onClicked: rightAction.triggered(null) } Kirigami.Action { id: leftAction icon.name: "arrow-left" enabled: overlay.visible && visible visible: root.currentIndex >= 1 && !indicator.running onTriggered: root.currentIndex = (root.currentIndex - 1) % root.count } Kirigami.Action { id: rightAction icon.name: "arrow-right" enabled: overlay.visible && visible visible: root.currentIndex < (root.count - 1) && !indicator.running onTriggered: root.currentIndex = (root.currentIndex + 1) % root.count } } Row { id: screenshotsLayout height: root.contentHeight spacing: Kirigami.Units.largeSpacing + leftPadding: spacing + rightPadding: spacing focus: overlay.visible Keys.onLeftPressed: if (leftAction.visible) leftAction.trigger() Keys.onRightPressed: if (rightAction.visible) rightAction.trigger() Repeater { id: screenshotsRep delegate: MouseArea { readonly property url imageSource: modelData readonly property real proportion: thumbnail.sourceSize.width>1 ? thumbnail.sourceSize.height/thumbnail.sourceSize.width : 1 + anchors.verticalCenter: parent.verticalCenter width: Math.max(50, height/proportion) - height: screenshotsLayout.height + height: screenshotsLayout.height - 2 * Kirigami.Units.largeSpacing hoverEnabled: true cursorShape: Qt.PointingHandCursor onClicked: { root.currentIndex = index overlay.open() } - DropShadow { - source: thumbnail + Kirigami.ShadowedRectangle { anchors.fill: thumbnail - verticalOffset: Kirigami.Units.largeSpacing - horizontalOffset: 0 - radius: 12.0 - samples: 25 - color: Kirigami.Theme.disabledTextColor - cached: true + Kirigami.Theme.colorSet: Kirigami.Theme.View + shadow.size: Kirigami.Units.largeSpacing + shadow.color: Qt.rgba(0, 0, 0, 0.3) } BusyIndicator { visible: running running: thumbnail.status == Image.Loading anchors.centerIn: parent } Image { id: thumbnail source: modelData height: parent.height fillMode: Image.PreserveAspectFit smooth: true } } } } clip: true readonly property var leftShadow: Shadow { parent: root anchors { left: parent.left top: parent.top bottom: parent.bottom } edge: Qt.LeftEdge width: Math.max(0, Math.min(root.width/5, root.contentX)) } readonly property var rightShadow: Shadow { parent: root anchors { right: parent.right top: parent.top bottom: parent.bottom } edge: Qt.RightEdge width: Math.max(0, Math.min(root.contentWidth - root.contentX - root.width)/5) } } diff --git a/src/qtquick/qml/private/GridTileDelegate.qml b/src/qtquick/qml/private/GridTileDelegate.qml index d91269a0..47f37258 100644 --- a/src/qtquick/qml/private/GridTileDelegate.qml +++ b/src/qtquick/qml/private/GridTileDelegate.qml @@ -1,183 +1,176 @@ /* Copyright (c) 2015 Marco Martin Copyright (c) 2019 Dan Leinir Turthra Jensen This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License version 2 as published by the Free Software Foundation. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ import QtQuick 2.11 import QtQuick.Controls 2.11 as Controls import QtQuick.Templates 2.11 as T2 import QtQuick.Layouts 1.11 import QtGraphicalEffects 1.11 -import org.kde.kirigami 2.2 as Kirigami +import org.kde.kirigami 2.12 as Kirigami /** * Base delegate for KControlmodules based on Grid views of thumbnails * Use the onClicked signal handler for managing the main action when * the user clicks on the tile, modified from the original GridDelegate * from the KCM module * @inherits QtQuick.Templates.ItemDelegate */ T2.ItemDelegate { id: delegate /** * toolTip: string * string for a tooltip for the whole delegate */ property string toolTip /** * tile: Item * the item actually implementing the tile: the visualization is up to the implementation */ property alias tile: thumbnailArea.data /** * thumbnailAvailable: bool * Set it to true when a tile is actually available: when false, * a default icon will be shown instead of the actual tile. */ property bool thumbnailAvailable: false /** * actions: list * A list of extra actions for the thumbnails. They will be shown as * icons on the bottom-right corner of the tile on mouse over */ property list actions /** * actionsAnchors: anchors * The anchors of the actions listing */ property alias actionsAnchors: actionsScope.anchors width: GridView.view.cellWidth height: GridView.view.cellHeight hoverEnabled: true - Rectangle { + Kirigami.ShadowedRectangle { id: tile anchors.centerIn: parent width: Kirigami.Settings.isMobile ? delegate.width - Kirigami.Units.gridUnit : Math.min(delegate.GridView.view.implicitCellWidth, delegate.width - Kirigami.Units.gridUnit) height: Math.min(delegate.GridView.view.implicitCellHeight, delegate.height - Kirigami.Units.gridUnit) radius: Kirigami.Units.smallSpacing Kirigami.Theme.inherit: false Kirigami.Theme.colorSet: Kirigami.Theme.View + shadow.xOffset: 0 + shadow.yOffset: 2 + shadow.size: 10 + shadow.color: Qt.rgba(0, 0, 0, 0.3) + color: { if (delegate.GridView.isCurrentItem) { return Kirigami.Theme.highlightColor; } else if (parent.hovered) { return Kirigami.Theme.highlightColor; } else { return Kirigami.Theme.backgroundColor; } } Behavior on color { ColorAnimation { duration: Kirigami.Units.longDuration easing.type: Easing.OutQuad } } Rectangle { id: thumbnailArea radius: Kirigami.Units.smallSpacing/2 anchors { fill: parent margins: Kirigami.Units.smallSpacing } color: Kirigami.Theme.backgroundColor Kirigami.Icon { visible: !delegate.thumbnailAvailable anchors.centerIn: parent width: Kirigami.Units.iconSizes.large height: width source: delegate.text === i18nd("knewstuff5", "None") ? "edit-none" : "view-preview" } } Rectangle { anchors.fill: thumbnailArea visible: actionsColumn.children.length > 0 opacity: Kirigami.Settings.isMobile || delegate.hovered || (actionsScope.focus) ? 1 : 0 radius: Kirigami.Units.smallSpacing color: Kirigami.Settings.isMobile ? "transparent" : Qt.rgba(1, 1, 1, 0.2) Behavior on opacity { NumberAnimation { duration: Kirigami.Units.longDuration easing.type: Easing.OutQuad } } FocusScope { id: actionsScope anchors { right: parent.right rightMargin: Kirigami.Units.smallSpacing top: parent.top topMargin: Kirigami.Units.smallSpacing } width: actionsColumn.width height: actionsColumn.height ColumnLayout { id: actionsColumn Repeater { model: delegate.actions delegate: Controls.Button { icon.name: modelData.iconName text: modelData.text activeFocusOnTab: focus || delegate.focus - onClicked: { - delegate.clicked() - modelData.trigger() - } + onClicked: modelData.trigger() enabled: modelData.enabled visible: modelData.visible //NOTE: there aren't any global settings where to take "official" tooltip timeouts Controls.ToolTip.delay: 1000 Controls.ToolTip.timeout: 5000 Controls.ToolTip.visible: (Kirigami.Settings.isMobile ? pressed : hovered) && modelData.tooltip.length > 0 Controls.ToolTip.text: modelData.tooltip } } } } } - // Bug 397367: explicitly using "delegate" as otherwise it crashes when switching between KCMs - layer.enabled: delegate.GraphicsInfo.api === GraphicsInfo.OpenGL - layer.effect: DropShadow { - horizontalOffset: 0 - verticalOffset: 2 - radius: 10 - samples: 32 - color: Qt.rgba(0, 0, 0, 0.3) - } } Controls.ToolTip.delay: 1000 Controls.ToolTip.timeout: 5000 Controls.ToolTip.visible: hovered && delegate.toolTip.length > 0 Controls.ToolTip.text: toolTip } diff --git a/src/qtquick/qml/private/entrygriddelegates/BigPreviewDelegate.qml b/src/qtquick/qml/private/entrygriddelegates/BigPreviewDelegate.qml index 96116301..8eaee43c 100644 --- a/src/qtquick/qml/private/entrygriddelegates/BigPreviewDelegate.qml +++ b/src/qtquick/qml/private/entrygriddelegates/BigPreviewDelegate.qml @@ -1,188 +1,187 @@ /* * Copyright (C) 2019 Dan Leinir Turthra Jensen * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) version 3, or any * later version accepted by the membership of KDE e.V. (or its * successor approved by the membership of KDE e.V.), which shall * act as a proxy defined in Section 6 of version 3 of the license. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library. If not, see . * */ import QtQuick 2.11 import QtQuick.Controls 2.11 as QtControls import QtQuick.Layouts 1.11 as QtLayouts import QtGraphicalEffects 1.11 as QtEffects -import org.kde.kirigami 2.7 as Kirigami +import org.kde.kirigami 2.12 as Kirigami import org.kde.newstuff 1.62 as NewStuff import ".." as Private Private.GridTileDelegate { id: component actionsAnchors.topMargin: bigPreview.height + Kirigami.Units.smallSpacing * 2 function showDetails() { pageStack.push(detailsPage, { newStuffModel: GridView.view.model, index: model.index, name: model.name, author: model.author, previews: model.previews, shortSummary: model.shortSummary, summary: model.summary, homepage: model.homepage, donationLink: model.donationLink, status: model.status, commentsCount: model.numberOfComments, rating: model.rating, downloadCount: model.downloadCount, downloadLinks: model.downloadLinks, providerId: model.providerId }); } actions: [ Kirigami.Action { text: root.useLabel iconName: "dialog-ok-apply" onTriggered: { model.adopt(model.index); } enabled: (model.status == NewStuff.ItemsModel.InstalledStatus || model.status == NewStuff.ItemsModel.UpdateableStatus) && newStuffEngine.hasAdoptionCommand visible: enabled }, Kirigami.Action { text: model.downloadLinks.length === 1 ? i18ndc("knewstuff5", "Request installation of this item, available when there is exactly one downloadable item", "Install") : i18ndc("knewstuff5", "Show installation options, where there is more than one downloadable item", "Install..."); iconName: "install" onTriggered: { if (model.downloadLinks.length === 1) { newStuffModel.installItem(model.index, NewStuff.ItemsModel.FirstLinkId); } else { downloadItemsSheet.downloadLinks = model.downloadLinks; downloadItemsSheet.entryId = model.index; downloadItemsSheet.open(); } } enabled: model.status == NewStuff.ItemsModel.DownloadableStatus || model.status == NewStuff.ItemsModel.DeletedStatus; visible: enabled; }, Kirigami.Action { text: i18ndc("knewstuff5", "Request updating of this item", "Update"); iconName: "update" onTriggered: { newStuffModel.updateItem(model.index); } enabled: model.status == NewStuff.ItemsModel.UpdateableStatus; visible: enabled; }, Kirigami.Action { text: root.uninstallLabel iconName: "uninstall" onTriggered: { newStuffModel.uninstallItem(model.index); } enabled: model.status == NewStuff.ItemsModel.InstalledStatus visible: enabled; } ] thumbnailAvailable: model.previewsSmall.length > 0 tile: Item { anchors { fill: parent margins: Kirigami.Units.smallSpacing } QtLayouts.ColumnLayout { anchors.fill: parent; Item { QtLayouts.Layout.fillWidth: true QtLayouts.Layout.minimumHeight: width / 1.8 QtLayouts.Layout.maximumHeight: width / 1.8 + Kirigami.ShadowedRectangle { + anchors.centerIn: bigPreview; + width: Math.min(bigPreview.paintedWidth, bigPreview.width); + height: Math.min(bigPreview.paintedHeight, bigPreview.height); + Kirigami.Theme.colorSet: Kirigami.Theme.View + shadow.size: 10 + shadow.color: Qt.rgba(0, 0, 0, 0.3) + } Image { id: bigPreview asynchronous: true; fillMode: Image.PreserveAspectCrop; source: thumbnailAvailable ? model.previews[0] : ""; anchors.fill: parent } - QtEffects.DropShadow { - anchors.fill: bigPreview - horizontalOffset: 0 - verticalOffset: 0 - radius: Kirigami.Units.largeSpacing - samples: radius * 2 - color: "#80000000" - source: bigPreview - } Kirigami.Icon { id: updateAvailableBadge; opacity: (model.status == NewStuff.ItemsModel.UpdateableStatus) ? 1 : 0; Behavior on opacity { NumberAnimation { duration: Kirigami.Units.shortDuration; } } anchors { top: parent.top; left: parent.left; margins: -Kirigami.Units.smallSpacing; } height: Kirigami.Units.iconSizes.medium; width: height; source: "package-installed-outdated"; } Kirigami.Icon { id: installedBadge; opacity: (model.status == NewStuff.ItemsModel.InstalledStatus) ? 1 : 0; Behavior on opacity { NumberAnimation { duration: Kirigami.Units.shortDuration; } } anchors { top: parent.top; left: parent.left; } height: Kirigami.Units.iconSizes.medium; width: height; source: "package-installed-updated"; } } Private.Rating { QtLayouts.Layout.fillWidth: true rating: model.rating / 10 } Kirigami.Heading { QtLayouts.Layout.fillWidth: true level: 5 elide: Text.ElideRight text: i18ndc("knewstuff5", "The number of times the item has been downloaded", "%1 downloads", model.downloadCount) } Kirigami.Heading { QtLayouts.Layout.fillWidth: true elide: Text.ElideRight level: 3 text: model.name } Kirigami.Heading { QtLayouts.Layout.fillWidth: true elide: Text.ElideRight level: 4 textFormat: Text.StyledText text: i18ndc("knewstuff5", "Subheading for the tile view, located immediately underneath the name of the item", "By %1", model.author.name) } QtControls.Label { QtLayouts.Layout.fillWidth: true QtLayouts.Layout.fillHeight: true wrapMode: Text.Wrap text: model.shortSummary.length > 0 ? model.shortSummary : model.summary elide: Text.ElideRight } } FeedbackOverlay { anchors.fill: parent newStuffModel: component.GridView.view.model } MouseArea { anchors.fill: parent; cursorShape: Qt.PointingHandCursor; onClicked: component.showDetails(); } } } diff --git a/src/qtquick/qml/private/entrygriddelegates/TileDelegate.qml b/src/qtquick/qml/private/entrygriddelegates/TileDelegate.qml index b6bbef44..81cad672 100644 --- a/src/qtquick/qml/private/entrygriddelegates/TileDelegate.qml +++ b/src/qtquick/qml/private/entrygriddelegates/TileDelegate.qml @@ -1,211 +1,210 @@ /* * Copyright (C) 2019 Dan Leinir Turthra Jensen * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) version 3, or any * later version accepted by the membership of KDE e.V. (or its * successor approved by the membership of KDE e.V.), which shall * act as a proxy defined in Section 6 of version 3 of the license. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library. If not, see . * */ import QtQuick 2.11 import QtQuick.Controls 2.11 as QtControls import QtQuick.Layouts 1.11 as QtLayouts import QtGraphicalEffects 1.11 as QtEffects -import org.kde.kirigami 2.7 as Kirigami +import org.kde.kirigami 2.12 as Kirigami import org.kde.newstuff 1.62 as NewStuff import ".." as Private Private.GridTileDelegate { id: component property string useLabel property string uninstallLabel function showDetails() { pageStack.push(detailsPage, { newStuffModel: GridView.view.model, index: model.index, name: model.name, author: model.author, previews: model.previews, shortSummary: model.shortSummary, summary: model.summary, homepage: model.homepage, donationLink: model.donationLink, status: model.status, commentsCount: model.numberOfComments, rating: model.rating, downloadCount: model.downloadCount, downloadLinks: model.downloadLinks, providerId: model.providerId }); } actions: [ Kirigami.Action { text: component.useLabel iconName: "dialog-ok-apply" onTriggered: { model.adopt(model.index); } enabled: (model.status == NewStuff.ItemsModel.InstalledStatus || model.status == NewStuff.ItemsModel.UpdateableStatus) && newStuffEngine.hasAdoptionCommand visible: enabled }, Kirigami.Action { text: model.downloadLinks.length === 1 ? i18ndc("knewstuff5", "Request installation of this item, available when there is exactly one downloadable item", "Install") : i18ndc("knewstuff5", "Show installation options, where there is more than one downloadable item", "Install..."); iconName: "install" onTriggered: { if (model.downloadLinks.length === 1) { newStuffModel.installItem(model.index, NewStuff.ItemsModel.FirstLinkId); } else { downloadItemsSheet.downloadLinks = model.downloadLinks; downloadItemsSheet.entryId = model.index; downloadItemsSheet.open(); } } enabled: model.status == NewStuff.ItemsModel.DownloadableStatus || model.status == NewStuff.ItemsModel.DeletedStatus; visible: enabled; }, Kirigami.Action { text: i18ndc("knewstuff5", "Request updating of this item", "Update"); iconName: "update" onTriggered: { newStuffModel.updateItem(model.index); } enabled: model.status == NewStuff.ItemsModel.UpdateableStatus; visible: enabled; }, Kirigami.Action { text: component.uninstallLabel iconName: "uninstall" onTriggered: { newStuffModel.uninstallItem(model.index); } enabled: model.status == NewStuff.ItemsModel.InstalledStatus visible: enabled; }, Kirigami.Action { text: i18ndc("knewstuff5", "Show a page with details for this item", "Details...") iconName: "documentinfo" onTriggered: { component.showDetails(); } } ] thumbnailAvailable: model.previewsSmall.length > 0 tile: Item { anchors { fill: parent margins: Kirigami.Units.smallSpacing } QtLayouts.GridLayout { anchors.fill: parent; columns: 2 QtLayouts.ColumnLayout { QtLayouts.Layout.minimumWidth: view.implicitCellWidth / 5 QtLayouts.Layout.maximumWidth: view.implicitCellWidth / 5 Item { QtLayouts.Layout.fillWidth: true QtLayouts.Layout.minimumHeight: width QtLayouts.Layout.maximumHeight: width + Kirigami.ShadowedRectangle { + anchors.centerIn: tilePreview; + width: Math.min(tilePreview.paintedWidth, tilePreview.width); + height: Math.min(tilePreview.paintedHeight, tilePreview.height); + Kirigami.Theme.colorSet: Kirigami.Theme.View + shadow.size: Kirigami.Units.largeSpacing + shadow.color: Qt.rgba(0, 0, 0, 0.3) + } Image { id: tilePreview asynchronous: true; fillMode: Image.PreserveAspectFit; source: thumbnailAvailable ? model.previewsSmall[0] : ""; anchors { fill: parent margins: Kirigami.Units.smallSpacing } verticalAlignment: Image.AlignTop } - QtEffects.DropShadow { - anchors.fill: tilePreview - horizontalOffset: 0 - verticalOffset: 0 - radius: Kirigami.Units.largeSpacing - samples: radius * 2 - color: "#80000000" - source: tilePreview - } Kirigami.Icon { id: updateAvailableBadge; opacity: (model.status == NewStuff.ItemsModel.UpdateableStatus) ? 1 : 0; Behavior on opacity { NumberAnimation { duration: Kirigami.Units.shortDuration; } } anchors { top: parent.top; left: parent.left; margins: -Kirigami.Units.smallSpacing; } height: Kirigami.Units.iconSizes.smallMedium; width: height; source: "package-installed-outdated"; } Kirigami.Icon { id: installedBadge; opacity: (model.status == NewStuff.ItemsModel.InstalledStatus) ? 1 : 0; Behavior on opacity { NumberAnimation { duration: Kirigami.Units.shortDuration; } } anchors { top: parent.top; left: parent.left; margins: -Kirigami.Units.smallSpacing; } height: Kirigami.Units.iconSizes.smallMedium; width: height; source: "package-installed-updated"; } } Item { QtLayouts.Layout.fillHeight: true } } QtLayouts.ColumnLayout { QtLayouts.Layout.fillWidth: true QtLayouts.Layout.fillHeight: true Kirigami.Heading { QtLayouts.Layout.fillWidth: true elide: Text.ElideRight level: 3 text: model.name } Kirigami.Heading { QtLayouts.Layout.fillWidth: true elide: Text.ElideRight level: 4 textFormat: Text.StyledText text: i18ndc("knewstuff5", "Subheading for the tile view, located immediately underneath the name of the item", "By %1", model.author.name) } QtControls.Label { QtLayouts.Layout.fillWidth: true QtLayouts.Layout.fillHeight: true wrapMode: Text.Wrap text: model.shortSummary.length > 0 ? model.shortSummary : model.summary elide: Text.ElideRight } } Private.Rating { QtLayouts.Layout.fillWidth: true rating: model.rating / 10 } Kirigami.Heading { QtLayouts.Layout.fillWidth: true level: 5 elide: Text.ElideRight text: i18ndc("knewstuff5", "The number of times the item has been downloaded", "%1 downloads", model.downloadCount) } } FeedbackOverlay { anchors.fill: parent newStuffModel: component.GridView.view.model } MouseArea { anchors.fill: parent; cursorShape: Qt.PointingHandCursor; onClicked: component.showDetails(); } } }