Skip to content
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
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,16 @@ package com.github.skyfe79.android.library.app
import android.view.View
import com.github.skyfe79.android.library.app.action.*
import com.github.skyfe79.android.reactcomponentkit.component.LayoutComponent
import com.github.skyfe79.android.reactcomponentkit.eventbus.Token
import com.github.skyfe79.android.reactcomponentkit.dispatcher.dispatch
import com.github.skyfe79.android.reactcomponentkit.viewmodel.Token
import com.github.skyfe79.android.reactcomponentkit.redux.State
import kotlinx.android.synthetic.main.activity_main.view.*
import org.jetbrains.anko.AnkoContext
import org.jetbrains.anko.include
import org.jetbrains.anko.sdk27.coroutines.onClick

class MainViewLayout(token: Token)
: LayoutComponent<MainActivity>(token, false) {
: LayoutComponent<MainActivity>(token) {

/**
* You can use layout xml file like below.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
package com.github.skyfe79.android.library.app

import android.app.Application
import com.github.skyfe79.android.library.app.action.*
import com.github.skyfe79.android.reactcomponentkit.redux.Output
import com.github.skyfe79.android.reactcomponentkit.redux.State
import com.github.skyfe79.android.reactcomponentkit.viewmodel.RootViewModelType
import com.github.skyfe79.android.library.app.redux.routeReducer
import com.github.skyfe79.android.library.app.redux.*
import com.github.skyfe79.android.reactcomponentkit.viewmodel.RCKViewModel

enum class MainRoute {
None,
Expand All @@ -13,17 +15,28 @@ enum class MainRoute {
EmojiCollectionExample,
CollectionViewExample
}
data class MainState(var route: MainRoute): State()
data class MainState(var route: MainRoute): State() {
override fun copyState(): MainState {
return this.copy()
}
}

class MainViewModel: RootViewModelType<MainState>() {
class MainViewModel(application: Application): RCKViewModel<MainState>(application) {

val route: Output<MainRoute> = Output(MainRoute.None)

override fun setupStore() {
store.set(
initialState = MainState(MainRoute.None),
reducers = arrayOf(::routeReducer)
)
initStore { store ->
store.initialState(MainState(MainRoute.None))

store.flow<ClickCounterExampleButtonAction>(::routeToCounterExample)
store.flow<ClickCounterExample2ButtonAction>(::routeToCounterExample2)
store.flow<ClickRecyclerViewExampleButtonAction>(::routeToRecyclerViewExample)
store.flow<ClickEmojiExampleButtonAction>(::routeToEmojiExample)
store.flow<ClickCollectionViewExampleButtonAction>({ state, _ ->
state.copy(route = MainRoute.CollectionViewExample)
})
}
}

override fun on(newState: MainState) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,6 @@ import android.view.View
import android.view.ViewGroup
import com.github.skyfe79.android.library.app.MainState
import com.github.skyfe79.android.reactcomponentkit.component.FragmentComponent
import com.github.skyfe79.android.reactcomponentkit.component.LayoutComponent
import com.github.skyfe79.android.reactcomponentkit.eventbus.Token
import com.github.skyfe79.android.reactcomponentkit.redux.State
import org.jetbrains.anko.*
import org.jetbrains.anko.support.v4.UI
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,40 +2,39 @@ package com.github.skyfe79.android.library.app.examples.collectionview

import android.app.Application
import com.github.skyfe79.android.library.app.examples.collectionview.action.LoadAction
import com.github.skyfe79.android.library.app.examples.collectionview.postwares.makeSectionModels
import com.github.skyfe79.android.library.app.examples.collectionview.reducer.loadEmoji
import com.github.skyfe79.android.library.app.examples.collectionview.reducer.makeSectionModels
import com.github.skyfe79.android.reactcomponentkit.collectionmodels.DefaultSectionModel
import com.github.skyfe79.android.reactcomponentkit.redux.Action
import com.github.skyfe79.android.reactcomponentkit.redux.Output
import com.github.skyfe79.android.reactcomponentkit.redux.State
import com.github.skyfe79.android.reactcomponentkit.redux.VoidAction
import com.github.skyfe79.android.reactcomponentkit.viewmodel.RootAndroidViewModelType
import com.github.skyfe79.android.reactcomponentkit.redux.*
import com.github.skyfe79.android.reactcomponentkit.viewmodel.RCKViewModel


data class CollectionState(
var emojis: List<List<String>> = emptyList(),
var sections: List<DefaultSectionModel> = emptyList()
): State()
): State() {

override fun copyState(): CollectionState {
return this.copy()
}
}



class CollectionViewModel(application: Application): RootAndroidViewModelType<CollectionState>(application) {
class CollectionViewModel(application: Application): RCKViewModel<CollectionState>(application) {

val sections: Output<List<DefaultSectionModel>> = Output(emptyList())

override fun setupStore() {
store.set(
initialState = CollectionState(),
reducers = arrayOf(::loadEmoji),
postwares = arrayOf(::makeSectionModels)
)
}

override fun beforeDispatch(action: Action): Action = when(action) {
is LoadAction -> {
if (store.state.emojis.isNotEmpty()) VoidAction else action
initStore { store ->
store.initialState(CollectionState())
store.flow<LoadAction>(
::loadEmoji,
{ state, _ ->
makeSectionModels(state)
}
)
}
else -> action
}

override fun on(newState: CollectionState) {
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,24 +1,58 @@
package com.github.skyfe79.android.library.app.examples.collectionview.reducer

import androidx.recyclerview.widget.GridLayoutManager
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.LinearSnapHelper
import androidx.recyclerview.widget.StaggeredGridLayoutManager
import com.github.skyfe79.android.library.app.examples.collectionview.CollectionState
import com.github.skyfe79.android.library.app.examples.collectionview.CollectionViewModel
import com.github.skyfe79.android.library.app.examples.collectionview.action.LoadAction
import com.github.skyfe79.android.library.app.examples.emojicollection.models.EmojiBoxModel
import com.github.skyfe79.android.library.app.examples.emojicollection.util.EmojiHelper
import com.github.skyfe79.android.library.app.examples.recyclerview.model.TextMessage
import com.github.skyfe79.android.reactcomponentkit.collectionmodels.DefaultSectionModel
import com.github.skyfe79.android.reactcomponentkit.redux.Action
import com.github.skyfe79.android.reactcomponentkit.redux.State
import io.reactivex.Observable

fun CollectionViewModel.loadEmoji(state: State, action: Action): Observable<State> {
val collectionState = (state as? CollectionState) ?: return Observable.just(state)
fun CollectionViewModel.loadEmoji(state: CollectionState, action: LoadAction): CollectionState {
val emojiCollection = (1..5)
.map {
(1..(40..80).random()).map { EmojiHelper.emoji }
}
return state.copy(emojis = emojiCollection)
}

fun CollectionViewModel.makeSectionModels(state: CollectionState): CollectionState {
val colors = listOf(
0xffd01774.toInt(),
0xfff7f93c.toInt(),
0xfff07777.toInt(),
0xfffcce62.toInt(),
0xff58c8d8.toInt()
)

val sectionModels = state.emojis.mapIndexed { index, list ->
val emojiBoxModels = list.map { EmojiBoxModel(it) }
DefaultSectionModel(
emojiBoxModels,
header = TextMessage("Section Header #$index", colors[index], true),
footer = TextMessage("Section Footer #$index", colors[index], false)
)
{ recyclerView ->
recyclerView.layoutManager = when(index) {
0 -> GridLayoutManager(getApplication(), 8)
1 -> GridLayoutManager(getApplication(), 4)
2 -> StaggeredGridLayoutManager(2, StaggeredGridLayoutManager.VERTICAL)
3 -> GridLayoutManager(getApplication(), 3)
else -> LinearLayoutManager(getApplication(), LinearLayoutManager.HORIZONTAL, false)
}

return when (action) {
is LoadAction -> {
val emojiCollection = (1..5)
.map {
(1..(40..80).random()).map { EmojiHelper.emoji }
}
Observable.just(collectionState.copy(emojis = emojiCollection))
if (index == 4) {
val snapHelper = LinearSnapHelper()
snapHelper.attachToRecyclerView(recyclerView)
}
}
else -> Observable.just(state)
}
return state.copy(sections = sectionModels)
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,19 +3,26 @@ package com.github.skyfe79.android.library.app.examples.counter
import androidx.lifecycle.ViewModelProviders
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.github.skyfe79.android.reactcomponentkit.rx.AutoDisposeBag
import com.github.skyfe79.android.reactcomponentkit.rx.disposedBy
import org.jetbrains.anko.setContentView

class CounterActivity: AppCompatActivity() {
private val disposeBag: AutoDisposeBag by lazy {
AutoDisposeBag(this)
}

private lateinit var viewModel: CounterViewModel
private val layout: CounterLayout by lazy {
CounterLayout(viewModel.token, true)
CounterLayout(viewModel.token)
}

override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)

viewModel = ViewModelProviders.of(this).get(CounterViewModel::class.java)
layout.setContentView(this)

layout.countTextView.text = "${viewModel.count.value}"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,20 @@ import android.view.Gravity
import android.view.View
import android.widget.Button
import android.widget.LinearLayout
import android.widget.ProgressBar
import android.widget.TextView
import com.github.skyfe79.android.library.app.examples.counter.action.AsyncIncreaseAction
import com.github.skyfe79.android.library.app.examples.counter.action.DecreaseAction
import com.github.skyfe79.android.library.app.examples.counter.action.IncreaseAction
import com.github.skyfe79.android.reactcomponentkit.component.LayoutComponent
import com.github.skyfe79.android.reactcomponentkit.eventbus.Token
import com.github.skyfe79.android.reactcomponentkit.dispatcher.dispatch
import com.github.skyfe79.android.reactcomponentkit.viewmodel.Token
import com.github.skyfe79.android.reactcomponentkit.redux.Async
import com.github.skyfe79.android.reactcomponentkit.redux.State
import com.github.skyfe79.android.reactcomponentkit.subscriber.subscribeState
import org.jetbrains.anko.*
import org.jetbrains.anko.sdk27.coroutines.onClick

class CounterLayout(token: Token, receiveState: Boolean): LayoutComponent<CounterActivity>(token, receiveState) {
class CounterLayout(token: Token): LayoutComponent<CounterActivity>(token) {

private enum class IDs {
TextView
Expand All @@ -22,6 +26,12 @@ class CounterLayout(token: Token, receiveState: Boolean): LayoutComponent<Counte
lateinit var countTextView: TextView
private lateinit var increaseButton: Button
private lateinit var decreaseButton: Button
private lateinit var asyncIncreaseButton: Button
private lateinit var progress: ProgressBar

override fun onInit() {
subscribeState()
}

override fun createView(ui: AnkoContext<CounterActivity>): View = with(ui) {
val view = relativeLayout {
Expand All @@ -33,13 +43,18 @@ class CounterLayout(token: Token, receiveState: Boolean): LayoutComponent<Counte
centerInParent()
}

progress = progressBar().lparams {
centerInParent()
}
progress.visibility = View.GONE

linearLayout {
orientation = LinearLayout.HORIZONTAL
gravity = Gravity.CENTER

decreaseButton = button(" - ").lparams(width = 0, weight = 1f)
increaseButton = button(" + ").lparams(width = 0, weight = 1f)

asyncIncreaseButton = button("async +").lparams(width = 0, weight = 1f)
}.applyRecursively {
when(it) {
is Button -> it.textSize = 20f
Expand All @@ -53,11 +68,15 @@ class CounterLayout(token: Token, receiveState: Boolean): LayoutComponent<Counte
}


increaseButton.onClick {
asyncIncreaseButton.setOnClickListener {
dispatch(AsyncIncreaseAction())
}

increaseButton.setOnClickListener {
dispatch(IncreaseAction())
}

decreaseButton.onClick {
decreaseButton.setOnClickListener {
dispatch(DecreaseAction())
}

Expand All @@ -67,5 +86,15 @@ class CounterLayout(token: Token, receiveState: Boolean): LayoutComponent<Counte
override fun on(state: State) {
val countState = (state as? CounterState) ?: return
countTextView.text = "${countState.count}"

when (state.asyncCount) {
is Async.Loading -> {
progress.visibility = View.VISIBLE
progress.animate()
}
is Async.Success -> {
progress.visibility = View.GONE
}
}
}
}
Loading