New channel navigation

This commit is contained in:
Arkadiusz Fal
2022-05-29 20:26:56 +02:00
parent c5af865ffe
commit 0ad350a6b5
8 changed files with 114 additions and 53 deletions

View File

@@ -2,15 +2,23 @@ import Siesta
import SwiftUI
struct ChannelVideosView: View {
let channel: Channel
#if os(iOS)
static let hiddenOffset = max(UIScreen.main.bounds.height, UIScreen.main.bounds.width) + 100
#endif
var channel: Channel?
@State private var presentingShareSheet = false
@State private var shareURL: URL?
@State private var subscriptionToggleButtonDisabled = false
#if os(iOS)
@State private var viewVerticalOffset = Self.hiddenOffset
#endif
@StateObject private var store = Store<Channel>()
@Environment(\.colorScheme) private var colorScheme
@Environment(\.navigationStyle) private var navigationStyle
#if os(iOS)
@Environment(\.horizontalSizeClass) private var horizontalSizeClass
@@ -19,17 +27,42 @@ struct ChannelVideosView: View {
@EnvironmentObject<AccountsModel> private var accounts
@EnvironmentObject<NavigationModel> private var navigation
@EnvironmentObject<RecentsModel> private var recents
@EnvironmentObject<SubscriptionsModel> private var subscriptions
@Namespace private var focusNamespace
var presentedChannel: Channel? {
recents.presentedChannel ?? channel
}
var videos: [ContentItem] {
ContentItem.array(of: store.item?.videos ?? [])
}
var body: some View {
BrowserPlayerControls {
content
if navigationStyle == .tab {
NavigationView {
BrowserPlayerControls {
content
}
}
#if os(iOS)
.onChange(of: navigation.presentingChannel) { newValue in
if newValue {
resource?.load()
viewVerticalOffset = 0
} else {
viewVerticalOffset = Self.hiddenOffset
}
}
.offset(y: viewVerticalOffset)
.animation(.easeIn(duration: 0.2), value: viewVerticalOffset)
#endif
} else {
BrowserPlayerControls {
content
}
}
}
@@ -43,8 +76,10 @@ struct ChannelVideosView: View {
Spacer()
FavoriteButton(item: FavoriteItem(section: .channel(channel.id, channel.name)))
.labelStyle(.iconOnly)
if let channel = presentedChannel {
FavoriteButton(item: FavoriteItem(section: .channel(channel.id, channel.name)))
.labelStyle(.iconOnly)
}
if let subscribers = store.item?.subscriptionsString {
Text("**\(subscribers)** subscribers")
@@ -66,11 +101,11 @@ struct ChannelVideosView: View {
#if !os(tvOS)
.toolbar {
ToolbarItem(placement: .navigation) {
ShareButton(
contentItem: contentItem,
presentingShareSheet: $presentingShareSheet,
shareURL: $shareURL
)
if navigationStyle == .tab {
Button("Done") {
navigation.presentingChannel = false
}
}
}
ToolbarItem {
@@ -79,14 +114,22 @@ struct ChannelVideosView: View {
Text("\(store.item?.subscriptionsString ?? "loading")")
.fontWeight(.bold)
Text(" subscribers")
.allowsTightening(true)
.foregroundColor(.secondary)
.opacity(store.item?.subscriptionsString != nil ? 1 : 0)
}
.allowsTightening(true)
.foregroundColor(.secondary)
.opacity(store.item?.subscriptionsString != nil ? 1 : 0)
ShareButton(
contentItem: contentItem,
presentingShareSheet: $presentingShareSheet,
shareURL: $shareURL
)
subscriptionToggleButton
FavoriteButton(item: FavoriteItem(section: .channel(channel.id, channel.name)))
if let channel = presentedChannel {
FavoriteButton(item: FavoriteItem(section: .channel(channel.id, channel.name)))
}
}
}
}
@@ -99,12 +142,11 @@ struct ChannelVideosView: View {
}
#endif
.onAppear {
if store.item.isNil {
resource.addObserver(store)
resource.load()
}
resource?.loadIfNeeded()
}
#if !os(tvOS)
.navigationTitle(navigationTitle)
#endif
return Group {
if #available(macOS 12.0, *) {
@@ -121,44 +163,50 @@ struct ChannelVideosView: View {
}
}
private var resource: Resource {
private var resource: Resource? {
guard let channel = presentedChannel else {
return nil
}
let resource = accounts.api.channel(channel.id)
resource.addObserver(store)
return resource
}
private var subscriptionToggleButton: some View {
Group {
if accounts.app.supportsSubscriptions && accounts.signedIn {
if subscriptions.isSubscribing(channel.id) {
Button("Unsubscribe") {
subscriptionToggleButtonDisabled = true
@ViewBuilder private var subscriptionToggleButton: some View {
if let channel = presentedChannel {
Group {
if accounts.app.supportsSubscriptions && accounts.signedIn {
if subscriptions.isSubscribing(channel.id) {
Button("Unsubscribe") {
subscriptionToggleButtonDisabled = true
subscriptions.unsubscribe(channel.id) {
subscriptionToggleButtonDisabled = false
subscriptions.unsubscribe(channel.id) {
subscriptionToggleButtonDisabled = false
}
}
}
} else {
Button("Subscribe") {
subscriptionToggleButtonDisabled = true
} else {
Button("Subscribe") {
subscriptionToggleButtonDisabled = true
subscriptions.subscribe(channel.id) {
subscriptionToggleButtonDisabled = false
navigation.sidebarSectionChanged.toggle()
subscriptions.subscribe(channel.id) {
subscriptionToggleButtonDisabled = false
navigation.sidebarSectionChanged.toggle()
}
}
}
}
}
.disabled(subscriptionToggleButtonDisabled)
}
.disabled(subscriptionToggleButtonDisabled)
}
private var contentItem: ContentItem {
ContentItem(channel: channel)
ContentItem(channel: presentedChannel)
}
private var navigationTitle: String {
store.item?.name ?? channel.name
presentedChannel?.name ?? store.item?.name ?? "No channel"
}
}