forked from Shinonome/dots-hyprland
sidebar calendar done
This commit is contained in:
@@ -114,8 +114,8 @@ Singleton {
|
|||||||
property color colOnLayer2: m3colors.m3onSurface;
|
property color colOnLayer2: m3colors.m3onSurface;
|
||||||
property color colLayer3: mix(m3colors.m3surfaceContainerHigh, m3colors.m3onSurface, 0.96);
|
property color colLayer3: mix(m3colors.m3surfaceContainerHigh, m3colors.m3onSurface, 0.96);
|
||||||
property color colOnLayer3: m3colors.m3onSurface;
|
property color colOnLayer3: m3colors.m3onSurface;
|
||||||
property color colLayer1Hover: mix(colLayer1, colOnLayer1, 0.85);
|
property color colLayer1Hover: mix(colLayer1, colOnLayer1, 0.88);
|
||||||
property color colLayer1Active: mix(colLayer1, colOnLayer1, 0.70);
|
property color colLayer1Active: mix(colLayer1, colOnLayer1, 0.77);
|
||||||
property color colLayer2Hover: mix(colLayer2, colOnLayer2, 0.90);
|
property color colLayer2Hover: mix(colLayer2, colOnLayer2, 0.90);
|
||||||
property color colLayer2Active: mix(colLayer2, colOnLayer2, 0.80);
|
property color colLayer2Active: mix(colLayer2, colOnLayer2, 0.80);
|
||||||
property color colLayer3Hover: mix(colLayer3, colOnLayer3, 0.90);
|
property color colLayer3Hover: mix(colLayer3, colOnLayer3, 0.90);
|
||||||
|
|||||||
@@ -6,6 +6,8 @@ pragma Singleton
|
|||||||
Singleton {
|
Singleton {
|
||||||
property string time: Qt.formatDateTime(clock.date, "hh:mm")
|
property string time: Qt.formatDateTime(clock.date, "hh:mm")
|
||||||
property string date: Qt.formatDateTime(clock.date, "dddd, dd/MM")
|
property string date: Qt.formatDateTime(clock.date, "dddd, dd/MM")
|
||||||
|
property string month: Qt.formatDateTime(clock.date, "MMMM")
|
||||||
|
property string year: Qt.formatDateTime(clock.date, "yyyy")
|
||||||
property string uptime: "0h, 0m"
|
property string uptime: "0h, 0m"
|
||||||
|
|
||||||
SystemClock {
|
SystemClock {
|
||||||
|
|||||||
@@ -11,8 +11,8 @@ Button {
|
|||||||
required default property Item content
|
required default property Item content
|
||||||
property bool extraActiveCondition: false
|
property bool extraActiveCondition: false
|
||||||
|
|
||||||
implicitWidth: 26
|
implicitHeight: Math.max(content.implicitHeight, 26, content.implicitHeight)
|
||||||
implicitHeight: 26
|
implicitWidth: Math.max(content.implicitHeight, 26, content.implicitWidth)
|
||||||
contentItem: content
|
contentItem: content
|
||||||
|
|
||||||
background: Rectangle {
|
background: Rectangle {
|
||||||
|
|||||||
@@ -7,5 +7,5 @@ Text {
|
|||||||
verticalAlignment: Text.AlignVCenter
|
verticalAlignment: Text.AlignVCenter
|
||||||
font.family: Appearance.font.family.main
|
font.family: Appearance.font.family.main
|
||||||
font.pixelSize: Appearance.font.pixelSize.small
|
font.pixelSize: Appearance.font.pixelSize.small
|
||||||
color: Appearance.colors.colOnBackground
|
color: Appearance.m3colors.m3onBackground
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,11 @@
|
|||||||
import "root:/modules/common"
|
import "root:/modules/common"
|
||||||
import "root:/modules/common/widgets"
|
import "root:/modules/common/widgets"
|
||||||
|
import "./calendar"
|
||||||
|
import "./calendar/calendar_layout.js" as CalendarLayout
|
||||||
import QtQuick
|
import QtQuick
|
||||||
import QtQuick.Controls
|
import QtQuick.Controls
|
||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
import Quickshell
|
import Quickshell
|
||||||
import "calendar_layout.js" as CalendarLayout
|
|
||||||
|
|
||||||
Rectangle {
|
Rectangle {
|
||||||
Layout.alignment: Qt.AlignHCenter
|
Layout.alignment: Qt.AlignHCenter
|
||||||
@@ -12,19 +13,21 @@ Rectangle {
|
|||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
radius: Appearance.rounding.normal
|
radius: Appearance.rounding.normal
|
||||||
color: Appearance.colors.colLayer1
|
color: Appearance.colors.colLayer1
|
||||||
implicitHeight: 300
|
implicitHeight: 343 // TODO NO HARD CODE
|
||||||
|
|
||||||
RowLayout {
|
RowLayout {
|
||||||
id: calendarRow
|
id: calendarRow
|
||||||
anchors.fill: parent
|
anchors.fill: parent
|
||||||
width: parent.width - 10 * 2
|
// width: parent.width - 10 * 2
|
||||||
height: parent.height - 10 * 2
|
height: parent.height - 10 * 2
|
||||||
spacing: 10
|
spacing: 10
|
||||||
property int selectedTab: 0
|
property int selectedTab: 0
|
||||||
|
|
||||||
|
// Navigation rail
|
||||||
ColumnLayout {
|
ColumnLayout {
|
||||||
id: tabBar
|
id: tabBar
|
||||||
Layout.fillHeight: true
|
Layout.fillHeight: true
|
||||||
|
Layout.fillWidth: false
|
||||||
Layout.leftMargin: 15
|
Layout.leftMargin: 15
|
||||||
spacing: 15
|
spacing: 15
|
||||||
Repeater {
|
Repeater {
|
||||||
@@ -42,44 +45,119 @@ Rectangle {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Content area
|
||||||
StackLayout {
|
StackLayout {
|
||||||
id: tabStack
|
id: tabStack
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
Layout.fillHeight: true
|
// Layout.fillHeight: true
|
||||||
|
Layout.alignment: Qt.AlignVCenter
|
||||||
property int realIndex: 0
|
property int realIndex: 0
|
||||||
property int animationDuration: Appearance.animation.elementDecel.duration * 1.5
|
property int animationDuration: Appearance.animation.elementDecel.duration * 1.5
|
||||||
|
|
||||||
// Calendar
|
// Calendar
|
||||||
Component {
|
Component {
|
||||||
id: calendarWidget
|
id: calendarWidget
|
||||||
ColumnLayout {
|
|
||||||
|
Item {
|
||||||
anchors.centerIn: parent
|
anchors.centerIn: parent
|
||||||
spacing: 5
|
width: calendarColumn.width
|
||||||
RowLayout {
|
height: calendarColumn.height
|
||||||
Layout.fillWidth: true
|
property int monthShift: 0
|
||||||
Layout.fillHeight: false
|
property var viewingDate: CalendarLayout.getDateInXMonthsTime(monthShift)
|
||||||
spacing: 5
|
|
||||||
Repeater {
|
MouseArea {
|
||||||
model: CalendarLayout.weekDays
|
anchors.fill: parent
|
||||||
delegate: CalendarDayButton {
|
onWheel: {
|
||||||
day: modelData.day
|
if (wheel.angleDelta.y > 0) {
|
||||||
isToday: modelData.today
|
monthShift--;
|
||||||
bold: true
|
} else if (wheel.angleDelta.y < 0) {
|
||||||
interactable: false
|
monthShift++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Repeater {
|
ColumnLayout {
|
||||||
model: CalendarLayout.getCalendarLayout(null, true)
|
id: calendarColumn
|
||||||
delegate: RowLayout {
|
anchors.centerIn: parent
|
||||||
|
spacing: 5
|
||||||
|
|
||||||
|
// Calendar header
|
||||||
|
RowLayout {
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
Layout.fillHeight: false
|
Layout.fillHeight: false
|
||||||
spacing: 5
|
spacing: 5
|
||||||
|
CalendarHeaderButton {
|
||||||
|
onClicked: {
|
||||||
|
monthShift = 0;
|
||||||
|
}
|
||||||
|
content: StyledText {
|
||||||
|
text: `${monthShift != 0 ? "• " : ""}${viewingDate.toLocaleDateString(Qt.locale(), "MMMM yyyy")}`
|
||||||
|
horizontalAlignment: Text.AlignHCenter
|
||||||
|
font.pixelSize: Appearance.font.pixelSize.larger
|
||||||
|
color: Appearance.colors.colOnLayer1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Item {
|
||||||
|
Layout.fillWidth: true
|
||||||
|
Layout.fillHeight: false
|
||||||
|
}
|
||||||
|
CalendarHeaderButton {
|
||||||
|
forceCircle: true
|
||||||
|
onClicked: {
|
||||||
|
monthShift--;
|
||||||
|
}
|
||||||
|
content: MaterialSymbol {
|
||||||
|
text: "chevron_left"
|
||||||
|
font.pixelSize: Appearance.font.pixelSize.large
|
||||||
|
horizontalAlignment: Text.AlignHCenter
|
||||||
|
color: Appearance.colors.colOnLayer1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
CalendarHeaderButton {
|
||||||
|
forceCircle: true
|
||||||
|
onClicked: {
|
||||||
|
monthShift++;
|
||||||
|
}
|
||||||
|
content: MaterialSymbol {
|
||||||
|
text: "chevron_right"
|
||||||
|
font.pixelSize: Appearance.font.pixelSize.large
|
||||||
|
horizontalAlignment: Text.AlignHCenter
|
||||||
|
color: Appearance.colors.colOnLayer1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Week days row
|
||||||
|
RowLayout {
|
||||||
|
id: weekDaysRow
|
||||||
|
Layout.alignment: Qt.AlignHCenter
|
||||||
|
Layout.fillHeight: false
|
||||||
|
spacing: 5
|
||||||
Repeater {
|
Repeater {
|
||||||
model: modelData
|
model: CalendarLayout.weekDays
|
||||||
delegate: CalendarDayButton {
|
delegate: CalendarDayButton {
|
||||||
day: modelData.day
|
day: modelData.day
|
||||||
isToday: modelData.today
|
isToday: modelData.today
|
||||||
|
bold: true
|
||||||
|
interactable: false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Real week rows
|
||||||
|
Repeater {
|
||||||
|
id: calendarRows
|
||||||
|
model: CalendarLayout.getCalendarLayout(viewingDate, monthShift === 0)
|
||||||
|
delegate: RowLayout {
|
||||||
|
Layout.alignment: Qt.AlignHCenter
|
||||||
|
Layout.fillHeight: false
|
||||||
|
spacing: 5
|
||||||
|
Repeater {
|
||||||
|
model: modelData
|
||||||
|
delegate: CalendarDayButton {
|
||||||
|
day: modelData.day
|
||||||
|
isToday: modelData.today
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -128,7 +206,7 @@ Rectangle {
|
|||||||
{ type: "calendar" },
|
{ type: "calendar" },
|
||||||
{ type: "todo" }
|
{ type: "todo" }
|
||||||
]
|
]
|
||||||
Item {
|
Item { // TODO: make behavior on y also act for the item that's switched to
|
||||||
id: tabItem
|
id: tabItem
|
||||||
property int tabIndex: index
|
property int tabIndex: index
|
||||||
property string tabType: modelData.type
|
property string tabType: modelData.type
|
||||||
|
|||||||
@@ -0,0 +1,31 @@
|
|||||||
|
import "root:/modules/common"
|
||||||
|
import "root:/modules/common/widgets"
|
||||||
|
import QtQuick
|
||||||
|
import QtQuick.Controls
|
||||||
|
import QtQuick.Layouts
|
||||||
|
|
||||||
|
Button {
|
||||||
|
id: button
|
||||||
|
required default property Item content
|
||||||
|
property bool forceCircle: false
|
||||||
|
|
||||||
|
implicitHeight: 30
|
||||||
|
implicitWidth: forceCircle ? implicitHeight : (contentItem.implicitWidth + 10 * 2)
|
||||||
|
|
||||||
|
background: Rectangle {
|
||||||
|
anchors.fill: parent
|
||||||
|
radius: Appearance.rounding.full
|
||||||
|
color: (button.down) ? Appearance.colors.colLayer2Active : (button.hovered ? Appearance.colors.colLayer2Hover : Appearance.colors.colLayer2)
|
||||||
|
|
||||||
|
Behavior on color {
|
||||||
|
ColorAnimation {
|
||||||
|
duration: Appearance.animation.elementDecel.duration
|
||||||
|
easing.type: Appearance.animation.elementDecel.type
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
contentItem: content
|
||||||
|
|
||||||
|
}
|
||||||
+20
@@ -40,6 +40,26 @@ function getPrevMonthDays(month, year) {
|
|||||||
return 31;
|
return 31;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getDateInXMonthsTime(x) {
|
||||||
|
var currentDate = new Date(); // Get the current date
|
||||||
|
if (x == 0) return currentDate; // If x is 0, return the current date
|
||||||
|
|
||||||
|
var targetMonth = currentDate.getMonth() + x; // Calculate the target month
|
||||||
|
var targetYear = currentDate.getFullYear(); // Get the current year
|
||||||
|
|
||||||
|
// Adjust the year and month if necessary
|
||||||
|
targetYear += Math.floor(targetMonth / 12);
|
||||||
|
targetMonth = (targetMonth % 12 + 12) % 12;
|
||||||
|
|
||||||
|
// Create a new date object with the target year and month
|
||||||
|
var targetDate = new Date(targetYear, targetMonth, 1);
|
||||||
|
|
||||||
|
// Set the day to the last day of the month to get the desired date
|
||||||
|
// targetDate.setDate(0);
|
||||||
|
|
||||||
|
return targetDate;
|
||||||
|
}
|
||||||
|
|
||||||
function getCalendarLayout(dateObject, highlight) {
|
function getCalendarLayout(dateObject, highlight) {
|
||||||
if (!dateObject) dateObject = new Date();
|
if (!dateObject) dateObject = new Date();
|
||||||
const weekday = (dateObject.getDay() + 6) % 7; // MONDAY IS THE FIRST DAY OF THE WEEK
|
const weekday = (dateObject.getDay() + 6) % 7; // MONDAY IS THE FIRST DAY OF THE WEEK
|
||||||
Reference in New Issue
Block a user