Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix behavior when tapping more detail button on EventMapView #828

Merged
merged 2 commits into from
Aug 28, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 5 additions & 20 deletions app-ios/Sources/EventMapFeature/EventItem.swift
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,8 @@ import Theme
import shared

struct EventItem: View {
@State private var isDescriptionExpanded: Bool = false
@State private var canBeExpanded: Bool = false
let event: EventMapEvent
let onTappedMoreDetail: (URL) -> Void

var body: some View {
VStack(alignment: .leading, spacing: 0) {
Expand All @@ -28,29 +27,16 @@ struct EventItem: View {
Text(event.description_.currentLangTitle)
.foregroundStyle(AssetColors.Surface.onSurface.swiftUIColor)
.textStyle(.bodyLarge)
.lineLimit(isDescriptionExpanded ? nil : 3)
.background {
ViewThatFits(in: .vertical) {
Text(event.description_.currentLangTitle)
.textStyle(.bodyLarge)
.hidden()
// Just for receiving onAppear event if the description exceeds its line limit
Color.clear
.onAppear {
canBeExpanded = true
}
}
}

if let message = event.message {
Text(message.currentLangTitle)
.foregroundStyle(AssetColors.Tertiary.tertiary.swiftUIColor)
.textStyle(.bodyMedium)
}

if canBeExpanded {
if let urlString = event.moreDetailsUrl, let url = URL(string: urlString) {
Button {
isDescriptionExpanded = true
canBeExpanded = false
onTappedMoreDetail(url)
} label: {
Text(String(localized: "Detail", bundle: .module))
.textStyle(.labelLarge)
Expand All @@ -71,10 +57,9 @@ struct EventItem: View {
}
.frame(maxWidth: .infinity)
.padding(.horizontal, 16)
.animation(.default, value: isDescriptionExpanded)
}
}

#Preview {
EventItem(event: EventMapEvent.companion.fakes().first!)
EventItem(event: EventMapEvent.companion.fakes().first!) { _ in }
}
15 changes: 14 additions & 1 deletion app-ios/Sources/EventMapFeature/EventMapReducer.swift
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import ComposableArchitecture
import KMPClient
import Model
import Foundation
@preconcurrency import shared

@Reducer
Expand All @@ -12,18 +14,21 @@ public struct EventMapReducer: Sendable {
public struct State: Equatable {
public var selectedFloorMap: FloorMap = .first
public var events: [EventMapEvent] = []
public var url: IdentifiableURL?

public init() { }
}

public enum Action {
public enum Action: BindableAction {
case binding(BindingAction<State>)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this parameter unused?

.binding below appears to not need or use any parameters.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Understood. Comment withdrawn.

case view(View)
case `internal`(Internal)

@CasePathable
public enum View {
case onAppear
case selectFloorMap(FloorMap)
case moreDetailButtonTapped(URL)
}

public enum Internal {
Expand All @@ -32,6 +37,7 @@ public struct EventMapReducer: Sendable {
}

public var body: some ReducerOf<Self> {
BindingReducer()
Reduce { state, action in
switch action {
case .view(.onAppear):
Expand All @@ -49,13 +55,20 @@ public struct EventMapReducer: Sendable {
state.selectedFloorMap = floor
return .none

case let .view(.moreDetailButtonTapped(url)):
state.url = IdentifiableURL(url)
return .none

case let .internal(.response(.success(events))):
state.events = events
return .none

case let .internal(.response(.failure(error))):
print(error.localizedDescription)
return .none

case .binding:
return .none
}
}
}
Expand Down
8 changes: 7 additions & 1 deletion app-ios/Sources/EventMapFeature/EventMapView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,9 @@ public struct EventMapView: View {

VStack(spacing: 24) {
ForEach(store.events, id: \.self) { event in
EventItem(event: event)
EventItem(event: event) { url in
store.send(.view(.moreDetailButtonTapped(url)))
}
}
}
// bottom floating tabbar padding
Expand All @@ -44,6 +46,10 @@ public struct EventMapView: View {
.navigationBarTitleDisplayMode(.large)
.navigationTitle(String(localized: "NavigationTitle", bundle: .module))
.onAppear { store.send(.view(.onAppear)) }
.sheet(item: $store.url, content: { url in
SafariView(url: url.id)
.ignoresSafeArea()
})
}
}

Expand Down
11 changes: 11 additions & 0 deletions app-ios/Tests/EventMapFeatureTests/EventMapTests.swift
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import XCTest
import ComposableArchitecture
import Model
@testable import EventMapFeature

final class EventMap_iosTests: XCTestCase {
Expand All @@ -12,4 +13,14 @@ final class EventMap_iosTests: XCTestCase {
$0.selectedFloorMap = .firstBasement
}
}

@MainActor func testMoreDetailButtonTapped() async throws {
let store = TestStore(initialState: EventMapReducer.State()) {
EventMapReducer()
}
let url = URL(string: "https://portal.droidkaigi.jp")!
await store.send(.view(.moreDetailButtonTapped(url))) {
$0.url = IdentifiableURL(url)
}
}
}
Loading