diff --git a/Xcodes/Frontend/XcodeList/MainToolbar.swift b/Xcodes/Frontend/XcodeList/MainToolbar.swift index f2f645f0..685a99f2 100644 --- a/Xcodes/Frontend/XcodeList/MainToolbar.swift +++ b/Xcodes/Frontend/XcodeList/MainToolbar.swift @@ -40,6 +40,8 @@ struct MainToolbarModifier: ViewModifier { .tag(XcodeListCategory.release) Label("BetaOnly", systemImage: "line.horizontal.3.decrease.circle.fill") .tag(XcodeListCategory.beta) + Label("ReleasePlusNewBetas", systemImage: "line.horizontal.3.decrease.circle.fill") + .tag(XcodeListCategory.releasePlusNewBetas) } } .help("FilterAvailableDescription") diff --git a/Xcodes/Frontend/XcodeList/XcodeListCategory.swift b/Xcodes/Frontend/XcodeList/XcodeListCategory.swift index f1bf0e4d..41fb1dd3 100644 --- a/Xcodes/Frontend/XcodeList/XcodeListCategory.swift +++ b/Xcodes/Frontend/XcodeList/XcodeListCategory.swift @@ -5,6 +5,7 @@ enum XcodeListCategory: String, CaseIterable, Identifiable, CustomStringConverti case all case release case beta + case releasePlusNewBetas var id: Self { self } @@ -13,6 +14,7 @@ enum XcodeListCategory: String, CaseIterable, Identifiable, CustomStringConverti case .all: return localizeString("All") case .release: return localizeString("Release") case .beta: return localizeString("Beta") + case .releasePlusNewBetas: return localizeString("ReleasePlusNewBetas") } } @@ -20,7 +22,7 @@ enum XcodeListCategory: String, CaseIterable, Identifiable, CustomStringConverti var versionFilter: XcodeListVersionFilter { switch self { - case .all: + case .all, .releasePlusNewBetas: return .all case .release: return .release diff --git a/Xcodes/Frontend/XcodeList/XcodeListView.swift b/Xcodes/Frontend/XcodeList/XcodeListView.swift index ce75938e..814154e6 100644 --- a/Xcodes/Frontend/XcodeList/XcodeListView.swift +++ b/Xcodes/Frontend/XcodeList/XcodeListView.swift @@ -21,7 +21,7 @@ struct XcodeListView: View { } private var visibleXcodes: [XcodeListEntry] { - appState.allXcodes + let entries = appState.allXcodes .enumerated() .map { XcodeListEntry(index: $0.offset, xcode: $0.element) } .applying(XcodeListFilters( @@ -31,6 +31,19 @@ struct XcodeListView: View { searchText: searchText, installedOnly: isInstalledOnly ), item: \.listItem) + + if category == .releasePlusNewBetas { + let releases = Set( + entries + .filter { $0.xcode.version.isNotPrerelease } + .map { $0.xcode.version.withoutIdentifiers } + ) + return entries.filter { + $0.xcode.version.isNotPrerelease || !releases.contains($0.xcode.version.withoutIdentifiers) + } + } else { + return entries + } } private func latestReleaseForSelectedPrerelease(_ xcode: Xcode) -> Xcode? { @@ -437,3 +450,9 @@ struct XcodeListView_Previews: PreviewProvider { .previewLayout(.sizeThatFits) } } + +private extension Version { + var withoutIdentifiers: Version { + Version(major, minor, patch) + } +} diff --git a/Xcodes/Resources/Localizable.xcstrings b/Xcodes/Resources/Localizable.xcstrings index 0716fee2..2692970d 100644 --- a/Xcodes/Resources/Localizable.xcstrings +++ b/Xcodes/Resources/Localizable.xcstrings @@ -22136,6 +22136,17 @@ } } }, + "ReleasePlusNewBetas" : { + "extractionState" : "manual", + "localizations" : { + "en" : { + "stringUnit" : { + "state" : "translated", + "value" : "Release & unreleased beta" + } + } + } + }, "Required" : { "localizations" : { "ar" : { @@ -26217,4 +26228,4 @@ } }, "version" : "1.0" -} +} \ No newline at end of file