BasicPlasmoidHeading component

plasmoids can use it as a standard heading with a config button and a
menu with all actions. this heading would be visible only when
plasmoids are not in the systemtray which has an header that replaces it
This commit is contained in:
Marco Martin 2020-11-05 16:51:11 +00:00
parent e845f3dbcc
commit 18ee2d9eed
7 changed files with 157 additions and 0 deletions

View File

@ -246,6 +246,9 @@ void QMenuProxy::addMenuItem(QMenuItem *item, QMenuItem *before)
m_menu->addAction(item->action()); m_menu->addAction(item->action());
m_items << item; m_items << item;
} }
connect(item, &QMenuItem::destroyed, this, [this, item]() {
removeMenuItem(item);
});
} }
void QMenuProxy::addSection(const QString &text) void QMenuProxy::addSection(const QString &text)

View File

@ -50,6 +50,7 @@ void QMenuItem::setAction(QAction *a)
connect(this, &QQuickItem::visibleChanged, this, &QMenuItem::updateAction); connect(this, &QQuickItem::visibleChanged, this, &QMenuItem::updateAction);
connect(this, &QQuickItem::enabledChanged, this, &QMenuItem::updateAction); connect(this, &QQuickItem::enabledChanged, this, &QMenuItem::updateAction);
connect(this, &QObject::destroyed, this, &QMenuItem::deleteLater);
emit actionChanged(); emit actionChanged();
} }

View File

@ -0,0 +1,130 @@
/*
SPDX-FileCopyrightText: 2020 Marco Martin <mart@kde.org>
SPDX-License-Identifier: LGPL-2.0-or-later
*/
import QtQuick 2.12
import QtQuick.Layouts 1.12
import org.kde.plasma.core 2.0 as PlasmaCore
import org.kde.plasma.components 2.0 as PC2
import org.kde.plasma.components 3.0 as PlasmaComponents
/**
* A standard basic header for plasmoids which has title, a config button and
* a popup menu with all extra plasmoid actions.
* By default, it will be invisible when the plamsoid is in the system tray, as it provides a replacement header with the same features
*
*
* @inherit PlasmoidHeading
*/
PlasmoidHeading {
/**
* extraControls: list<QtObject>
* any extra control and button that may be inserted in the heading
*/
default property alias extraControls: extraControlsLayout.data
visible: plasmoid.containmentType !== PlasmaCore.Types.CustomEmbeddedContainment
contentItem: RowLayout {
Heading {
elide: Text.ElideRight
wrapMode: Text.NoWrap
Layout.fillWidth: true
visible: plasmoid.containmentType !== PlasmaCore.Types.CustomEmbeddedContainment
level: 1
text: plasmoid.title
}
RowLayout {
id: extraControlsLayout
visible: children.length > 0
Layout.fillHeight: true
}
PlasmaComponents.ToolButton {
id: actionsButton
visible: visibleActions > 0 && plasmoid.containmentType !== PlasmaCore.Types.CustomEmbeddedContainment
checked: configMenu.status !== PC2.DialogStatus.Closed
property int visibleActions: 0
property QtObject singleAction
Component.onCompleted: updateVisibleActions()
function updateVisibleActions() {
let newSingleAction = null;
let newVisibleActions = 0;
for (let i in plasmoid.contextualActions) {
let action = plasmoid.contextualActions[i];
if (action.visible && action !== plasmoid.action("configure")) {
newVisibleActions++;
newSingleAction = action;
action.changed.connect(() => {updateVisibleActions()});
}
}
if (newVisibleActions > 1) {
newSingleAction = null;
}
visibleActions = newVisibleActions;
singleAction = newSingleAction;
}
Connections {
target: plasmoid
function onContextualActionsChanged() {updateVisibleActions();}
}
icon.name: "application-menu"
checkable: visibleActions > 1
contentItem.opacity: visibleActions > 1
// NOTE: it needs an IconItem because QtQuickControls2 buttons cannot load QIcons as their icon
PlasmaCore.IconItem {
parent: actionsButton
anchors.centerIn: parent
active: actionsButton.hovered
implicitWidth: PlasmaCore.Units.iconSizes.smallMedium
implicitHeight: implicitWidth
source: actionsButton.singleAction !== null ? actionsButton.singleAction.icon : ""
visible: actionsButton.singleAction
}
onToggled: {
if (checked) {
configMenu.openRelative();
} else {
configMenu.close();
}
}
onClicked: {
if (singleAction) {
singleAction.trigger();
}
}
PlasmaComponents.ToolTip {
text: actionsButton.singleAction ? actionsButton.singleAction.text : i18n("More actions")
}
PC2.Menu {
id: configMenu
visualParent: actionsButton
placement: PlasmaCore.Types.BottomPosedLeftAlignedPopup
}
Instantiator {
model: plasmoid.contextualActions
delegate: PC2.MenuItem {
id: menuItem
action: modelData
}
onObjectAdded: {
if (object !== plasmoid.action("configure")) {
configMenu.addMenuItem(object);
}
}
}
}
PlasmaComponents.ToolButton {
icon.name: "configure"
visible: plasmoid && plasmoid.action("configure") && plasmoid.containmentType !== PlasmaCore.Types.CustomEmbeddedContainment
PlasmaComponents.ToolTip {
text: parent.visible ? plasmoid.action("configure").text : ""
}
onClicked: plasmoid.action("configure").trigger();
}
}
}

View File

@ -13,6 +13,7 @@ ScrollArea 2.0 ScrollArea.qml
Title 2.0 Title.qml Title 2.0 Title.qml
DescriptiveLabel 2.0 DescriptiveLabel.qml DescriptiveLabel 2.0 DescriptiveLabel.qml
PlasmoidHeading 2.0 PlasmoidHeading.qml PlasmoidHeading 2.0 PlasmoidHeading.qml
BasicPlasmoidHeading 2.0 BasicPlasmoidHeading.qml
ActivateAnimation 2.0 animations/ActivateAnimation.qml ActivateAnimation 2.0 animations/ActivateAnimation.qml
AppearAnimation 2.0 animations/AppearAnimation.qml AppearAnimation 2.0 animations/AppearAnimation.qml

View File

@ -95,6 +95,7 @@ public:
NoContainmentType = -1, /**< @internal */ NoContainmentType = -1, /**< @internal */
DesktopContainment = 0, /**< A desktop containment */ DesktopContainment = 0, /**< A desktop containment */
PanelContainment, /**< A desktop panel */ PanelContainment, /**< A desktop panel */
CustomContainment = 127, /**< A containment that is neither a desktop nor a panel CustomContainment = 127, /**< A containment that is neither a desktop nor a panel
but something application specific */ but something application specific */
CustomPanelContainment = 128, /**< A customized desktop panel */ CustomPanelContainment = 128, /**< A customized desktop panel */

View File

@ -114,6 +114,9 @@ AppletInterface::AppletInterface(DeclarativeAppletScript *script, const QVariant
connect(applet()->containment(), &Plasma::Containment::screenChanged, connect(applet()->containment(), &Plasma::Containment::screenChanged,
this, &AppletInterface::screenGeometryChanged); this, &AppletInterface::screenGeometryChanged);
connect(applet()->containment(), &Plasma::Containment::containmentTypeChanged,
this, &AppletInterface::containmentTypeChanged);
connect(applet()->containment()->corona(), &Plasma::Corona::screenGeometryChanged, this, [this](int id) { connect(applet()->containment()->corona(), &Plasma::Corona::screenGeometryChanged, this, [this](int id) {
if (id == applet()->containment()->screen()) { if (id == applet()->containment()->screen()) {
emit screenGeometryChanged(); emit screenGeometryChanged();
@ -232,6 +235,15 @@ Plasma::Types::Location AppletInterface::location() const
return applet()->location(); return applet()->location();
} }
Plasma::Types::ContainmentType AppletInterface::containmentType() const
{
if (applet()->containment()) {
return applet()->containment()->containmentType();
} else {
return Plasma::Types::NoContainmentType;
}
}
QString AppletInterface::currentActivity() const QString AppletInterface::currentActivity() const
{ {
if (applet()->containment()) { if (applet()->containment()) {

View File

@ -112,6 +112,12 @@ class AppletInterface : public PlasmaQuick::AppletQuickItem
*/ */
Q_PROPERTY(Plasma::Types::FormFactor formFactor READ formFactor NOTIFY formFactorChanged) Q_PROPERTY(Plasma::Types::FormFactor formFactor READ formFactor NOTIFY formFactorChanged)
/**
* Type of the containment we're in
* @since 5.76
*/
Q_PROPERTY(Plasma::Types::ContainmentType containmentType READ containmentType NOTIFY containmentTypeChanged)
/** /**
* Location for the plasmoid * Location for the plasmoid
*/ */
@ -375,6 +381,8 @@ public:
Plasma::Types::Location location() const; Plasma::Types::Location location() const;
Plasma::Types::ContainmentType containmentType() const;
QString currentActivity() const; QString currentActivity() const;
QObject *configuration() const; QObject *configuration() const;
@ -458,6 +466,7 @@ Q_SIGNALS:
void toolTipItemChanged(); void toolTipItemChanged();
void formFactorChanged(); void formFactorChanged();
void locationChanged(); void locationChanged();
void containmentTypeChanged();
void contextChanged(); void contextChanged();
void immutabilityChanged(); void immutabilityChanged();
void statusChanged(); void statusChanged();