Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
stephencelis committed Feb 13, 2023
1 parent ff5bc78 commit c0ded85
Show file tree
Hide file tree
Showing 18 changed files with 840 additions and 0 deletions.
5 changes: 5 additions & 0 deletions 0221-pflive-dependencies-stacks/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
## [Point-Free](https://www.pointfree.co)

> #### This directory contains code from Point-Free Episode: [Point-Free Live: Dependencies & Stacks](https://www.pointfree.co/episodes/ep221-point-free-live-dependencies-stacks)
>
> Our first ever livestream! We talk about a few new features that made it into our [Dependencies](https://github.com/pointfreeco/swift-dependencies) library when we extracted it from the Composable Architecture, live code our way through a `NavigationStack` refactor of our [Standups](https://github.com/pointfreeco/standups) app, and answer your questions along the way!

Large diffs are not rendered by default.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IDEDidComputeMac32BitWarning</key>
<true/>
</dict>
</plist>
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"colors" : [
{
"idiom" : "universal"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
{
"images" : [
{
"idiom" : "universal",
"platform" : "ios",
"size" : "1024x1024"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"info" : {
"author" : "xcode",
"version" : 1
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
import ComposableArchitecture
import SwiftUI

struct AppFeature: Reducer {
struct State: Equatable {
var firstTab = FirstTabFeature.State()
var inventory = InventoryFeature.State()
var selectedTab: Tab = .one
var thirdTab = ThirdTabFeature.State()
}
enum Action: Equatable {
case firstTab(FirstTabFeature.Action)
case inventory(InventoryFeature.Action)
case selectedTabChanged(Tab)
case thirdTab(ThirdTabFeature.Action)
}
var body: some ReducerOf<Self> {
Reduce<State, Action> { state, action in
switch action {
case let .firstTab(.delegate(action)):
switch action {
case .switchToInventoryTab:
state.selectedTab = .inventory
return .none
}

case let .selectedTabChanged(tab):
state.selectedTab = tab
return .none

case .firstTab, .inventory, .thirdTab:
return .none
}
}
Scope(state: \.firstTab, action: /Action.firstTab) {
FirstTabFeature()
}
Scope(state: \.inventory, action: /Action.inventory) {
InventoryFeature()
}
Scope(state: \.thirdTab, action: /Action.thirdTab) {
ThirdTabFeature()
}
}
}

enum Tab {
case one, inventory, three
}

struct ContentView: View {
//@State var selectedTab: Tab = .one
let store: StoreOf<AppFeature>
// Store<AppFeature.State, AppFeature.Action>

var body: some View {
WithViewStore(self.store, observe: \.selectedTab) { viewStore in
TabView(selection: viewStore.binding(send: AppFeature.Action.selectedTabChanged)) {
FirstTabView(
store: self.store.scope(
state: \.firstTab,
action: AppFeature.Action.firstTab
)
)
.tabItem { Text("One") }
.tag(Tab.one)

InventoryView(
store: self.store.scope(
state: \.inventory,
action: AppFeature.Action.inventory
)
)
.tabItem { Text("Inventory") }
.tag(Tab.inventory)

ThirdTabView(
store: self.store.scope(
state: \.thirdTab,
action: AppFeature.Action.thirdTab
)
)
.tabItem { Text("Three") }
.tag(Tab.three)
}
}
}
}

struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView(
store: Store(
initialState: AppFeature.State(),
reducer: AppFeature()
)
)
}
}
38 changes: 38 additions & 0 deletions 0222-composable-navigation-pt1/Inventory/Inventory/FirstTab.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import ComposableArchitecture
import SwiftUI

struct FirstTabFeature: Reducer {
struct State: Equatable {}
enum Action: Equatable {
case goToInventoryButtonTapped
case delegate(Delegate)

enum Delegate: Equatable {
case switchToInventoryTab
}
}

func reduce(into state: inout State, action: Action) -> Effect<Action> {
switch action {
case .delegate:
return .none

case .goToInventoryButtonTapped:
return .send(.delegate(.switchToInventoryTab))
}
}
}

struct FirstTabView: View {
let store: StoreOf<FirstTabFeature>

var body: some View {
WithViewStore(self.store, observe: { $0 }) { viewStore in
Button {
viewStore.send(.goToInventoryButtonTapped)
} label: {
Text("Go to inventory")
}
}
}
}
18 changes: 18 additions & 0 deletions 0222-composable-navigation-pt1/Inventory/Inventory/Inventory.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import ComposableArchitecture
import SwiftUI

struct InventoryFeature: Reducer {
struct State: Equatable {}
enum Action: Equatable {}

func reduce(into state: inout State, action: Action) -> Effect<Action> {
}
}

struct InventoryView: View {
let store: StoreOf<InventoryFeature>

var body: some View {
Text("Inventory")
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import ComposableArchitecture
import SwiftUI

@main
struct InventoryApp: App {
var body: some Scene {
WindowGroup {
ContentView(
store: Store(
initialState: AppFeature.State(),
reducer: AppFeature()
)
)
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"info" : {
"author" : "xcode",
"version" : 1
}
}
18 changes: 18 additions & 0 deletions 0222-composable-navigation-pt1/Inventory/Inventory/ThirdTab.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import ComposableArchitecture
import SwiftUI

struct ThirdTabFeature: Reducer {
struct State: Equatable {}
enum Action: Equatable {}

func reduce(into state: inout State, action: Action) -> Effect<Action> {
}
}

struct ThirdTabView: View {
let store: StoreOf<ThirdTabFeature>

var body: some View {
Text("Three")
}
}
32 changes: 32 additions & 0 deletions 0222-composable-navigation-pt1/Inventory/Inventory/Vanilla.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import SwiftUI
import XCTestDynamicOverlay

class AppModel: ObservableObject {
@Published var firstTab: FirstTabModel {
didSet { self.bind() }
}
@Published var selectedTab: Tab

init(
firstTab: FirstTabModel,
selectedTab: Tab = .one
) {
self.firstTab = firstTab
self.selectedTab = selectedTab
self.bind()
}

private func bind() {
self.firstTab.switchToInventoryTab = { [weak self] in
self?.selectedTab = .inventory
}
}
}

class FirstTabModel: ObservableObject {
var switchToInventoryTab: () -> Void = unimplemented("FirstTabModel.switchToInventoryTab")

func goToInventoryTab() {
self.switchToInventoryTab()
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import ComposableArchitecture
import XCTest
@testable import Inventory

@MainActor
final class InventoryTests: XCTestCase {
func testGoToInventory() async {
let store = TestStore(
initialState: AppFeature.State(),
reducer: AppFeature()
)

await store.send(.firstTab(.goToInventoryButtonTapped))
await store.receive(.firstTab(.delegate(.switchToInventoryTab))) {
$0.selectedTab = .inventory
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
import XCTest

@testable import Inventory

class VanillaTests: XCTestCase {
func testFirstTabModel() {
let model = FirstTabModel()

// let expectation = self.expectation(description: "switchToInventoryTab")
model.switchToInventoryTab = {
// expectation.fulfill()
}

model.goToInventoryTab()
// self.wait(for: [expectation], timeout: 0)
}

func testAppModel() {
let model = AppModel(
firstTab: FirstTabModel()
)

model.firstTab.goToInventoryTab()
// XCTAssertEqual(model.selectedTab, .inventory)
}
}
5 changes: 5 additions & 0 deletions 0222-composable-navigation-pt1/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
## [Point-Free](https://www.pointfree.co)

> #### This directory contains code from Point-Free Episode: [Composable Navigation: Tabs](https://www.pointfree.co/episodes/ep222-composable-navigation-tabs)
>
> It’s finally time to tackle navigation in the Composable Architecture. We’ll port the Inventory app we first built to understand SwiftUI navigation, which will push us to understand what makes the architecture “composable,” how it facilitates communication between features, and testing.
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -222,3 +222,5 @@ This repository is the home of code written on episodes of [Point-Free](https://
1. [Modern SwiftUI: Effects, Part 2](0218-modern-swiftui-pt5)
1. [Modern SwiftUI: Dependencies & Testing, Part 1](0219-modern-swiftui-pt6)
1. [Modern SwiftUI: Dependencies & Testing, Part 2](0220-modern-swiftui-pt7)
1. [Point-Free Live: Dependencies & Stacks](0221-pf-live-dependencies-stacks)
1. [Composable Navigation: Tabs](0222-composable-navigation-pt1)

0 comments on commit c0ded85

Please sign in to comment.