diff --git a/.github/workflows/build_linux.yml b/.github/workflows/build_linux.yml index 3109b0e9..c2baa003 100644 --- a/.github/workflows/build_linux.yml +++ b/.github/workflows/build_linux.yml @@ -1,24 +1,22 @@ name: Linux CI on: workflow_dispatch: - push: - branches: - - "main" - paths-ignore: - - "docs/**" - - "**/.gitignore" - - "**/.dockerignore" - - LICENSE - - "**/*.md" - pull_request: - branches: - - "main" - paths-ignore: - - "docs/**" - - "**/.gitignore" - - "**/.dockerignore" - - LICENSE - - "**/*.md" + # push: + # branches: + # - "dev" + # paths-ignore: + # - "docs/**" + # - ".gitignore" + # - LICENSE + # - "*.md" + # pull_request: + # branches: + # - "dev" + # paths-ignore: + # - "docs/**" + # - ".gitignore" + # - LICENSE + # - "*.md" jobs: build: diff --git a/.github/workflows/build_release.yml b/.github/workflows/build_release.yml index ddbf97b2..68d0d046 100644 --- a/.github/workflows/build_release.yml +++ b/.github/workflows/build_release.yml @@ -1,8 +1,14 @@ name: CI Passing on: - push: - tags: - - v* + workflow_dispatch: + # push: + # branches: + # - "dev" + # paths-ignore: + # - "docs/**" + # - "*.md" + # - LICENSE + # - .gitignore env: CARGO_TERM_COLOR: always @@ -23,7 +29,7 @@ jobs: os: ubuntu-latest target: arm64 # x86_64-windows-gnu - - arch: x86_64-windows-gnu + - arch: ucrt-x86_64-windows-gnu os: windows-latest target: amd64 @@ -189,7 +195,7 @@ jobs: - name: Get latest tag name id: tag - run: echo "TAG_NAME=$(git describe --tags --abbrev=0)" >> $GITHUB_OUTPUT + run: echo "TAG_NAME=v$(date '+%Y-%m-%d-%H%M%S')" >> $GITHUB_OUTPUT - name: Set prerelease variable if: startsWith(github.ref, 'refs/tags/v') && endsWith(github.ref, '-alpha') diff --git a/.github/workflows/build_windows.yml b/.github/workflows/build_windows.yml index fc4e5ce0..0443238f 100644 --- a/.github/workflows/build_windows.yml +++ b/.github/workflows/build_windows.yml @@ -3,22 +3,20 @@ on: workflow_dispatch: push: branches: - - "main" + - "dev" paths-ignore: - "docs/**" - - "**/.gitignore" - - "**/.dockerignore" + - ".gitignore" - LICENSE - - "**/*.md" - pull_request: - branches: - - "main" - paths-ignore: - - "docs/**" - - "**/.gitignore" - - "**/.dockerignore" - - LICENSE - - "**/*.md" + - "*.md" + # pull_request: + # branches: + # - "dev" + # paths-ignore: + # - "docs/**" + # - ".gitignore" + # - LICENSE + # - "*.md" env: CARGO_TERM_COLOR: always @@ -38,7 +36,6 @@ jobs: # env: x86_64 - arch: ucrt64-x86_64-windows-gnu os: windows-latest - target: x86_64-pc-windows-gnu msystem: ucrt64 env: ucrt-x86_64 @@ -72,7 +69,7 @@ jobs: mingw-w64-${{ matrix.env }}-gst-libav curl - - name: Build tsukimi-${{ matrix.target }} + - name: Build tsukimi-${{ matrix.arch }} if: ${{ !startsWith(github.ref, 'refs/tags/') }} shell: msys2 {0} run: | @@ -151,10 +148,10 @@ jobs: if: ${{ !startsWith(github.ref, 'refs/tags/') }} uses: actions/upload-artifact@v4 with: - name: tsukimi-${{matrix.target}} + name: tsukimi-${{matrix.arch}} path: | - artifact/*.exe artifact/*.7z + artifact/*.exe artifact/*.sha512sum compression-level: 0 retention-days: 3 diff --git a/.gitignore b/.gitignore index 3b42f00d..59a1e75a 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ /i18n /.idea /backup +/.cargo diff --git a/Cargo.toml b/Cargo.toml index 00da0d5b..d9bb1f6a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -96,3 +96,6 @@ assets = [ [profile.release] lto = true +codegen-units = 1 +opt-level = "s" +strip = true diff --git a/src/arg.rs b/src/arg.rs index e18b103c..aee43ca7 100644 --- a/src/arg.rs +++ b/src/arg.rs @@ -29,6 +29,27 @@ pub struct Args { gsk_renderer: Option, } +struct Envs { + log_level: LevelFilter, + log_file: Option, +} + +impl Envs { + fn load() -> Self { + Self { + log_level: match std::env::var("TSUKIMI_LOG_LEVEL").as_deref() { + Ok("ERROR") => LevelFilter::ERROR, + Ok("WARN") => LevelFilter::WARN, + Ok("INFO") => LevelFilter::INFO, + Ok("DEBUG") => LevelFilter::DEBUG, + Ok("TRACE") => LevelFilter::TRACE, + _ => LevelFilter::INFO, + }, + log_file: std::env::var("TSUKIMI_LOG_FILE").ok(), + } + } +} + impl Args { /// Build the tracing subscriber using parameters from the command line /// arguments @@ -45,11 +66,20 @@ impl Args { Some("info") => builder.with_max_level(LevelFilter::INFO), Some("debug") => builder.with_max_level(LevelFilter::DEBUG), Some("trace") => builder.with_max_level(LevelFilter::TRACE), - _ => builder.with_max_level(LevelFilter::INFO), + _ => builder.with_max_level(Envs::load().log_level), }; match &self.log_file { - None => builder.with_writer(io::stderr).init(), + None => { + if let Some(f) = Envs::load().log_file { + builder + .with_ansi(false) + .with_writer(Mutex::new(File::create(f).unwrap())) + .init() + } else { + builder.with_writer(io::stderr).init() + } + } Some(f) => { builder.with_ansi(false).with_writer(Mutex::new(File::create(f).unwrap())).init() } diff --git a/src/ui/mod.rs b/src/ui/mod.rs index 63b9b204..4447043a 100644 --- a/src/ui/mod.rs +++ b/src/ui/mod.rs @@ -57,7 +57,7 @@ pub fn load_css() { border-radius: 999px; margin: 3px; }} - + box>overlay>image {{ background-color: {}; border-radius: 999px; @@ -70,6 +70,9 @@ pub fn load_css() { accent_color )); + #[cfg(target_os = "windows")] + styles.push_str("window {box-shadow: 0px 0px 5px 0px rgba(5, 5, 5, 0.4);}"); + provider.load_from_string(&styles); gtk::style_context_add_provider_for_display( diff --git a/src/ui/mpv/tsukimi_mpv.rs b/src/ui/mpv/tsukimi_mpv.rs index 1e1a7a7b..046f2108 100644 --- a/src/ui/mpv/tsukimi_mpv.rs +++ b/src/ui/mpv/tsukimi_mpv.rs @@ -568,6 +568,7 @@ const KEYSTRING_MAP: &[(&str, &str)] = &[ ("", "Shift_R"), ("", "grave"), ("SPACE", " "), + ("TAB", "\t"), ]; fn keyval_to_keystr(keyval: u32) -> Option { diff --git a/src/ui/style.css b/src/ui/style.css index dabffa82..d834839c 100644 --- a/src/ui/style.css +++ b/src/ui/style.css @@ -66,7 +66,7 @@ child { border-radius: 10px; } -.tu-listview>row { +.tu-listview > row { margin: 10px; border-radius: 10px; } @@ -81,7 +81,8 @@ button.star:hover { -gtk-icon-transform: rotate(-72deg); } - to {} + to { + } } @keyframes rotate_unstar { @@ -89,7 +90,8 @@ button.star:hover { -gtk-icon-transform: rotate(72deg); } - to {} + to { + } } button.star.interacted.starred image { @@ -113,13 +115,13 @@ button.star.interacted:not(.starred) image { border-radius: 10px; } -.horizontal-listview>row { +.horizontal-listview > row { margin-left: 9px; margin-right: 9px; border-radius: 10px; } -.vertical-listview>row { +.vertical-listview > row { margin: 9px; border-radius: 10px; } @@ -136,41 +138,41 @@ gridview { background-color: rgba(0, 0, 0, 0); } -gridview>child box { +gridview > child box { margin: 0px; } -overlay>label { +overlay > label { background-color: #aeb5fa; border-radius: 999px; margin: 3px; } -box>overlay>image { +box > overlay > image { background-color: #aeb5fa; border-radius: 999px; margin: 3px; } -revealer>box>box>widget { +revealer > box > box > widget { background-color: rgba(1, 1, 1, 0.1); border-radius: 10px; } -revealer>box>box>widget>box { +revealer > box > box > widget > box { margin: 10px; } -tabbar>revealer>box { +tabbar > revealer > box { background-color: rgba(0, 0, 0, 0); } -scrolledwindow>viewport>box>box>box { +scrolledwindow > viewport > box > box > box { margin-left: 15px; margin-top: 15px; } -.osd>box { +.osd > box { margin: 0px; padding: 0px; border-radius: 10px; @@ -199,4 +201,67 @@ row.expand.interacted.expanded image { row image { transition: 200ms cubic-bezier(0.25, 0.46, 0.45, 0.94); -} \ No newline at end of file +} + +/* Scale UI Font to 125% */ +* { + -gtk-dpi: 125; +} + +/* GTK4 Window Controls Styles */ +windowcontrols > button { + color: transparent; + min-width: 20px; + min-height: 20px; + padding: 0; + margin: 0 2px; + border: none; + border-radius: 50%; + transition: all 0.2s ease; +} + +windowcontrols > button > image { + padding: 0; + -gtk-icon-size: 14px; + color: rgba(0, 0, 0, 0.7); + opacity: 0; + transition: opacity 0.2s ease, color 0.2s ease; +} + +/* Button colors */ +button.titlebutton.close, +windowcontrols > button.close { + background-color: #ff5f56; +} + +button.titlebutton.maximize, +windowcontrols > button.maximize { + background-color: #ffbd2e; +} + +button.titlebutton.minimize, +windowcontrols > button.minimize { + background-color: #27c93f; +} + +/* Hover states */ +windowcontrols > button:hover { + background-color: rgba(0, 0, 0, 0.1); +} + +windowcontrols > button:hover > image { + opacity: 1; + color: rgba(0, 0, 0, 0.9); +} + +windowcontrols > button.close:hover { + background-color: #ff5f56; +} + +windowcontrols > button.maximize:hover { + background-color: #ffbd2e; +} + +windowcontrols > button.minimize:hover { + background-color: #27c93f; +} diff --git a/src/ui/widgets/item.rs b/src/ui/widgets/item.rs index ae6dbeb3..a0ab3406 100644 --- a/src/ui/widgets/item.rs +++ b/src/ui/widgets/item.rs @@ -489,12 +489,14 @@ impl ItemPage { imp.episode_list_vec.replace(continue_play_list); } _ => { - let season_list = imp.season_list_vec.borrow(); - let Some(season) = season_list.iter().find(|s| s.name == season_name) else { - return; - }; + let season_id = { + let season_list = imp.season_list_vec.borrow(); + let Some(season) = season_list.iter().find(|s| s.name == season_name) else { + return; + }; - let season_id = season.id.clone(); + season.id.clone() + }; let episodes = match spawn_tokio(async move { EMBY_CLIENT.get_episodes(&series_id, &season_id).await