Added Fragment, Store and StoreProvider stub types

This commit is contained in:
Max Desiatov 2018-10-12 09:03:04 +01:00
parent 3b8d36a643
commit 88537ac046
No known key found for this signature in database
GPG Key ID: FE08EBF9CF58CBA2
6 changed files with 72 additions and 13 deletions

View File

@ -216,12 +216,12 @@
607FACCF1AFB9204008FA782 = { 607FACCF1AFB9204008FA782 = {
CreatedOnToolsVersion = 6.3.1; CreatedOnToolsVersion = 6.3.1;
DevelopmentTeam = H4Z9Z4RD2G; DevelopmentTeam = H4Z9Z4RD2G;
LastSwiftMigration = 0900; LastSwiftMigration = 1000;
}; };
607FACE41AFB9204008FA782 = { 607FACE41AFB9204008FA782 = {
CreatedOnToolsVersion = 6.3.1; CreatedOnToolsVersion = 6.3.1;
DevelopmentTeam = H4Z9Z4RD2G; DevelopmentTeam = H4Z9Z4RD2G;
LastSwiftMigration = 0900; LastSwiftMigration = 1000;
TestTargetID = 607FACCF1AFB9204008FA782; TestTargetID = 607FACCF1AFB9204008FA782;
}; };
}; };
@ -508,8 +508,7 @@
MODULE_NAME = ExampleApp; MODULE_NAME = ExampleApp;
PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.demo.$(PRODUCT_NAME:rfc1034identifier)"; PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.demo.$(PRODUCT_NAME:rfc1034identifier)";
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
SWIFT_SWIFT3_OBJC_INFERENCE = Default; SWIFT_VERSION = 4.2;
SWIFT_VERSION = 4.0;
}; };
name = Debug; name = Debug;
}; };
@ -524,8 +523,7 @@
MODULE_NAME = ExampleApp; MODULE_NAME = ExampleApp;
PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.demo.$(PRODUCT_NAME:rfc1034identifier)"; PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.demo.$(PRODUCT_NAME:rfc1034identifier)";
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
SWIFT_SWIFT3_OBJC_INFERENCE = Default; SWIFT_VERSION = 4.2;
SWIFT_VERSION = 4.0;
}; };
name = Release; name = Release;
}; };
@ -546,8 +544,7 @@
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.$(PRODUCT_NAME:rfc1034identifier)"; PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.$(PRODUCT_NAME:rfc1034identifier)";
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
SWIFT_SWIFT3_OBJC_INFERENCE = Default; SWIFT_VERSION = 4.2;
SWIFT_VERSION = 4.0;
TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Gluon_Example.app/Gluon_Example"; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Gluon_Example.app/Gluon_Example";
}; };
name = Debug; name = Debug;
@ -565,8 +562,7 @@
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.$(PRODUCT_NAME:rfc1034identifier)"; PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.$(PRODUCT_NAME:rfc1034identifier)";
PRODUCT_NAME = "$(TARGET_NAME)"; PRODUCT_NAME = "$(TARGET_NAME)";
SWIFT_SWIFT3_OBJC_INFERENCE = Default; SWIFT_VERSION = 4.2;
SWIFT_VERSION = 4.0;
TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Gluon_Example.app/Gluon_Example"; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Gluon_Example.app/Gluon_Example";
}; };
name = Release; name = Release;

View File

@ -14,7 +14,7 @@ class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow? var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch. // Override point for customization after application launch.
return true return true
} }

View File

@ -1,11 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="13771" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES" initialViewController="vXZ-lx-hvc"> <document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="14313.18" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES" initialViewController="vXZ-lx-hvc">
<device id="retina4_7" orientation="portrait"> <device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/> <adaptation id="fullscreen"/>
</device> </device>
<dependencies> <dependencies>
<deployment identifier="iOS"/> <deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13772"/> <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14283.14"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/> <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies> </dependencies>
<scenes> <scenes>
@ -20,6 +20,16 @@
<view key="view" contentMode="scaleToFill" id="kh9-bI-dsS"> <view key="view" contentMode="scaleToFill" id="kh9-bI-dsS">
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/> <rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/> <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<subviews>
<button opaque="NO" contentMode="scaleToFill" fixedFrame="YES" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="ovA-Wu-0YV">
<rect key="frame" x="164" y="318" width="46" height="30"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<state key="normal" title="Button"/>
<connections>
<action selector="onTap:" destination="vXZ-lx-hvc" eventType="touchUpInside" id="5VH-rA-yXd"/>
</connections>
</button>
</subviews>
<color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/> <color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
</view> </view>
</viewController> </viewController>

View File

@ -9,6 +9,25 @@
import UIKit import UIKit
import Gluon import Gluon
struct TodoList: Store {
enum Action {
case add(String, Int)
case remove(Int)
case update(String, Int)
}
func apply(action: Action, to state: inout [String]) {
switch action {
case let .add(item, index):
state.insert(item, at: index)
case let .update(item, index):
state[index] = item
case let .remove(index):
state.remove(at: index)
}
}
}
final class Counter: Component<NoProps, Counter.State> { final class Counter: Component<NoProps, Counter.State> {
struct State: StateType { struct State: StateType {
var counter = 0 var counter = 0

View File

@ -63,6 +63,9 @@ open class BaseComponent<Props: Equatable>: ComponentType {
} }
} }
final class Fragment: BaseComponent<NoProps> {
}
extension BaseComponent where Props: Default { extension BaseComponent where Props: Default {
public static func node(childrenFactory: () -> [Node]) -> Node { public static func node(childrenFactory: () -> [Node]) -> Node {
return self.node(Props(), childrenFactory: childrenFactory) return self.node(Props(), childrenFactory: childrenFactory)
@ -91,6 +94,10 @@ extension Node {
public init(_ string: String) { public init(_ string: String) {
factory = { string } factory = { string }
} }
public init(_ nodes: [Node]) {
factory = { Fragment(props: NoProps(), children: nodes) }
}
} }
public final class StackView: BaseComponent<NoProps> { public final class StackView: BaseComponent<NoProps> {

27
Gluon/Classes/Store.swift Normal file
View File

@ -0,0 +1,27 @@
//
// Store.swift
// Gluon
//
// Created by Max Desiatov on 12/10/2018.
//
import Foundation
public protocol Store: Equatable {
associatedtype State
associatedtype Action
func apply(action: Action, to: inout State)
}
// FIXME: need context working for its implementation
public final class StoreProvider<S>: Component<StoreProvider.Props, S.State>
where S: Store, S.State: StateType {
struct Props: Equatable {
var store: S
}
public func render() -> Node {
return Node(children)
}
}