{"id":2623,"date":"2017-07-19T13:20:07","date_gmt":"2017-07-19T13:20:07","guid":{"rendered":"https:\/\/intelligentbee.com\/blog\/?p=2623"},"modified":"2024-12-13T08:19:57","modified_gmt":"2024-12-13T08:19:57","slug":"introduction-react-native","status":"publish","type":"post","link":"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/","title":{"rendered":"Introduction to React Native"},"content":{"rendered":"<blockquote><p>React Native is a framework for building native apps using React made by Facebook. With React Native, you don&#8217;t build a \u201cmobile web app\u201d, an \u201cHTML5 app\u201d, or a \u201chybrid app\u201d. You build a real mobile app that&#8217;s indistinguishable from an app built using Objective-C or Java. React Native uses the same fundamental UI building blocks as regular iOS and Android apps. You just put those building blocks together using JavaScript and React. &#8211; from <a href=\"https:\/\/facebook.github.io\/react-native\/\" target=\"_blank\" rel=\"noopener\">https:\/\/facebook.github.io\/react-native\/<\/a><\/p><\/blockquote>\n<p>In the following lines we will take a short tour of React Native to help you familiarize with the platform and hopefully get you started in your React Native development career.<\/p>\n<p>We will create a simple app called RandomNumbers that will pick some numbers from a pool, numbers that you can use later at anything you need (for example playing the lottery).<\/p>\n<div id=\"ez-toc-container\" class=\"ez-toc-v2_0_68_1 counter-hierarchy ez-toc-counter ez-toc-grey ez-toc-container-direction\">\n<div class=\"ez-toc-title-container\">\n<p class=\"ez-toc-title \" >Table of Contents<\/p>\n<span class=\"ez-toc-title-toggle\"><a href=\"#\" class=\"ez-toc-pull-right ez-toc-btn ez-toc-btn-xs ez-toc-btn-default ez-toc-toggle\" aria-label=\"Toggle Table of Content\"><span class=\"ez-toc-js-icon-con\"><span class=\"\"><span class=\"eztoc-hide\" style=\"display:none;\">Toggle<\/span><span class=\"ez-toc-icon-toggle-span\"><svg style=\"fill: #999;color:#999\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" class=\"list-377408\" width=\"20px\" height=\"20px\" viewBox=\"0 0 24 24\" fill=\"none\"><path d=\"M6 6H4v2h2V6zm14 0H8v2h12V6zM4 11h2v2H4v-2zm16 0H8v2h12v-2zM4 16h2v2H4v-2zm16 0H8v2h12v-2z\" fill=\"currentColor\"><\/path><\/svg><svg style=\"fill: #999;color:#999\" class=\"arrow-unsorted-368013\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"10px\" height=\"10px\" viewBox=\"0 0 24 24\" version=\"1.2\" baseProfile=\"tiny\"><path d=\"M18.2 9.3l-6.2-6.3-6.2 6.3c-.2.2-.3.4-.3.7s.1.5.3.7c.2.2.4.3.7.3h11c.3 0 .5-.1.7-.3.2-.2.3-.5.3-.7s-.1-.5-.3-.7zM5.8 14.7l6.2 6.3 6.2-6.3c.2-.2.3-.5.3-.7s-.1-.5-.3-.7c-.2-.2-.4-.3-.7-.3h-11c-.3 0-.5.1-.7.3-.2.2-.3.5-.3.7s.1.5.3.7z\"\/><\/svg><\/span><\/span><\/span><\/a><\/span><\/div>\n<nav><ul class='ez-toc-list ez-toc-list-level-1 ' ><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-1\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Install_React_Native\" title=\"Install React Native\">Install React Native<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-2\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Make_Your_First_Change\" title=\"Make Your First Change\">Make Your First Change<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-3\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#React_Native_Components\" title=\"React Native Components\">React Native Components<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-4\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Generate_a_Random_Number\" title=\"Generate a Random Number\">Generate a Random Number<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-5\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Output_Data_to_the_Screen\" title=\"Output Data to the Screen\">Output Data to the Screen<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-6\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#How_Many_Numbers\" title=\"How Many Numbers?\">How Many Numbers?<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-7\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Making_the_App_Look_Good\" title=\"Making the App Look Good\">Making the App Look Good<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-8\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Getting_Your_App_Ready_to_Be_Published\" title=\"Getting Your App Ready to Be Published\">Getting Your App Ready to Be Published<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-9\" href=\"https:\/\/intelligentbee.com\/blog\/introduction-react-native\/#Final_Words\" title=\"Final Words\">Final Words<\/a><\/li><\/ul><\/nav><\/div>\n<h2><span class=\"ez-toc-section\" id=\"Install_React_Native\"><\/span>Install React Native<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>You will need to install Node, Watchman, the React Native command line interface, a JDK, and Xcode or Android Studio (or both). You can find details on how exactly do to this, depending on your platform, here:\u00a0<a href=\"https:\/\/facebook.github.io\/react-native\/docs\/getting-started.html\" target=\"_blank\" rel=\"noopener\">https:\/\/facebook.github.io\/react-native\/docs\/getting-started.html<\/a>. Select the &#8220;Building Projects with Native Code&#8221; tab and then follow the instructions.<\/p>\n<p><img decoding=\"async\" class=\"size-full wp-image-2639 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-15.33.12.png\" alt=\"\" width=\"704\" height=\"433\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-15.33.12.png 704w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-15.33.12-300x185.png 300w\" sizes=\"(max-width: 704px) 100vw, 704px\" \/><\/p>\n<p>When you\u2019re done, create a new project with the <code>react<span class=\"token operator\">-<\/span>native init RandomNumbers<\/code> command then <code>cd<\/code> into the newly created <code>RandomNumbers<\/code> folder.<\/p>\n<p>The above command created an empty React Native project that you can immediately run on your device using the <code>react-native run-ios<\/code> or <code>react-native run-android<\/code> commands (you need to have an Android emulator already started for the last command to work).<\/p>\n<p><img decoding=\"async\" class=\"aligncenter wp-image-2642 size-medium\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-15.45.02-169x300.png\" alt=\"\" width=\"169\" height=\"300\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-15.45.02-169x300.png 169w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-15.45.02-577x1024.png 577w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-15.45.02.png 640w\" sizes=\"(max-width: 169px) 100vw, 169px\" \/><\/p>\n<h2><span class=\"ez-toc-section\" id=\"Make_Your_First_Change\"><\/span>Make Your First Change<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Open the <code>RandomNumbers<\/code> folder in an code editor of your choice. Here you will find some files and folders, the most important ones being the <code>index.ios.js<\/code> and <code>index.android.js<\/code> files that contain our starting point of the app.<\/p>\n<p>Edit one (or both) of the files above, depending on the platform you are testing, to the following:<\/p>\n<p>&nbsp;<\/p>\n<pre class=\"theme:github lang:js decode:true \">\/\/ ...\r\n\r\nexport default class RandomNumbers extends Component {\r\n  render() {\r\n    return (\r\n      &lt;View style={styles.container}&gt;\r\n        &lt;Text style={styles.welcome}&gt;\r\n          Random Numbers\r\n        &lt;\/Text&gt;\r\n      &lt;\/View&gt;\r\n    );\r\n  }\r\n}\r\n\r\n\/\/ ...<\/pre>\n<p>Save the edited file, then, in the emulator, press <strong>Cmd+R<\/strong> to reload the app. It will refresh itself to reflect the changes, no recompiling needed. Isn\u2019t this cool?<\/p>\n<h2><span class=\"ez-toc-section\" id=\"React_Native_Components\"><\/span>React Native Components<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Just like in React, a React Native app is made up by several components that work together to achieve the ultimate goal of the app. To see the list of available components visit <a href=\"https:\/\/facebook.github.io\/react-native\/docs\/getting-started.html\" target=\"_blank\" rel=\"noopener\">https:\/\/facebook.github.io\/react-native\/docs\/getting-started.html<\/a> and scroll to the <strong>Components<\/strong> section in the left menu.<\/p>\n<p>We will start by making the two React Native starting points (from the <code>index.ios.js<\/code> and <code>index.android.js<\/code> files) to load a single component called\u00a0<code>App<\/code>.<\/p>\n<p>Create a new <code>App.js<\/code> file with the following content:<\/p>\n<pre class=\"theme:github lang:js decode:true\">import React, { Component } from 'react';\r\nimport {\r\n    View,\r\n    Text,\r\n    StyleSheet\r\n} from 'react-native';\r\n\r\nexport default class App extends Component {\r\n    render() {\r\n        return (\r\n            &lt;View style={styles.container}&gt;\r\n                &lt;Text style={styles.welcome}&gt;\r\n                    Random Numbers\r\n                &lt;\/Text&gt;\r\n            &lt;\/View&gt;\r\n        );\r\n    }\r\n}\r\n\r\nconst styles = StyleSheet.create({\r\n    container: {\r\n        flex: 1,\r\n        justifyContent: 'center',\r\n        alignItems: 'center',\r\n        backgroundColor: '#F5FCFF',\r\n    },\r\n    welcome: {\r\n        fontSize: 20,\r\n        textAlign: 'center',\r\n        margin: 10,\r\n    },\r\n});<\/pre>\n<p>Now change the <code>index.ios.js<\/code> and <code>index.android.js<\/code> to the following (both will have the same content):<\/p>\n<pre class=\"theme:github lang:js decode:true \">import React, { Component } from 'react';\r\nimport {\r\n  AppRegistry\r\n} from 'react-native';\r\nimport App from '.\/App';\r\n\r\nexport default class RandomNumbers extends Component {\r\n  render() {\r\n    return (\r\n       &lt;App \/&gt;\r\n    );\r\n  }\r\n}\r\n\r\nAppRegistry.registerComponent('RandomNumbers', () =&gt; RandomNumbers);<\/pre>\n<p>We just removed everything from them and loaded the <code>App<\/code> component so we now have a common starting point for both platforms.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"Generate_a_Random_Number\"><\/span>Generate a Random Number<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Let\u2019s add a <code>Button<\/code> that will trigger the number generator of our app. First import the <code>Button<\/code> component, then add the actual button to the render method (in <code>App.js<\/code>):<\/p>\n<pre class=\"theme:github lang:js decode:true\">\/\/ ...\r\n\r\nimport {\r\n    View,\r\n    Text,\r\n    Button,\r\n    StyleSheet\r\n} from 'react-native';\r\n\r\nexport default class App extends Component {\r\n    render() {\r\n        return (\r\n            &lt;View style={styles.container}&gt;\r\n                &lt;Text style={styles.welcome}&gt;\r\n                    Random Numbers\r\n                &lt;\/Text&gt;\r\n                &lt;Button onPress={this.generateRandomNumber} title=\"Generate!\" \/&gt;\r\n            &lt;\/View&gt;\r\n        );\r\n    }\r\n}\r\n\r\n\/\/ ...\r\n\r\n<\/pre>\n<p>For this to work we need to define a new method <code>generateRandomNumber<\/code>:<\/p>\n<pre class=\"theme:github lang:js decode:true\">\/\/ ...\r\n\r\nexport default class App extends Component {\r\n    generateRandomNumber = () =&gt; {\r\n        let random = Math.floor(Math.random() * 100);\r\n        console.log(random);\r\n    }\r\n    \r\n\/\/ ...<\/pre>\n<p>Now if you click on the <strong>Generate!<\/strong> button, a random number between 0 and 100 will be generated and printed to the console.<\/p>\n<p>To see the console output open the developer menu in your app by \u00a0pressing <strong>Cmd+D<\/strong>\u00a0and select <strong>Debug JS Remotely<\/strong>. A new browser window will open and there you can check the console output like you normally do when developing for the web.<\/p>\n<p><img decoding=\"async\" class=\"size-large wp-image-2656 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.22.28-1024x589.png\" alt=\"\" width=\"525\" height=\"302\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.22.28-1024x589.png 1024w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.22.28-300x173.png 300w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.22.28-768x442.png 768w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.22.28.png 2728w\" sizes=\"(max-width: 525px) 100vw, 525px\" \/><\/p>\n<p><img decoding=\"async\" class=\"size-medium wp-image-2655 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.23.12-185x300.png\" alt=\"\" width=\"185\" height=\"300\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.23.12-185x300.png 185w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.23.12-768x1248.png 768w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.23.12-630x1024.png 630w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-18-at-16.23.12.png 864w\" sizes=\"(max-width: 185px) 100vw, 185px\" \/><\/p>\n<h2><span class=\"ez-toc-section\" id=\"Output_Data_to_the_Screen\"><\/span>Output Data to the Screen<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Now we have our generated random number, but how can we show it to the user? For this we will use the <strong>state<\/strong> concept of React. The are two fundamental concepts of React that you need to understand: the <strong>state<\/strong> and <strong>props<\/strong>.<\/p>\n<blockquote><p>There are two types of data that control a component: props and state. Props are set by the parent and they are fixed throughout the lifetime of a component. For data that is going to change, we have to use state.<\/p><\/blockquote>\n<p>You can read more about this topic here:<\/p>\n<ul>\n<li><a href=\"https:\/\/facebook.github.io\/react-native\/docs\/props.html\" target=\"_blank\" rel=\"noopener\">https:\/\/facebook.github.io\/react-native\/docs\/props.html<\/a><\/li>\n<li><a href=\"https:\/\/facebook.github.io\/react-native\/docs\/state.html\">https:\/\/facebook.github.io\/react-native\/docs\/state.html<\/a><\/li>\n<\/ul>\n<p>Start by creating a constructor for our <code>App<\/code> component that sets the initial state:<\/p>\n<pre class=\"theme:github lang:js decode:true\">\/\/ ...\r\n\r\nexport default class App extends Component {\r\n    constructor(props) {\r\n        super(props);\r\n\r\n        this.state = {\r\n            random: null\r\n        };\r\n    }\r\n\r\n\/\/ ...<\/pre>\n<p>In the <code>generateRandomNumber<\/code> method, change the state to contain the newly generated number:<\/p>\n<pre class=\"theme:github lang:js decode:true\">\/\/ ...\r\n\r\ngenerateRandomNumber = () =&gt; {\r\n    let random = Math.floor(Math.random() * 100);\r\n    this.setState({random: random});\r\n}\r\n\r\n\/\/ ...<\/pre>\n<p>Finally add a new <code>Text<\/code> component in the <code>render()<\/code> method that will show the random number from the app\u2019s state:<\/p>\n<pre class=\"theme:github lang:default decode:true\">\/\/ ...\r\n\r\nrender() {\r\n    return (\r\n        &lt;View style={styles.container}&gt;\r\n            &lt;Text style={styles.welcome}&gt;\r\n                Random Numbers\r\n            &lt;\/Text&gt;\r\n            &lt;Text&gt;{this.state.random}&lt;\/Text&gt;\r\n            &lt;Button onPress={this.generateRandomNumber} title=\"Generate!\" \/&gt;\r\n        &lt;\/View&gt;\r\n    );\r\n}\r\n\r\n\/\/ ...<\/pre>\n<p>Now, every time you click the <strong>Generate!<\/strong> button a new random number will appear on the screen.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"How_Many_Numbers\"><\/span>How Many Numbers?<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>What if you need more than one number, extracted from a pool of numbers?<\/p>\n<p>To define the pool of numbers we will use a <strong>slider<\/strong> with values from 1 to 100. To define how many numbers do we need to be extracted from the pool, we will use a <strong>picker<\/strong> with values from 1 to 10. This way we can configure the app to do what we need at run-time.<\/p>\n<p>Import the <code>Slider<\/code> component then add it to the app:<\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;Text style={styles.welcome}&gt;\r\n    Random Numbers\r\n&lt;\/Text&gt;\r\n&lt;Slider style={{width: '100%'}} minimumValue={1} maximumValue={100} \/&gt;\r\n&lt;Text&gt;{this.state.random}&lt;\/Text&gt;<\/pre>\n<p>We need to show the current slider value to the user so we will add it to the state of our app:<\/p>\n<pre class=\"theme:github lang:js decode:true\">this.state = {\r\n    random: null,\r\n    pool: 1\r\n};<\/pre>\n<p>When the slider moves, we have to update the state:<\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;Slider style={{width: '100%'}} minimumValue={1} maximumValue={100} onValueChange={(value) =&gt; this.setState({pool: Math.round(value)})} \/&gt;<\/pre>\n<p>Add a new text component to show it to the user (and an informative label):<\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;Text style={styles.welcome}&gt;\r\n    Random Numbers\r\n&lt;\/Text&gt;\r\n&lt;Text&gt;Pool of numbers:&lt;\/Text&gt;\r\n&lt;Text&gt;{this.state.pool}&lt;\/Text&gt;<\/pre>\n<p><span style=\"font-weight: 400;\">Now to select how many numbers we need, let\u2019s try a picker:<\/span><\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;Picker selectedValue={this.state.amount} style={{width: '100%'}} onValueChange={(itemValue, itemIndex) =&gt; this.setState({amount: itemValue})}&gt;\r\n    &lt;Picker.Item label=\"1\" value=\"1\" \/&gt;\r\n    &lt;Picker.Item label=\"2\" value=\"2\" \/&gt;\r\n    &lt;Picker.Item label=\"3\" value=\"3\" \/&gt;\r\n    &lt;Picker.Item label=\"4\" value=\"4\" \/&gt;\r\n    &lt;Picker.Item label=\"5\" value=\"5\" \/&gt;\r\n    &lt;Picker.Item label=\"6\" value=\"6\" \/&gt;\r\n    &lt;Picker.Item label=\"7\" value=\"7\" \/&gt;\r\n    &lt;Picker.Item label=\"8\" value=\"8\" \/&gt;\r\n    &lt;Picker.Item label=\"9\" value=\"9\" \/&gt;\r\n    &lt;Picker.Item label=\"10\" value=\"10\" \/&gt;\r\n&lt;\/Picker&gt;<\/pre>\n<p>For this we added <code>amount<\/code> to the state:<\/p>\n<pre class=\"theme:github lang:js decode:true\">this.state = {\r\n    random: null,\r\n    pool: 1,\r\n    amount: 1\r\n};<\/pre>\n<p>Now let\u2019s change the <code>generateRandomNumbers<\/code> method to take in account the new settings:<\/p>\n<pre class=\"theme:github lang:js decode:true\">generateRandomNumber = () =&gt; {\r\n    \/\/ build the pool of numbers\r\n    var pool = [];\r\n    for(let i = 1; i &lt;= this.state.pool; i++) {\r\n        pool.push(i);\r\n    }\r\n    \r\n    \/\/ generate random numbers\r\n    var randomString = '';\r\n    for(let i = 1; i &lt;= this.state.amount; i++) {\r\n        let index = Math.floor(Math.random() * pool.length);\r\n        let random = pool[index];\r\n        pool.splice(index, 1);\r\n        randomString = randomString + (randomString ? \", \" : \"\") + random;\r\n    }\r\n    this.setState({random: randomString});\r\n}<\/pre>\n<p>What if you try to generate 10 numbers out of 5? Or something like this? We will have to tell the user that\u2019s not possible using an <strong>alert<\/strong>.<\/p>\n<pre class=\"theme:github lang:js decode:true\">generateRandomNumber = () =&gt; {\r\n    if(this.state.amount &gt; this.state.pool) {\r\n        Alert.alert(\"Error\", \"The pool must not be smaller than the amount of numbers you want to generate!\");\r\n        return;\r\n    }\r\n\r\n    \/\/ ...<\/pre>\n<p><span style=\"font-weight: 400;\">That\u2019s all we had to do for our app functionality. Try it!<\/span><\/p>\n<p><span style=\"font-weight: 400;\">&#8230; but, to be honest, it doesn&#8217;t look so good \ud83d\ude41<\/span><\/p>\n<h2><span class=\"ez-toc-section\" id=\"Making_the_App_Look_Good\"><\/span>Making the App Look Good<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Let\u2019s start by adding a nice background to our app. First download the image from <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\/blob\/master\/background.png\" target=\"_blank\" rel=\"noopener\">here<\/a> and save it to your project folder. Then replace the root <code>&lt;View&gt;<\/code> with an <code>&lt;Image&gt;<\/code> component (also be sure to include the <code>Image<\/code> component at the beginning of the file):<\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;Image source={require('.\/background.png')} style={styles.container}&gt;\r\n\u2026\r\n&lt;\/Image&gt;\r\n<\/pre>\n<p>Update the <code>container<\/code> style to this:<\/p>\n<pre class=\"theme:github lang:js decode:true\">container: {\r\n    flex: 1,\r\n    padding: 15,\r\n    backgroundColor: '#fff',\r\n    alignItems: 'center',\r\n    justifyContent: 'space-between',\r\n    width: null,\r\n    height: null\r\n}\r\n<\/pre>\n<p>Now, let\u2019s take care of the button. We will remove the <code>&lt;Button&gt;<\/code> component because it\u2019s not as customizable as we need and replace it with a <code>&lt;TouchableOpacity&gt;<\/code> (don\u2019t forget to include this component too and remove the <code>&lt;Button&gt;<\/code> from the includes because we will not use it anymore). Also get the button background image from <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\/blob\/master\/button.png\" target=\"_blank\" rel=\"noopener\">here<\/a>.<\/p>\n<pre class=\"theme:github lang:js decode:true\">&lt;TouchableOpacity onPress={this.generateRandomNumber}&gt;\r\n    &lt;Image style={styles.button} source={require('.\/button.png')}&gt;\r\n        &lt;Text style={styles.buttonText}&gt;Generate!&lt;\/Text&gt;\r\n    &lt;\/Image&gt;\r\n&lt;\/TouchableOpacity&gt;<\/pre>\n<p>Next we will use some styling for the rest of the components, here is all the <code>render()<\/code> code and <code>styles<\/code>:<\/p>\n<pre class=\"theme:github lang:default decode:true\">render() {\r\n    return (\r\n        &lt;Image source={require('.\/background.png')} style={styles.container}&gt;\r\n            &lt;Text style={styles.textTitle}&gt;Random Numbers&lt;\/Text&gt;\r\n            &lt;Text style={styles.text}&gt;Pool of numbers:&lt;\/Text&gt;\r\n            &lt;Text style={styles.text}&gt;{this.state.pool}&lt;\/Text&gt;\r\n            &lt;Slider \r\n                style={styles.slider}\r\n                minimumValue={1}\r\n                maximumValue={100}\r\n                onValueChange={(value) =&gt; this.setState({pool: Math.round(value)})}\r\n                minimumTrackTintColor=\"#a0a0a0\"\r\n                maximumTrackTintColor=\"#a0a0a0\"\r\n                thumbTintColor=\"#ff0000\"\r\n                thumbImage={require('.\/thumb.png')}\r\n            \/&gt;\r\n            &lt;Text style={styles.resultText}&gt;{this.state.random}&lt;\/Text&gt;\r\n            &lt;Picker\r\n                selectedValue={this.state.amount}\r\n                style={styles.picker}\r\n                itemStyle={styles.pickerItem}\r\n                onValueChange={(itemValue, itemIndex) =&gt; this.setState({amount: itemValue})}&gt;\r\n                &lt;Picker.Item label=\"1\" value=\"1\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"2\" value=\"2\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"3\" value=\"3\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"4\" value=\"4\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"5\" value=\"5\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"6\" value=\"6\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"7\" value=\"7\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"8\" value=\"8\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"9\" value=\"9\" color=\"#FF6600\" \/&gt;\r\n                &lt;Picker.Item label=\"10\" value=\"10\" color=\"#FF6600\" \/&gt;\r\n            &lt;\/Picker&gt;\r\n            &lt;TouchableOpacity onPress={this.generateRandomNumber}&gt;\r\n                &lt;Image style={styles.button} source={require('.\/button.png')}&gt;\r\n                    &lt;Text style={styles.buttonText}&gt;Generate!&lt;\/Text&gt;\r\n                &lt;\/Image&gt;\r\n            &lt;\/TouchableOpacity&gt;\r\n        &lt;\/Image&gt;\r\n    );\r\n}<\/pre>\n<pre class=\"theme:github lang:js decode:true\">const styles = StyleSheet.create({\r\n    container: {\r\n        flex: 1,\r\n        padding: 15,\r\n        backgroundColor: '#fff',\r\n        alignItems: 'center',\r\n        justifyContent: 'space-between',\r\n        width: null,\r\n        height: null\r\n    },\r\n    textTitle: {\r\n        color: '#ffffff',\r\n        backgroundColor: '#00000000',\r\n        fontSize: 28\r\n    },\r\n    text: {\r\n        color: '#ffffff',\r\n        backgroundColor: '#00000000'\r\n    },\r\n    resultText: {\r\n        color: '#ffffff',\r\n        backgroundColor: '#00000000',\r\n        fontSize: 18\r\n    },\r\n    slider: {\r\n        width: '100%'\r\n    },\r\n    picker: {\r\n        width: '100%',\r\n        backgroundColor: '#000000C0',\r\n        borderRadius: 10,\r\n        borderWidth: 2,\r\n        borderColor: '#000000'\r\n    },\r\n    pickerItem: {\r\n        color: '#ffffff'\r\n    },\r\n    button: {\r\n        flexDirection: 'row',\r\n        alignItems: 'center',\r\n        justifyContent: 'center',\r\n        width: 175,\r\n        height: 60\r\n    },\r\n    buttonText: {\r\n        color: '#ffffff',\r\n        fontWeight: 'bold',\r\n        backgroundColor: '#00000000'\r\n    }\r\n});<\/pre>\n<p>You will also need the slider thumb images from <a href=\"https:\/\/github.com\/dragosholban\/RandomNumbersRN\/blob\/master\/thumb.png\" target=\"_blank\" rel=\"noopener\">here<\/a>\u00a0and <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\/blob\/master\/thumb%402x.png\" target=\"_blank\" rel=\"noopener\">here<\/a>.<\/p>\n<p>If you run the app now, you will find a much better interface:<\/p>\n<p><img decoding=\"async\" class=\"size-medium wp-image-2665 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.42.23-169x300.png\" alt=\"\" width=\"169\" height=\"300\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.42.23-169x300.png 169w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.42.23.png 562w\" sizes=\"(max-width: 169px) 100vw, 169px\" \/><\/p>\n<p><span style=\"font-weight: 400;\">The images used in this tutorial were downloaded from pixabay.com then edited using Photoshop:<\/span><\/p>\n<ul>\n<li><a href=\"https:\/\/pixabay.com\/en\/cube-play-random-luck-points-1979775\/\" target=\"_blank\" rel=\"noopener\">https:\/\/pixabay.com\/en\/cube-play-random-luck-points-1979775\/<\/a><\/li>\n<li><a href=\"https:\/\/pixabay.com\/en\/button-click-hit-web-element-2155595\/\" target=\"_blank\" rel=\"noopener\">https:\/\/pixabay.com\/en\/button-click-hit-web-element-2155595\/<\/a><\/li>\n<li><a href=\"https:\/\/pixabay.com\/en\/buttons-gloss-round-circle-colors-150235\/\" target=\"_blank\" rel=\"noopener\">https:\/\/pixabay.com\/en\/buttons-gloss-round-circle-colors-150235\/<\/a><\/li>\n<\/ul>\n<h2><span class=\"ez-toc-section\" id=\"Getting_Your_App_Ready_to_Be_Published\"><\/span>Getting Your App Ready to Be Published<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>So our app is done, how do we publish it to the AppStore and Google Play Store?<\/p>\n<p>First, let&#8217;s fix one small problem: if you rotate your emulator screen (Cmd+Left or Right Arrow) you will see that the app will go into landscape and it will not be usable anymore \ud83d\ude41<\/p>\n<p><img decoding=\"async\" class=\"size-medium wp-image-2667 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.47.16-300x169.png\" alt=\"\" width=\"300\" height=\"169\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.47.16-300x169.png 300w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.47.16-768x432.png 768w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Simulator-Screen-Shot-18-Jul-2017-19.47.16.png 1000w\" sizes=\"(max-width: 300px) 100vw, 300px\" \/><\/p>\n<p>Too lock the app to portrait we need to go &#8220;native&#8221;.<\/p>\n<p>For iOS, open xCode then open the project found in the randomNumbers\/ios folder. Select the project in the left pane then, under Deployment Info, uncheck Landscape Left and Landscape Right Device Orientation so we are only left with the Portrait orientation.<\/p>\n<p>For Android, you can just open the android\/app\/src\/AndroidManifest.xml and add\u00a0<code>android:screenOrientation=\"portrait\"<\/code> under the <code>activity<\/code> section:<\/p>\n<pre class=\"theme:github lang:default decode:true\">&lt;activity\r\n    android:name=\".MainActivity\"\r\n    android:label=\"@string\/app_name\"\r\n    android:configChanges=\"keyboard|keyboardHidden|orientation|screenSize\"\r\n    android:screenOrientation=\"portrait\"\r\n    android:windowSoftInputMode=\"adjustResize\"&gt;\r\n    &lt;intent-filter&gt;\r\n        &lt;action android:name=\"android.intent.action.MAIN\" \/&gt;\r\n        &lt;category android:name=\"android.intent.category.LAUNCHER\" \/&gt;\r\n    &lt;\/intent-filter&gt;\r\n&lt;\/activity&gt;<\/pre>\n<p>&nbsp;<\/p>\n<p>Now, to see those changes, you have to relaunch the app again. Not just reload, relaunch with the <code>react-native run-ios<\/code> or <code>react-native run-android<\/code> commands and try to rotate the emulator. Everything should be fine this time.<\/p>\n<p>Now back to our main task, getting the app ready to be published.<\/p>\n<h3>iOS<\/h3>\n<p>First let&#8217;s add the app&#8217;s icons. Open the xCode project and select Images.xcassets from the left panel. Then select the AppIcon item and drag each icon image to its corresponding placeholder. Download the icons from <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\/tree\/master\/ios\/RandomNumbers\/Images.xcassets\/AppIcon.appiconset\" target=\"_blank\" rel=\"noopener\">here<\/a>.<\/p>\n<p><img decoding=\"async\" class=\"size-large wp-image-2673 aligncenter\" src=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-19-at-08.54.27-1024x598.png\" alt=\"\" width=\"525\" height=\"307\" srcset=\"https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-19-at-08.54.27-1024x598.png 1024w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-19-at-08.54.27-300x175.png 300w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-19-at-08.54.27-768x449.png 768w, https:\/\/intelligentbee.com\/blog\/wp-content\/uploads\/2017\/07\/Screen-Shot-2017-07-19-at-08.54.27.png 1392w\" sizes=\"(max-width: 525px) 100vw, 525px\" \/><\/p>\n<p>When you&#8217;re done, select Product -&gt; Archive from the menu to build the iOS package (it only works with a Generic iOS Device selected or a real device, no emulators).<\/p>\n<h3>Android<\/h3>\n<p>To add app icons in Android, you have to put them in the <code>android\/app\/src\/main\/res\/mipmap*<\/code> folders (overwrite the existing <code>ic_launcher.png<\/code>). You can get the icons from <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\/tree\/master\/android\/app\/src\/main\/res\" target=\"_blank\" rel=\"noopener\">here<\/a>.<\/p>\n<p>Now you need to generate a\u00a0signing key then a signed APK. I found the walkthrough from the React Native documentation to be pretty good so you just follow it:\u00a0<a href=\"https:\/\/facebook.github.io\/react-native\/docs\/signed-apk-android.html\" target=\"_blank\" rel=\"noopener\">https:\/\/facebook.github.io\/react-native\/docs\/signed-apk-android.html<\/a><\/p>\n<h2><span class=\"ez-toc-section\" id=\"Final_Words\"><\/span>Final Words<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>That&#8217;s it! You now have your first React Native application ready to be sent into the wild. I hope you had fun doing this, please let us know in the comments how it worked for you. Oh, and you can find the final code <a href=\"https:\/\/github.com\/intelligentbee\/RandomNumbersRN\" target=\"_blank\" rel=\"noopener\">here<\/a>.<\/p>\n<p>Have a nice mobile developer life! \ud83d\ude42<\/p>\n","protected":false},"excerpt":{"rendered":"<p>React Native is a framework for building native apps using React made by Facebook. With React Native, you don&#8217;t build [&hellip;]<\/p>\n","protected":false},"author":3,"featured_media":2685,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[75,80,83],"tags":[],"yst_prominent_words":[1193,2117,1201,1200,1199,1198,1197,1196,1195,1194,273,1192,1191,1190,1100,1065,537,426,300],"post_mailing_queue_ids":[],"_links":{"self":[{"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/posts\/2623"}],"collection":[{"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/users\/3"}],"replies":[{"embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/comments?post=2623"}],"version-history":[{"count":2,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/posts\/2623\/revisions"}],"predecessor-version":[{"id":75288,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/posts\/2623\/revisions\/75288"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/media\/2685"}],"wp:attachment":[{"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/media?parent=2623"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/categories?post=2623"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/tags?post=2623"},{"taxonomy":"yst_prominent_words","embeddable":true,"href":"https:\/\/intelligentbee.com\/blog\/wp-json\/wp\/v2\/yst_prominent_words?post=2623"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}