Intro to CrossPlatform Mobile Apps
Well... It sucks!
(compared to web development)
Why?
Device Fragmentation
Global Market Share
18%
82%
US
50%
50%
Revenue
2x
1x
So which platform do I pick?
Languages & Environments
Java
XML
Groovy
(AndroidStudio)
Objective C or Swift
(XCode)
class FetchWeatherData extends AsyncTask<Void, Void, String> {
@Override
protected String doInBackground(Void... params) {
// These two need to be declared outside the try/catch
// so that they can be closed in the finally block.
HttpURLConnection urlConnection = null;
BufferedReader reader = null;
// Will contain the raw JSON response as a string.
String forecastJsonStr = null;
try {
// Construct the URL for the OpenWeatherMap query
// Possible parameters are avaiable at OWM's forecast API page, at
// http://openweathermap.org/API#forecast
URL url = new URL("http://api.openweathermap.org/data/2.5/forecast/daily?q=94043&mode=json&units=metric&cnt=7&appid=2de143494c0b295cca9337e1e96b00e0");
// Create the request to OpenWeatherMap, and open the connection
urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setRequestMethod("GET");
urlConnection.connect();
// Read the input stream into a String
InputStream inputStream = urlConnection.getInputStream();
StringBuffer buffer = new StringBuffer();
if (inputStream == null) {
// Nothing to do.
return null;
}
reader = new BufferedReader(new InputStreamReader(inputStream));
String line;
while ((line = reader.readLine()) != null) {
// Since it's JSON, adding a newline isn't necessary (it won't affect parsing)
// But it does make debugging a *lot* easier if you print out the completed
// buffer for debugging.
buffer.append(line + "\n");
}
if (buffer.length() == 0) {
// Stream was empty. No point in parsing.
return null;
}
forecastJsonStr = buffer.toString();
return forecastJsonStr;
} catch (IOException e) {
Log.e("PlaceholderFragment", "Error ", e);
// If the code didn't successfully get the weather data, there's no point in attemping
// to parse it.
return null;
} finally{
if (urlConnection != null) {
urlConnection.disconnect();
}
if (reader != null) {
try {
reader.close();
} catch (final IOException e) {
Log.e("PlaceholderFragment", "Error closing stream", e);
}
}
}
}
@Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
tvWeatherJson.setText(s);
Log.i("json", s);
}
}
Actual Android Code : GET
Javascript
fetch(endpoint, fetchConfig)
.then(response => {
return response.json()
)
(Bamm!)
Layouts
Android: XML
Layouts
iOS: StoryBoard & AutoLayout
Layouts
Web: CSS
Layouts
ReactNative: CSS+Flexbox
Layouts
Layouts
Distribution Platforms
AppStore
brew install node
brew install watchman
https://facebook.github.io/react-native/docs
npm install -g react-native-cli
react-native init AwesomeProject
cd AwesomeProject
react-native run-ios
https://facebook.github.io/react-native/docs
<ListView />
<MapView />
<Text />
<View />
...
<TabBarIOS />
...
<ToolbarAndroid />
<SegmentedControlIOS />
<ViewPagerAndroid />
It's React!
We have Components!
We pass values between them using Properties (Props)
Each component has State that you can change
Let's see all this in Action!!
A Simple Counter App
npm i react-native-router-flux --save
<Router>
<Scene
key="counter"
component={Counter}
title="Counter"
initial={true}
/>
<Scene
key="count"
component={Count}
title="Count"
/>
</Router>
Actions.count({key: value}) // launch Count component
Adding Mobx
npm i mobx mobx-react --save
npm i babel-plugin-transform-decorators-legacy babel-preset-react-native-stage-0 --save
Adding Babel decorators transformer/preset
{
"presets": ["react-native"],
"plugins": ["transform-decorators-legacy"]
}
Add plugin to .babelrc