Commit e78320a2 authored by Wietse Kuipers's avatar Wietse Kuipers
Browse files

Refactor to satisfactory navigation

parent 85c19ca2
...@@ -10,8 +10,8 @@ New and improved ThaliApp ...@@ -10,8 +10,8 @@ New and improved ThaliApp
`yarn install` `yarn install`
## Starting the app ## Starting the app
Ensure that the development server is started with `react-native start`. Ensure that the development server is started with `yarn run react-native start`.
Deploy the app on a running emulator or connected Android Phone with `react-native run-android`. Deploy the app on a running emulator or connected Android Phone with `yarn run react-native run-android`.
## Debugging ## Debugging
Open the console with `react-native log-android`. Open the console with `yarn run react-native log-android`.
export const LOGIN = 'LOGIN'; export const LOGIN = 'LOGIN';
export const NAVIGATE = 'NAVIGATE';
...@@ -3,7 +3,6 @@ import * as types from './actionTypes'; ...@@ -3,7 +3,6 @@ import * as types from './actionTypes';
export function login(username, password) { export function login(username, password) {
return { return {
type: types.LOGIN, type: types.LOGIN,
username, success: password === '42',
password,
}; };
} }
import * as types from './actionTypes';
export function navigate(scene) {
return {
type: types.NAVIGATE,
scene,
};
}
...@@ -3,12 +3,17 @@ import { createStore, applyMiddleware, combineReducers } from 'redux'; ...@@ -3,12 +3,17 @@ import { createStore, applyMiddleware, combineReducers } from 'redux';
import { Provider } from 'react-redux'; import { Provider } from 'react-redux';
import thunk from 'redux-thunk'; import thunk from 'redux-thunk';
import * as reducers from '../reducers'; import * as reducers from './reducers';
import ThaliApp from './ThaliApp'; import ReduxNavigator from './components/navigator';
const createStoreWithMiddleware = applyMiddleware(thunk)(createStore); const createStoreWithMiddleware = applyMiddleware(thunk)(createStore);
const reducer = combineReducers(reducers); const reducer = combineReducers(reducers);
const store = createStoreWithMiddleware(reducer); const store = createStoreWithMiddleware(reducer);
const Main = () => <Provider store={store}><ThaliApp /></Provider>;
const Main = () =>
<Provider store={store}>
<ReduxNavigator />
</Provider>
;
export default Main; export default Main;
import React, { Component } from 'react'; import React, { Component } from 'react';
import { View, TextInput, Button, Text } from 'react-native'; import { View, TextInput, Button, Text } from 'react-native';
import { connect } from 'react-redux';
export default class Login extends Component { import * as actions from '../actions/login';
class Login extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
username: '', username: '',
password: '', password: '',
}; };
this.login = props.login;
}
onPress() {
return this.login.bind(null, this.state.username, this.state.password);
} }
render() { render() {
const { loginError } = this.props; const { loginError, login } = this.props;
return ( return (
<View> <View>
<TextInput <TextInput
...@@ -28,7 +26,7 @@ export default class Login extends Component { ...@@ -28,7 +26,7 @@ export default class Login extends Component {
secureTextEntry secureTextEntry
onChangeText={password => this.setState({ password })} onChangeText={password => this.setState({ password })}
/> />
<Button title="Log in" onPress={this.onPress()} /> <Button title="Log in" onPress={() => login(this.state.username, this.state.password)} />
<Text>{ loginError ? 'Login faal' : '' }</Text> <Text>{ loginError ? 'Login faal' : '' }</Text>
</View> </View>
); );
...@@ -39,3 +37,10 @@ Login.propTypes = { ...@@ -39,3 +37,10 @@ Login.propTypes = {
login: React.PropTypes.func.isRequired, login: React.PropTypes.func.isRequired,
loginError: React.PropTypes.bool.isRequired, loginError: React.PropTypes.bool.isRequired,
}; };
const mapStateToProps = state => state.login;
const mapDispatchToProps = dispatch => ({
login: (username, password) => dispatch(actions.login(username, password)),
});
export default connect(mapStateToProps, mapDispatchToProps)(Login);
import React from 'react';
import { View, Text } from 'react-native';
const Welcome = () =>
<View>
<Text>Welcome!</Text>
</View>
;
export default Welcome;
import React from 'react';
import { connect } from 'react-redux';
import * as actions from '../actions/navigation';
import Login from './Login';
import Welcome from './Welcome';
// const mapStateToProps = state => state.currentScene;
const mapStateToProps = state => (
{ currentScene: state.navigation.currentScene }
);
const mapDispatchToProps = dispatch => ({
navigate: scene => dispatch(actions.navigate(scene)),
});
const ReduxNavigator = (props) => {
const currentScene = props.currentScene;
switch (currentScene) {
case 'login':
return (<Login />);
case 'welcome':
return (<Welcome />);
default:
return (<Login />);
}
};
ReduxNavigator.propTypes = {
currentScene: React.PropTypes.string.isRequired,
};
export default connect(mapStateToProps, mapDispatchToProps)(ReduxNavigator);
import React from 'react';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import Login from '../components/Login';
import * as ThaliAppActions from '../actions/ThaliAppActions';
const ThaliApp = (props) => {
const { state, actions } = props;
return (
<Login
loggedIn={state.loggedIn}
loginError={state.loginError}
{...actions}
/>
);
};
ThaliApp.propTypes = {
state: React.PropTypes.objectOf(React.PropTypes.oneOfType([
React.PropTypes.string,
React.PropTypes.bool,
React.PropTypes.number,
])).isRequired,
actions: React.PropTypes.objectOf(React.PropTypes.func).isRequired,
};
export default connect(
state => (
{ state: state.login }
),
dispatch => (
{ actions: bindActionCreators(ThaliAppActions, dispatch) }
),
)(ThaliApp);
import login from './login'; import login from './login';
import navigation from './navigation';
export { export {
login, login,
navigation,
}; };
...@@ -8,7 +8,7 @@ const initialState = { ...@@ -8,7 +8,7 @@ const initialState = {
export default function login(state = initialState, action = {}) { export default function login(state = initialState, action = {}) {
switch (action.type) { switch (action.type) {
case types.LOGIN: case types.LOGIN:
if (action.password === '42') { if (action.success) {
return { ...state, loginError: false, loggedIn: true }; return { ...state, loginError: false, loggedIn: true };
} }
return { ...state, loginError: true }; return { ...state, loginError: true };
......
import * as types from '../actions/actionTypes';
const initialState = {
currentScene: 'login',
};
export default function navigate(state = initialState, action = {}) {
switch (action.type) {
case types.LOGIN:
if (action.success) {
return { ...state, currentScene: 'welcome' };
}
return { ...state };
default:
return { ...state };
}
}
import { import {
AppRegistry, AppRegistry,
} from 'react-native'; } from 'react-native';
import App from './app/containers/app'; import App from './app/app';
AppRegistry.registerComponent('ThaliApp', () => App); AppRegistry.registerComponent('ThaliApp', () => App);
import { import {
AppRegistry, AppRegistry,
} from 'react-native'; } from 'react-native';
import App from './app/containers/app'; import App from './app/app';
AppRegistry.registerComponent('ThaliApp', () => App); AppRegistry.registerComponent('ThaliApp', () => App);
...@@ -349,7 +349,7 @@ babel-helpers@^6.22.0: ...@@ -349,7 +349,7 @@ babel-helpers@^6.22.0:
babel-runtime "^6.22.0" babel-runtime "^6.22.0"
babel-template "^6.22.0" babel-template "^6.22.0"
babel-jest@18.0.0, babel-jest@^18.0.0: babel-jest@^18.0.0:
version "18.0.0" version "18.0.0"
resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-18.0.0.tgz#17ebba8cb3285c906d859e8707e4e79795fb65e3" resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-18.0.0.tgz#17ebba8cb3285c906d859e8707e4e79795fb65e3"
dependencies: dependencies:
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment