Skip to content

Commit 05a01ae

Browse files
committed
chore: navbar changes
1 parent ebe67ce commit 05a01ae

5 files changed

Lines changed: 291 additions & 63 deletions

File tree

TelegramDownloader/Shared/MainLayout.razor

Lines changed: 100 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,38 +17,101 @@
1717

1818
<style>
1919
.modalshow {
20-
display: block
20+
display: block;
2121
}
2222
2323
.modalhide {
24-
display: none
24+
display: none;
25+
}
26+
27+
/* Sidebar toggle button */
28+
.sidebar-toggle {
29+
padding: 0.25rem 0.5rem;
30+
font-size: 1.25rem;
31+
color: #333;
32+
text-decoration: none;
33+
border: none;
34+
background: transparent;
35+
}
36+
37+
.sidebar-toggle:hover {
38+
color: #007bff;
39+
}
40+
41+
/* Sidebar collapsed state - desktop only */
42+
@@media (min-width: 2048px) {
43+
.sidebar {
44+
transition: width 0.3s ease, min-width 0.3s ease;
45+
}
46+
47+
.sidebar.collapsed {
48+
width: 0 !important;
49+
min-width: 0 !important;
50+
overflow: hidden !important;
51+
padding: 0 !important;
52+
}
53+
}
54+
55+
/* Mobile: hide toggle button since NavMenu has its own */
56+
@@media (max-width: 2048px) {
57+
.sidebar-toggle {
58+
display: none;
59+
}
60+
61+
/* Sidebar full height when nav menu is expanded */
62+
.sidebar {
63+
height: 100vh !important;
64+
min-height: 100vh !important;
65+
}
66+
67+
/* Sidebar collapses when nav menu is collapsed */
68+
.sidebar.nav-collapsed {
69+
height: auto !important;
70+
min-height: auto !important;
71+
max-height: fit-content !important;
72+
overflow: hidden !important;
73+
}
2574
}
2675
</style>
2776

2877
<link href="css/custombuttons.css" rel="stylesheet" />
2978

79+
3080
<Preload LoadingText="Loading..." />
3181

3282

33-
<div class="page">
34-
<div class="sidebar">
35-
<NavMenu @ref="menu" OnClickCallback="openOffCanvasMenu" OnClickOpenImportCallback="openImportModalMenu" />
83+
<div class="page @(sidebarCollapsed ? "sidebar-collapsed" : "")">
84+
<div class="sidebar @(sidebarCollapsed ? "collapsed" : "") @(navMenuCollapsed ? "nav-collapsed" : "")">
85+
<NavMenu @ref="menu" OnClickCallback="openOffCanvasMenu" OnClickOpenImportCallback="openImportModalMenu" OnCollapseChanged="OnNavMenuCollapseChanged" />
3686
</div>
3787

3888
<main>
39-
<div class="top-row px-4 d-flex">
89+
<div class="top-row px-4 d-flex justify-content-end">
90+
<button class="btn btn-link sidebar-toggle me-auto" @onclick="ToggleSidebar">
91+
<i class="bi @(sidebarCollapsed ? "bi-list" : "bi-x-lg")"></i>
92+
</button>
4093
@if(active) {
4194
@if (tis.isUploading())
4295
{
43-
<button class="btn btn-primary download-button" @onclick='() => Navigateto("/downloads")'>
44-
<Icon Class="arrow" Name="IconName.ArrowUp"></Icon>
45-
<span>@tis.uploadSpeed</span>
96+
<button class="btn water-fill-button upload @(GetUploadProgress() > 50 ? "filled-high" : "")"
97+
@onclick='() => Navigateto("/downloads")'>
98+
<span class="water-fill" style="height: @(GetUploadProgress())%;"></span>
99+
<span class="water-wave" style="height: @(GetUploadProgress())%;"></span>
100+
<span class="btn-content">
101+
<Icon Class="arrow" Name="IconName.ArrowUp"></Icon>
102+
<span>@tis.uploadSpeed</span>
103+
</span>
46104
</button>
47105
}
48106
@if(tis.isDownloading()) {
49-
<button class="btn btn-primary download-button" @onclick='() => Navigateto("/downloads")'>
50-
<Icon Class="arrow" Name="IconName.ArrowDown"></Icon>
51-
<span>@tis.downloadSpeed</span>
107+
<button class="btn water-fill-button download @(GetDownloadProgress() > 50 ? "filled-high" : "")"
108+
@onclick='() => Navigateto("/downloads")'>
109+
<span class="water-fill" style="height: @(GetDownloadProgress())%;"></span>
110+
<span class="water-wave" style="height: @(GetDownloadProgress())%;"></span>
111+
<span class="btn-content">
112+
<Icon Class="arrow" Name="IconName.ArrowDown"></Icon>
113+
<span>@tis.downloadSpeed</span>
114+
</span>
52115
</button>
53116
}
54117
<Button Color="ButtonColor.None" Size="ButtonSize.Small" @onclick='() => Navigateto("/downloads")'>
@@ -103,6 +166,8 @@
103166
private GithubVersionModel LastVersion { get; set; }
104167
private NavMenu menu { get; set; }
105168
private bool active { get; set; } = true;
169+
private bool sidebarCollapsed { get; set; } = false;
170+
private bool navMenuCollapsed { get; set; } = true;
106171

107172
protected override async Task OnAfterRenderAsync(bool firstRender)
108173
{
@@ -186,11 +251,34 @@
186251
await InvokeAsync(StateHasChanged);
187252
}
188253

254+
private int GetDownloadProgress()
255+
{
256+
var activeDownload = tis.downloadModels.FirstOrDefault(x => x.state == StateTask.Working);
257+
return activeDownload?.progress ?? 0;
258+
}
259+
260+
private int GetUploadProgress()
261+
{
262+
var activeUpload = tis.uploadModels.FirstOrDefault(x => x.state == StateTask.Working);
263+
return activeUpload?.progress ?? 0;
264+
}
265+
189266
private void eventChangedWorkingTasks(object sender, System.EventArgs e)
190267
{
191268
checkWorkingTasks();
192269
}
193270

271+
private void ToggleSidebar()
272+
{
273+
sidebarCollapsed = !sidebarCollapsed;
274+
}
275+
276+
private void OnNavMenuCollapseChanged(bool isCollapsed)
277+
{
278+
navMenuCollapsed = isCollapsed;
279+
StateHasChanged();
280+
}
281+
194282
public void Dispose()
195283
{
196284
tis.TaskEventChanged -= eventChangedWorkingTasks;
Lines changed: 38 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,62 +1,69 @@
11
.page {
22
position: relative;
33
display: flex;
4-
flex-direction: column;
4+
flex-direction: row;
5+
min-height: 100vh;
56
}
67

78
main {
89
flex: 1;
10+
min-width: 0;
911
}
1012

1113
.sidebar {
1214
background-image: linear-gradient(180deg, rgb(5, 39, 103) 0%, #3a0647 70%);
15+
width: 20%;
16+
min-width: 280px;
17+
height: 100vh;
18+
position: sticky;
19+
top: 0;
20+
overflow-y: auto;
21+
overflow-x: hidden;
1322
}
1423

1524
.top-row {
1625
background-color: #f7f7f7;
1726
border-bottom: 1px solid #d6d5d5;
18-
justify-content: flex-end;
1927
height: 3.5rem;
2028
display: flex;
2129
align-items: center;
2230
}
2331

24-
.top-row ::deep a, .top-row .btn-link {
25-
white-space: nowrap;
26-
margin-left: 1.5rem;
27-
}
28-
29-
.top-row a:first-child {
30-
overflow: hidden;
31-
text-overflow: ellipsis;
32-
}
32+
.top-row ::deep a, .top-row ::deep .btn-link {
33+
white-space: nowrap;
34+
}
3335

34-
@media (max-width: 640.98px) {
35-
.top-row:not(.auth) {
36-
display: none;
36+
@media (max-width: 2048px) {
37+
.page {
38+
flex-direction: column;
3739
}
3840

39-
.top-row.auth {
40-
justify-content: space-between;
41+
.sidebar {
42+
width: 100%;
43+
min-width: 100%;
44+
height: auto;
45+
min-height: auto;
46+
max-height: none;
47+
position: relative;
48+
overflow-y: auto;
49+
flex-shrink: 0;
50+
transition: height 0.3s ease, min-height 0.3s ease;
4151
}
4252

43-
.top-row a, .top-row .btn-link {
44-
margin-left: 0;
53+
.sidebar.nav-collapsed {
54+
height: auto;
55+
min-height: auto;
56+
max-height: fit-content;
4557
}
46-
}
4758

48-
@media (min-width: 2048px) { /*641*/
49-
.page {
50-
flex-direction: row;
51-
}
52-
53-
.sidebar {
54-
width: 40vh;
55-
height: 100vh;
59+
.top-row {
5660
position: sticky;
5761
top: 0;
62+
z-index: 10;
5863
}
64+
}
5965

66+
@media (min-width: 2049px) {
6067
.top-row {
6168
position: sticky;
6269
top: 0;
@@ -67,4 +74,8 @@ main {
6774
padding-left: 2rem !important;
6875
padding-right: 1.5rem !important;
6976
}
77+
78+
main {
79+
display: block;
80+
}
7081
}

TelegramDownloader/Shared/NavMenu.razor

Lines changed: 44 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,43 @@
1010
@inject ITelegramService ts;
1111
@inject IJSRuntime JS;
1212

13+
<style>
14+
/* Collapse behavior for NavMenu */
15+
@@media (max-width: 2048px) {
16+
.nav-collapse-content {
17+
display: none;
18+
height: 0;
19+
overflow: hidden;
20+
transition: height 0.3s ease;
21+
}
22+
23+
.nav-collapse-content.show {
24+
display: block;
25+
height: auto;
26+
overflow: visible;
27+
}
28+
29+
.nav-collapse-content .menu {
30+
height: auto !important;
31+
max-height: calc(100vh - 3.5rem);
32+
overflow-y: auto;
33+
}
34+
35+
.navbar-toggler {
36+
display: block !important;
37+
}
38+
}
39+
40+
@@media (min-width: 2049px) {
41+
.nav-collapse-content {
42+
display: block !important;
43+
}
44+
45+
.navbar-toggler {
46+
display: none !important;
47+
}
48+
}
49+
</style>
1350

1451
<div class="navbar navbar-dark bg-dark top-row ps-3 navbar-expand-xl">
1552
<div class="container-fluid">
@@ -20,7 +57,7 @@
2057
</div>
2158
</div>
2259

23-
<div class="@NavMenuCssClass">
60+
<div class="nav-collapse-content @(collapseNavMenu ? "" : "show")">
2461
<nav class="flex-column menu">
2562
@if (showSearch)
2663
{
@@ -233,6 +270,7 @@
233270

234271
[Parameter] public EventCallback OnClickCallback { get; set; }
235272
[Parameter] public EventCallback OnClickOpenImportCallback { get; set; }
273+
[Parameter] public EventCallback<bool> OnCollapseChanged { get; set; }
236274

237275
Tabs tabs = default!;
238276

@@ -248,9 +286,13 @@
248286

249287
private string NavMenuCssClass => collapseNavMenu ? "collapse" : "collapse show";
250288

251-
private void ToggleNavMenu()
289+
private async Task ToggleNavMenu()
252290
{
253291
collapseNavMenu = !collapseNavMenu;
292+
if (OnCollapseChanged.HasDelegate)
293+
{
294+
await OnCollapseChanged.InvokeAsync(collapseNavMenu);
295+
}
254296
}
255297
private async Task ToggleSearch()
256298
{

TelegramDownloader/Shared/NavMenu.razor.css

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -67,19 +67,6 @@
6767
flex: 1;
6868
}
6969

70-
/* Always show navbar-toggler and allow collapse on all screen sizes */
71-
.navbar-toggler {
72-
display: block !important;
73-
}
74-
75-
/* Collapse behavior - works on all screen sizes */
76-
.collapse:not(.show) {
77-
display: none !important;
78-
}
79-
80-
.collapse.show {
81-
display: block !important;
82-
}
8370

8471
/* Row alignment for channel items */
8572
.row {

0 commit comments

Comments
 (0)