From 74740b1048e8c39d80d779fd319141834b409a1b Mon Sep 17 00:00:00 2001 From: "allen.yan" Date: Fri, 8 Aug 2025 10:31:59 +0800 Subject: [PATCH 1/2] =?UTF-8?q?vod=E9=A0=81=E9=9D=A2=E4=B8=8A=E4=B8=8B?= =?UTF-8?q?=E9=A0=81=E5=BE=AA=E7=92=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../PrimaryForm.MultiPagePanel.cs | 186 ++++++++++-------- 1 file changed, 107 insertions(+), 79 deletions(-) diff --git a/PrimaryFormParts/PrimaryForm.MultiPagePanel.cs b/PrimaryFormParts/PrimaryForm.MultiPagePanel.cs index 0fdeb0c..cc10287 100644 --- a/PrimaryFormParts/PrimaryForm.MultiPagePanel.cs +++ b/PrimaryFormParts/PrimaryForm.MultiPagePanel.cs @@ -6,29 +6,30 @@ using System.Text; namespace DualScreenDemo { - public partial class PrimaryForm : Form{ + public partial class PrimaryForm : Form + { public class MultiPagePanel : Panel { private const int ItemHeight = 70; private const int RowGap = 2; - private int itemsPerPage + private int itemsPerPage { get { Screen screen = Screen.PrimaryScreen; int screenWidth = screen.Bounds.Width; int screenHeight = screen.Bounds.Height; - if(screenWidth==1440 && screenHeight==900) + if (screenWidth == 1440 && screenHeight == 900) { - return 14; + return 14; } - else if(screenWidth==1024 && screenHeight==768) + else if (screenWidth == 1024 && screenHeight == 768) { - return 12; + return 12; } - else if(screenWidth == 1920 && screenHeight == 1080) + else if (screenWidth == 1920 && screenHeight == 1080) { - return 16; + return 16; } return 16; // 預設值 } @@ -43,12 +44,12 @@ namespace DualScreenDemo public bool IsSimplified { get { return _isSimplified; } - set - { + set + { if (_isSimplified != value) { _isSimplified = value; - if(currentArtistList != null && currentArtistList.Count > 0) + if (currentArtistList != null && currentArtistList.Count > 0) RefreshDisplayBase_Singer(); else RefreshDisplay(); @@ -57,7 +58,8 @@ namespace DualScreenDemo } private bool _isShowingSinger = true; private List currentSongList = new List(); - public List get_currentSongList(){ + public List get_currentSongList() + { return currentSongList; } private List currentArtistList = new List(); @@ -68,30 +70,30 @@ namespace DualScreenDemo public int currentPageIndex { get { return _currentPageIndex; } - set - { + set + { if (_currentPageIndex != value) { _currentPageIndex = value; // 觸發事件,通知頁面索引已改變 PageIndexChanged?.Invoke(); - } + } } } public int totalPages { get { return _totalPages; } - set - { + set + { if (_totalPages != value) { _totalPages = value; // 觸發事件,通知頁面索引已改變 PageIndexChanged?.Invoke(); - } + } } } - + public MultiPagePanel() { this.SetStyle( @@ -102,7 +104,7 @@ namespace DualScreenDemo true); this.BackColor = Color.FromArgb(64, 0, 0, 0); this.BorderStyle = BorderStyle.None; - + // 添加滑動事件 this.MouseDown += MultiPagePanel_MouseDown; this.MouseMove += MultiPagePanel_MouseMove; @@ -125,12 +127,12 @@ namespace DualScreenDemo int deltaX = e.X - mouseDownLocation.X; if (Math.Abs(deltaX) > 20) // 滑動距離超過50像素才觸發 { - if (deltaX > 0 && currentPageIndex > 0) + if (deltaX > 0 ) { // 向右滑動,上一頁 LoadPreviousPage(); } - else if (deltaX < 0 && currentPageIndex < totalPages - 1) + else if (deltaX < 0) { // 向左滑動,下一頁 LoadNextPage(); @@ -149,7 +151,7 @@ namespace DualScreenDemo { currentPageIndex++; // 如果歌單為0(沒有歌單),則刷新歌手列表 - if(_isShowingSinger) + if (_isShowingSinger) { RefreshDisplayBase_Singer(); } @@ -158,21 +160,41 @@ namespace DualScreenDemo RefreshDisplay(); } } + else + { + if (totalPages > 1) + { + currentPageIndex = -1; + LoadNextPage(); + } + + } } public void LoadPreviousPage() { if (currentPageIndex - 1 >= 0) { currentPageIndex--; - if(_isShowingSinger) + if (_isShowingSinger) { RefreshDisplayBase_Singer(); } + else { RefreshDisplay(); } } + else + { + if (totalPages > 1) + { + currentPageIndex = totalPages; + LoadPreviousPage(); + } + + } + } public void LoadSongs(List songs, bool clearHistory = false) @@ -182,7 +204,7 @@ namespace DualScreenDemo currentArtistList.Clear(); currentPageIndex = 0; totalPages = (int)Math.Ceiling(songs.Count / (double)itemsPerPage); - + // 直接調用基礎刷新邏輯 RefreshDisplayBase(); } @@ -204,7 +226,7 @@ namespace DualScreenDemo currentArtistList.Clear(); currentPageIndex = 0; totalPages = (int)Math.Ceiling(songs.Count / (double)itemsPerPage); - + // 直接調用基礎刷新邏輯 RefreshDisplayBase(); } @@ -225,10 +247,10 @@ namespace DualScreenDemo } this.SuspendLayout(); // 暫停 UI 更新,提高效能 this.Controls.Clear(); // 清空 UI (這裡會再清除一次) - + int startIndex = currentPageIndex * itemsPerPage; int endIndex = Math.Min(startIndex + itemsPerPage, currentSongList.Count); - + for (int i = startIndex; i < endIndex; i++) { CreateSongLabel(currentSongList[i], i - startIndex, startIndex); // 這行負責新增 UI @@ -237,7 +259,7 @@ namespace DualScreenDemo } private void RefreshDisplayBase_Singer() { - this.Controls.Clear(); + this.Controls.Clear(); if (this.InvokeRequired) // 確保 UI 操作在主執行緒執行 { this.Invoke(new Action(() => RefreshDisplayBase_Singer())); @@ -245,30 +267,30 @@ namespace DualScreenDemo } this.SuspendLayout(); // 暫停 UI 更新,提高效能 this.Controls.Clear(); // 清空 UI (這裡會再清除一次) - + int startIndex = currentPageIndex * itemsPerPage; int endIndex = Math.Min(startIndex + itemsPerPage, currentArtistList.Count); - + for (int i = startIndex; i < endIndex; i++) { CreateSingerLabel(currentArtistList[i], i - startIndex, startIndex); // 這行負責新增 UI } this.ResumeLayout(); // 恢復 UI 更新 - this.Invalidate(); + this.Invalidate(); } - + private void CreateSingerLabel(Artist artist, int index, int pageOffset) { - + // 創建歌手標籤 Label artistLabel = new Label(); - string artistText = IsSimplified ? - (!string.IsNullOrEmpty(artist.NameSimplified) ? artist.NameSimplified : artist.Name) : + string artistText = IsSimplified ? + (!string.IsNullOrEmpty(artist.NameSimplified) ? artist.NameSimplified : artist.Name) : artist.Name; artistLabel.Text = artistText; artistLabel.Tag = artist; artistLabel.AutoSize = true; - + // 計算文字寬度 artistLabel.Font = new Font("微軟正黑體", 22, FontStyle.Bold); Screen screen = Screen.PrimaryScreen; @@ -282,22 +304,22 @@ namespace DualScreenDemo _ => 8 // 預設值 }; // 計算位置 - 依照NumberOfItem來計算 - bool isLeftColumn = index < NumberOfItem; + bool isLeftColumn = index < NumberOfItem; int row = isLeftColumn ? index : index - NumberOfItem; // 如果是右边,需要减去8来计算正确的行号 float startX = isLeftColumn ? LeftColumnX : RightColumnX; int y = row * (ItemHeight + RowGap); // 計算歌手標籤的位置和大小 int singerX = (int)(this.Width * startX); - int singerWidth = (int)(this.Width * (SongWidth+ArtistWidth)); + int singerWidth = (int)(this.Width * (SongWidth + ArtistWidth)); // 字體顏色 artistLabel.ForeColor = Color.White; // 標籤座標設定 artistLabel.Location = new Point(singerX, y); artistLabel.Size = new Size(singerWidth + 20, ItemHeight); - + Panel separatorPanel = new Panel { - Location = new Point(singerX , y + ItemHeight), + Location = new Point(singerX, y + ItemHeight), //Size = new Size(singerWidth + 20, 2), Size = new Size(730, 2), BackColor = Color.FromArgb(80, 255, 255, 255), @@ -306,28 +328,30 @@ namespace DualScreenDemo // 字體調整和字體背景顏色 artistLabel.TextAlign = ContentAlignment.TopLeft; artistLabel.BackColor = Color.Transparent; - + // 設置滑鼠事件 - EventHandler mouseEnter = (sender, e) => { - // 變更歌手名稱為黃色 - artistLabel.ForeColor = Color.Yellow; - // 增強分隔線的亮度,使其更明顯 - separatorPanel.BackColor = Color.FromArgb(120, 255, 255, 255); - + EventHandler mouseEnter = (sender, e) => + { + // 變更歌手名稱為黃色 + artistLabel.ForeColor = Color.Yellow; + // 增強分隔線的亮度,使其更明顯 + separatorPanel.BackColor = Color.FromArgb(120, 255, 255, 255); + }; - EventHandler mouseLeave = (sender, e) => { - // 還原歌手名稱為白色 - artistLabel.ForeColor = Color.White; - // 還原分隔線的亮度 - separatorPanel.BackColor = Color.FromArgb(80, 255, 255, 255); + EventHandler mouseLeave = (sender, e) => + { + // 還原歌手名稱為白色 + artistLabel.ForeColor = Color.White; + // 還原分隔線的亮度 + separatorPanel.BackColor = Color.FromArgb(80, 255, 255, 255); }; - artistLabel.Click += (sender, e) => + artistLabel.Click += (sender, e) => { string searchText = artistLabel.Text; // 取得輸入內容 // 歌星 轉 歌曲 string query = IsSimplified ? ( - !string.IsNullOrEmpty(artist.NameSimplified)? + !string.IsNullOrEmpty(artist.NameSimplified) ? $"SELECT * FROM song_library_cache WHERE artistA_simplified = '{searchText}' OR artistB_simplified = '{searchText}'" : $"SELECT * FROM song_library_cache WHERE artistA = '{searchText}' OR artistB = '{searchText}'" ) @@ -357,7 +381,7 @@ namespace DualScreenDemo this.Controls.Add(artistLabel); // 將歌手標籤置於最上層 artistLabel.BringToFront(); - + } private void CreateSongLabel(SongData song, int index, int pageOffset) @@ -386,7 +410,7 @@ namespace DualScreenDemo string fullText = songText + statusText; int textLength = fullText.Length; - + // 計算文字寬度 songLabel.Font = new Font("微軟正黑體", 22, FontStyle.Bold); songLabel.Text = fullText; @@ -402,21 +426,21 @@ namespace DualScreenDemo int screenWidth = screen.Bounds.Width; int screenHeight = screen.Bounds.Height; int NumberOfItem = 0; - if(screenWidth==1440 && screenHeight==900) + if (screenWidth == 1440 && screenHeight == 900) { - NumberOfItem = 7; + NumberOfItem = 7; } - else if(screenWidth==1024 && screenHeight==768) + else if (screenWidth == 1024 && screenHeight == 768) { - NumberOfItem = 6; + NumberOfItem = 6; } - else if(screenWidth == 1920 && screenHeight == 1080) + else if (screenWidth == 1920 && screenHeight == 1080) { - NumberOfItem = 8; + NumberOfItem = 8; } // 計算位置 - 依照NumberOfItem來計算 - bool isLeftColumn = index < NumberOfItem; - int row = isLeftColumn ? index : index - NumberOfItem; + bool isLeftColumn = index < NumberOfItem; + int row = isLeftColumn ? index : index - NumberOfItem; float startX = isLeftColumn ? LeftColumnX : RightColumnX; int y = row * (ItemHeight + RowGap); // 設置位置和大小 @@ -439,7 +463,7 @@ namespace DualScreenDemo }; this.Controls.Add(icon); icon.BringToFront(); - + // 有圖標時歌名右移 songLabel.Location = new Point(songX + 42, y); //songLabel.Size = new Size(songWidth - 47, ItemHeight - 20); @@ -455,18 +479,20 @@ namespace DualScreenDemo // 歌手標籤位置調整 artistLabel.Location = new Point(artistX, y + 33); artistLabel.Size = new Size(artistWidth - 10, ItemHeight - 35); - if (artistText.Length > 3) - { - artistLabel.Location = new Point(artistX - 95, y + 33); - artistLabel.Size = new Size(artistWidth + 90, ItemHeight - 35); - } + if (song.getB() != null) { artistText += " + " + song.getArtist_B(IsSimplified); - artistLabel.Location = new Point(artistX - 95, y + 33); - artistLabel.Size = new Size(artistWidth + 90, ItemHeight - 35); - + //artistLabel.Location = new Point(artistX - 95, y + 33); + //artistLabel.Size = new Size(artistWidth + 90, ItemHeight - 35); } + + if (artistText.Length > 3) + { + artistLabel.Location = new Point(artistX - 581, y + 33); + artistLabel.Size = new Size(artistWidth + 573, ItemHeight - 35); + } + artistLabel.Text = artistText; // 創建分隔線面板 Panel separatorPanel = new Panel @@ -487,24 +513,26 @@ namespace DualScreenDemo artistLabel.Font = new Font("微軟正黑體", fold, FontStyle.Bold); //artistLabel.ForeColor = Color.FromArgb(30,144,255); - artistLabel.ForeColor = Color.FromArgb(36,209,216); + artistLabel.ForeColor = Color.FromArgb(36, 209, 216); songLabel.TextAlign = ContentAlignment.MiddleLeft; artistLabel.TextAlign = ContentAlignment.MiddleRight; // 確保背景透明 songLabel.BackColor = Color.Transparent; artistLabel.BackColor = Color.Transparent; // 定義滑鼠進入 (MouseEnter) 事件的處理程序 - EventHandler mouseEnter = (sender, e) => { + EventHandler mouseEnter = (sender, e) => + { songLabel.ForeColor = Color.Yellow; artistLabel.ForeColor = Color.Yellow; separatorPanel.BackColor = Color.FromArgb(120, 255, 255, 255); - + }; // 定義滑鼠離開 (MouseLeave) 事件的處理程序 - EventHandler mouseLeave = (sender, e) => { + EventHandler mouseLeave = (sender, e) => + { songLabel.ForeColor = color; //artistLabel.ForeColor = Color.FromArgb(30, 144, 255); - artistLabel.ForeColor = Color.FromArgb(36,209,216); + artistLabel.ForeColor = Color.FromArgb(36, 209, 216); separatorPanel.BackColor = Color.FromArgb(80, 255, 255, 255); }; // 添加事件处理 From 65c7ad7c147797b83389cdd1f06f5c2ecf63e486 Mon Sep 17 00:00:00 2001 From: "allen.yan" Date: Fri, 8 Aug 2025 10:42:48 +0800 Subject: [PATCH 2/2] =?UTF-8?q?=E4=BF=AE=E6=AD=A3=E4=BD=8E=E8=A7=A3?= =?UTF-8?q?=E6=9E=90=E5=BA=A6=E6=B3=A8=E9=9F=B3=E8=BC=B8=E5=85=A5=E5=AD=97?= =?UTF-8?q?=E9=AB=94=E5=A4=A7=E5=B0=8F=E5=95=8F=E9=A1=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../PrimaryForm.SingerSearch.BopomofoSearch.cs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/PrimaryFormParts/SingerSearch/PrimaryForm.SingerSearch.BopomofoSearch.cs b/PrimaryFormParts/SingerSearch/PrimaryForm.SingerSearch.BopomofoSearch.cs index 2203018..8738a58 100644 --- a/PrimaryFormParts/SingerSearch/PrimaryForm.SingerSearch.BopomofoSearch.cs +++ b/PrimaryFormParts/SingerSearch/PrimaryForm.SingerSearch.BopomofoSearch.cs @@ -659,6 +659,13 @@ namespace DualScreenDemo // 從配置中加載字體屬性 inputBoxFontName = data["InputBoxZhuYinSingers"]["FontName"]; // 字體名稱 inputBoxFontSize = float.Parse(data["InputBoxZhuYinSingers"]["FontSize"]); // 字體大小 + Screen screen = Screen.PrimaryScreen; + int screenWidth = screen.Bounds.Width; + int screenHeight = screen.Bounds.Height; + if (screenWidth < 1920 && screenHeight < 1080) + { + inputBoxFontSize = 22; + } inputBoxFontStyle = (FontStyle)Enum.Parse(typeof(FontStyle), data["InputBoxZhuYinSingers"]["FontStyle"]); // 字體樣式 inputBoxForeColor = Color.FromName(data["InputBoxZhuYinSingers"]["ForeColor"]); // 字體顏色