Add Tab-related controls

pull/19/head
reionwong 5 years ago
parent 46adf20371
commit 8f95c4f698

@ -0,0 +1,83 @@
/*
* Copyright (C) 2021 CutefishOS Team.
*
* Author: Reion Wong <reion@cutefishos.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* 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 General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import QtQuick 2.15
import QtQml 2.15
import QtQuick.Window 2.15
import QtQuick.Controls 2.15
import QtQuick.Layouts 1.15
import FishUI 1.0 as FishUI
TabBar {
id: control
implicitWidth: _content.width
default property alias content : _content.data
property bool newTabVisibile: true
signal newTabClicked()
background: Rectangle {
color: "transparent"
}
contentItem: Item {
RowLayout {
anchors.fill: parent
spacing: FishUI.Units.smallSpacing
ScrollView {
id: _scrollView
Layout.fillWidth: true
Layout.fillHeight: true
ScrollBar.horizontal.policy: ScrollBar.AlwaysOff
ScrollBar.vertical.policy: ScrollBar.AlwaysOff
clip: true
Flickable {
id: _flickable
Row {
id: _content
width: _scrollView.width
height: _scrollView.height
}
}
}
Loader {
active: control.newTabVisibile
visible: active
asynchronous: true
Layout.fillHeight: true
Layout.preferredWidth: visible ? height : 0
sourceComponent: FishUI.RoundImageButton {
source: "qrc:/images/" + (FishUI.Theme.darkMode ? "dark/" : "light/") + "add.svg"
onClicked: control.newTabClicked()
}
}
}
}
}

@ -0,0 +1,81 @@
import QtQuick 2.15
import QtQml 2.15
import QtQuick.Window 2.15
import QtQuick.Controls 2.15
import QtQuick.Layouts 1.15
import FishUI 1.0 as FishUI
Item {
id: control
property bool checked: false
property bool hovered: _mouseArea.containsMouse
property alias font: _label.font
property string text: ""
signal clicked()
signal closeClicked()
MouseArea {
id: _mouseArea
anchors.fill: parent
hoverEnabled: true
onClicked: control.clicked()
}
Rectangle {
id: hoveredRect
anchors.fill: parent
anchors.leftMargin: FishUI.Units.smallSpacing / 2
anchors.rightMargin: FishUI.Units.smallSpacing / 2
anchors.topMargin: FishUI.Units.smallSpacing / 2
color: _mouseArea.containsMouse ? FishUI.Theme.textColor : FishUI.Theme.secondBackgroundColor
opacity: _mouseArea.containsMouse ? _mouseArea.pressed ? 0.1 : 0.05 : 0.9
border.width: 0
radius: FishUI.Theme.smallRadius
}
Rectangle {
id: checkedRect
anchors.leftMargin: FishUI.Units.smallSpacing / 2
anchors.rightMargin: FishUI.Units.smallSpacing / 2
anchors.topMargin: FishUI.Units.smallSpacing / 2
anchors.fill: parent
color: FishUI.Theme.highlightColor
opacity: _mouseArea.pressed ? 0.9 : 1
border.width: 0
visible: checked
radius: FishUI.Theme.smallRadius
}
RowLayout {
anchors.fill: parent
anchors.leftMargin: FishUI.Units.smallSpacing / 2
anchors.rightMargin: FishUI.Units.smallSpacing / 2
anchors.topMargin: FishUI.Units.smallSpacing / 2
spacing: 0
Label {
id: _label
text: control.text
leftPadding: FishUI.Units.smallSpacing / 2
Layout.fillWidth: true
Layout.fillHeight: true
horizontalAlignment: Qt.AlignHCenter
verticalAlignment: Qt.AlignVCenter
color: control.checked ? FishUI.Theme.highlightedTextColor
: FishUI.Theme.textColor
elide: Text.ElideMiddle
wrapMode: Text.NoWrap
}
FishUI.TabCloseButton {
enabled: control.checked
Layout.preferredHeight: 24
Layout.preferredWidth: 24
size: 24
source: !enabled ? "" : "qrc:/images/" + (FishUI.Theme.darkMode || control.checked ? "dark/" : "light/") + "close.svg"
onClicked: control.closeClicked()
}
}
}

@ -0,0 +1,68 @@
/*
* Copyright (C) 2021 CutefishOS Team.
*
* Author: Reion Wong <reion@cutefishos.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* 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 General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import QtQuick 2.12
import QtQuick.Window 2.3
import QtQuick.Controls 2.4
import FishUI 1.0 as FishUI
Item {
id: control
property var size: 32
property var iconMargins: 0
height: size
width: size
property alias background: _background
property color backgroundColor: "transparent"
property color hoveredColor: "#FF5C6D"
property color pressedColor: "#CC4A57"
property alias source: _image.source
property alias image: _image
signal clicked()
Rectangle {
id: _background
anchors.fill: parent
anchors.margins: size * 0.1
radius: control.height / 2
opacity: 0.9
color: mouseArea.pressed ? pressedColor : mouseArea.containsMouse ? control.hoveredColor : control.backgroundColor
}
MouseArea {
id: mouseArea
anchors.fill: parent
hoverEnabled: true
onClicked: control.clicked()
}
Image {
id: _image
objectName: "image"
anchors.fill: parent
anchors.margins: control.iconMargins
fillMode: Image.PreserveAspectFit
sourceSize: Qt.size(width, height)
cache: true
asynchronous: false
}
}

@ -0,0 +1,84 @@
/*
* Copyright (C) 2021 CutefishOS Team.
*
* Author: Reion Wong <reion@cutefishos.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* 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 General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import QtQuick 2.15
import QtQml 2.15
import QtQuick.Window 2.15
import QtQuick.Controls 2.15
import QtQuick.Layouts 1.15
import FishUI 1.0 as FishUI
Container {
id: control
spacing: 0
contentItem: ColumnLayout {
spacing: 0
ListView {
id: _view
Layout.fillWidth: true
Layout.fillHeight: true
interactive: false
orientation: ListView.Horizontal
snapMode: ListView.SnapOneItem
currentIndex: control.currentIndex
model: control.contentModel
boundsBehavior: Flickable.StopAtBounds
boundsMovement :Flickable.StopAtBounds
spacing: 0
preferredHighlightBegin: 0
preferredHighlightEnd: width
highlightRangeMode: ListView.StrictlyEnforceRange
highlightMoveDuration: 0
highlightFollowsCurrentItem: true
highlightResizeDuration: 0
highlightMoveVelocity: -1
highlightResizeVelocity: -1
maximumFlickVelocity: 4 * width
cacheBuffer: _view.count * width
keyNavigationEnabled : false
keyNavigationWraps : false
}
}
function closeTab(index) {
control.removeItem(control.takeItem(index))
control.currentItemChanged()
control.currentItem.forceActiveFocus()
}
function addTab(component, properties) {
const object = component.createObject(control.contentModel, properties)
control.addItem(object)
control.currentIndex = Math.max(control.count - 1, 0)
object.forceActiveFocus()
return object
}
}

@ -22,4 +22,9 @@ PopupTips 1.0 PopupTips.qml
RoundedRect 1.0 RoundedRect.qml
Window 1.0 Window.qml
RoundImageButton 1.0 RoundImageButton.qml
TabBar 1.0 TabBar.qml
TabButton 1.0 TabButton.qml
TabCloseButton 1.0 TabCloseButton.qml
TabView 1.0 TabView.qml
Toast 1.0 Toast.qml

@ -69,6 +69,10 @@ void FishUI::registerTypes(const char *uri)
qmlRegisterType(componentUrl(QStringLiteral("Icon.qml")), uri, 1, 0, "Icon");
qmlRegisterType(componentUrl(QStringLiteral("PopupTips.qml")), uri, 1, 0, "PopupTips");
qmlRegisterType(componentUrl(QStringLiteral("RoundedRect.qml")), uri, 1, 0, "RoundedRect");
qmlRegisterType(componentUrl(QStringLiteral("TabBar.qml")), uri, 1, 0, "TabBar");
qmlRegisterType(componentUrl(QStringLiteral("TabButton.qml")), uri, 1, 0, "TabButton");
qmlRegisterType(componentUrl(QStringLiteral("TabCloseButton.qml")), uri, 1, 0, "TabCloseButton");
qmlRegisterType(componentUrl(QStringLiteral("TabView.qml")), uri, 1, 0, "TabView");
qmlRegisterType(componentUrl(QStringLiteral("Toast.qml")), uri, 1, 0, "Toast");
qmlRegisterType(componentUrl(QStringLiteral("Window.qml")), uri, 1, 0, "Window");
qmlRegisterType(componentUrl(QStringLiteral("RoundImageButton.qml")), uri, 1, 0, "RoundImageButton");

@ -10,12 +10,18 @@
<file alias="Units.qml">controls/Units.qml</file>
<file alias="Window.qml">controls/Window.qml</file>
<file alias="RoundImageButton.qml">controls/RoundImageButton.qml</file>
<file alias="TabBar.qml">controls/TabBar.qml</file>
<file alias="TabButton.qml">controls/TabButton.qml</file>
<file alias="TabCloseButton.qml">controls/TabCloseButton.qml</file>
<file alias="TabView.qml">controls/TabView.qml</file>
<file alias="DesktopMenu.qml">controls/DesktopMenu.qml</file>
<file>images/refresh.svg</file>
<file>images/dark/close.svg</file>
<file>images/dark/maximize.svg</file>
<file>images/dark/minimize.svg</file>
<file>images/dark/restore.svg</file>
<file>images/light/add.svg</file>
<file>images/dark/add.svg</file>
<file>images/light/close.svg</file>
<file>images/light/maximize.svg</file>
<file>images/light/minimize.svg</file>

@ -0,0 +1,66 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="16"
height="16"
enable-background="new"
version="1.1"
id="svg6"
sodipodi:docname="add.svg"
inkscape:version="1.0.1 (3bc2e813f5, 2020-09-07)">
<metadata
id="metadata12">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs10" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1652"
inkscape:window-height="997"
id="namedview8"
showgrid="false"
inkscape:zoom="45.9375"
inkscape:cx="8"
inkscape:cy="8"
inkscape:window-x="290"
inkscape:window-y="564"
inkscape:window-maximized="0"
inkscape:current-layer="svg6"
inkscape:document-rotation="0" />
<rect
style="opacity:0.95;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.597918;stroke-miterlimit:4;stroke-dasharray:none"
id="rect832"
width="8.2469997"
height="0.5"
x="3.8765001"
y="7.75" />
<rect
style="opacity:0.95;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.597918;stroke-miterlimit:4;stroke-dasharray:none"
id="rect832-3"
width="8.2469997"
height="0.5"
x="3.8765001"
y="-8.25"
transform="rotate(90)" />
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

@ -0,0 +1,66 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="16"
height="16"
enable-background="new"
version="1.1"
id="svg6"
sodipodi:docname="add.svg"
inkscape:version="1.0.1 (3bc2e813f5, 2020-09-07)">
<metadata
id="metadata12">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs10" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="2160"
inkscape:window-height="1304"
id="namedview8"
showgrid="false"
inkscape:zoom="45.9375"
inkscape:cx="8"
inkscape:cy="8"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="svg6"
inkscape:document-rotation="0" />
<rect
style="opacity:0.95;fill:#363636;fill-opacity:1;stroke:none;stroke-width:0.597918;stroke-miterlimit:4;stroke-dasharray:none"
id="rect832"
width="8.2469997"
height="0.5"
x="3.8765001"
y="7.75" />
<rect
style="opacity:0.95;fill:#363636;fill-opacity:1;stroke:none;stroke-width:0.597918;stroke-miterlimit:4;stroke-dasharray:none"
id="rect832-3"
width="8.2469997"
height="0.5"
x="3.8765001"
y="-8.25"
transform="rotate(90)" />
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

Loading…
Cancel
Save