How to make a default page in React Native? - javascript

Why I have index.android.js as default. How I can make a home.js as default?

When your platform-specific code is more complex, you should consider splitting the code out into separate files. React Native will detect when a file has a .ios. or .android. extension and load the relevant platform file when required from other components.
see: https://facebook.github.io/react-native/docs/platform-specific-code.html#platform-specific-extensions
so if you add .android.js or .ios.js to your extension RN will pick one of them based on the platform. If you want the same component for both platform just don't add platform specific extension and use just foo.js

I think what you asked for can be done this way:
import { AppRegistry } from 'react-native';
import Home from './path/to/home';
AppRegistry.registerComponent('SBlank', () => Home);
By doing this in both your index.android.js and index.ios.js you redirect your app to Home.js file.
Bonus: In addition to knowbody's answer, you can use Platform object to change how your code works on different platforms. For example:
render() {
if (Platform.OS === 'android') {
return this.renderAndroid();
}
return this.renderIOS();
}
where you import Platform by adding
import { Platform } from 'react-native';

Related

Office Add-ins excel extension is not working on IE11 with 'import axios' statement

I'm currently developing a Excel extension for my company with Office Add-ins and Reactjs.
Lately I've been using Axios in order to make http requests to get data from a remote back-end service. The issue is that the statement "import axios from 'axios'" is not handled in IE11 and the application runs into an exception when this statement is present in a script file. The exception is :
Office.js has not fully loaded. Your app must call "Office.onReady()" as part of it's loading sequence (or set the "Office.initialize" function). In itself that doesn't say a lot except that "the code does not compile".
After a few researches on my own I discovered that IE11 needs polyfill in order to make it work since it doesn't natively support the most recent js scripts (ES6, promises by example).
I've tried many kinds of combinations with babel/polyfill, react-app-polyfill, es-promise with no result so far. Happily, in a another application I've been working on recently (VueJs with axios), I met the same problem and just adding 'import babel/polyfill' did the trick.
I would like to know if anyone has succeeded in doing what I am trying to do for a few days and if not, any help will be appreciated. Some of my coworkers are using Windows 7 or Windows Server 2019 and I really need this excel extension to function with IE11.
Thank you for your help.
Edit on 06/29 :
Here is what I have in my index.js :
import "office-ui-fabric-react/dist/css/fabric.min.css";
import App from "./components/App";
import { AppContainer } from "react-hot-loader";
import { initializeIcons } from "office-ui-fabric-react/lib/Icons";
import * as React from "react";
import * as ReactDOM from "react-dom";
/* global AppCpntainer, Component, document, Office, module, React, require */
initializeIcons();
let isOfficeInitialized = false;
const title = "Contoso Task Pane Add-in";
const render = Component => {
ReactDOM.render(
<AppContainer>
<Component title={title} isOfficeInitialized={isOfficeInitialized} />
</AppContainer>,
document.getElementById("container")
);
};
Office.initialize = () => {
isOfficeInitialized = true;
render(App);
};
render(App);
if (module.hot) {
module.hot.accept("./components/App", () => {
const NextApp = require("./components/App").default;
render(NextApp);
});
}
commands.js : You can see that I have a commented import statement in this file regarding axios. My intent is to make it work in the dataservice instead but I put that statement here just for testing purpose. The dataservice class itself has only one dependency : axios.
import "babel-polyfill";
// import axios from 'axios';
import DataService from '../server/dataservice';

React PWA - enforce update on click

community,
I am doing "programmatic presentations" using React (CLI) and PWA (register()). Everything works just fine, but anytime some changes are made, the URL of the final app needs to be changed so all changes are loaded.
The whole mechanism works like this:
The final app is sent to Github,
this private repo is connected to Netlify,
Netlify generates a unique URL,
users visit this Netlify URL and hit "add to home screen" on iPad,
the whole app runs under the Safari engine.
If any change in the code is made, I have to change the link in Netlify and send this new link to a people.
The process mentioned above works just fine, but honestly, it would be nice to have some kind of functionality that allows request latest update on demand - let's say - on click of a button.
Is something like that possible?
Thank you for comments!
Kind Regards
Linc
At serviceWorker.js file can find this code
if (config && config.onUpdate) {
config.onUpdate(registration);
}
So implement the config.onUpdate funtion
Create a file swConfig.js
export default {
onUpdate: registration => {
registration.unregister().then(() => {
window.location.reload()
})
},
}
At index.js send the implement function to serviceWorker
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';
import * as serviceWorker from './serviceWorker';
import swConfig from './swConfig'
ReactDOM.render(<App />,
document.getElementById('root'));
serviceWorker.register(swConfig);
Check out this repo
https://github.com/wgod58/create_react_app_pwaupdate
If you want to control the update with a button click, I did using the following snippet:
Note: If your app must work offline, you should add some extra logic to verify if the user has internet connection, as the following code would break the app if it's unable to fetch the service-worker.
import React from 'react';
function App(){
const updateApp = () => {
if ('serviceWorker' in navigator) {
navigator.serviceWorker.ready.then((registration) => {
registration.unregister().then(() => {
window.location.reload();
});
});
}}
return(
<div style={{margin:"auto"}}>
<button onClick={updateApp}>
Update App
</button>
</div>
);
}
https://gist.github.com/juliomilani/6492312d1eb657d06b13c9b87d5ad023

Import typescript files based on naming convention in React Native

So I have three ts files named as below :
MyModule.ios.ts
MyModule.android.ts
MyModule.ts ( this is empty )
first two files have a method named : setup() which need to run based on platform Also metro bundler will do the resolution, it will try to import .ios when building for ios and .android when building for android..
and I have another file which import this method like this :
import { setup } from 'MyModule';
the problem is, I am not sure if this will resolve the .android and .ios files. What is the proper way to do this kind of code splitting?
I find this workaround here but I was wondering if there is a better way : https://github.com/Microsoft/TypeScript/issues/8328#issuecomment-219583152
If you want to use separate files for iOS and Android, you need to call them MyModule.ios.ts and MyModule.android.ts extensions. The empty MyModule.ts file is not necessary.
Then just import them as if they didn't have the platform specific extensions. React Native will automatically pick up the right file based on the running platform.
import { setup } from './MyModule'; // Will automatically import either MyModule.ios.ts or MyModule.android.ts
See the documentation on this: https://facebook.github.io/react-native/docs/platform-specific-code.html#platform-specific-extensions
If you don't want to use separate files, you can use the Platform module. This is nice for small pieces of code that you want to make platform specific.
import { Platform } from 'react-native';
if(Platform.OS === 'ios') {
// iOS specific code here
} else if(Platform.OS === 'android') {
// Android specific code here
} else {
// Other platform
}
See: https://facebook.github.io/react-native/docs/platform-specific-code#platform-module

How to import node module in React-Kotlin?

I created an app using the create-react-kotlin-app command and it loads in Chrome fine. I added the React Material UI package via NPM and that was successful. Now how do I use the Material UI module in my component?
Normally with JavaScript, it's a simple import Button from '#material-ui/core/Button' at the top of the component's file, but Kotlin doesn't like that.
How do I translate that line to Kotlin? I am not using Gradle.
I have been struggling with this problem for days now. I came up with the following solution. First we will see multiple ways to declare external modules, then I will show how to use them
.
Consider the following javascript code
import Button from '#material-ui/core/Button' // this means button is exported as default
This will be imported in kotlin in the following ways
Button.kt
#file:JsModule("#material-ui/core/Button")
#file:JsNonModule
package com.mypckage.mykillerapp
import react.Component
import react.RProps
import react.RState
import react.ReactElement
#JsName("default") // because it was exported as default
external val Button : RClass<RProps>
// way 2
#JsName("default")
external class Button : Component<RProps,RState> {
override fun render(): ReactElement?
}
But again, if the statement intend for kotlin has to match the javascript import statement bellow,
import { Button } from "material-ui" // not exported as default
We use the following approach: Button.kt
#file:JsModule("material-ui")
#file:JsNonModule
package com.mypckage.mykillerapp
import react.Component
import react.RProps
import react.RState
import react.ReactElement
// way 1
#JsName("Button") // because it was exported as default
external val Button : RClass<RProps>
// way 2
#JsName("Button")
external class Button : Component<RProps,RState> {
override fun render(): ReactElement?
}
once you have declared on how to use your components, you can just use them as follows:
//way 1:
fun RBuilder.render() {
div {
Button {
attrs.asDynamic().className="submit-button"
+"Submit"
}
}
}
//way 2:
fun RBuilder.render() {
div {
child(Button::class) {
attrs.asDynamic().className="submit-button"
+"Submit"
}
}
}
great. you have imported your component. But until then your are not relying on kotlin type safety and even code completion, to achieve that, you have to go to extra length
as shown bellow
external interface ButtonProps: RProps {
var className : String
var onClick: (Event?)->Unit
var color: String
// . . .
var href: String
}
then go ahead and declare your button as
#JsModule("#material-ui/core/Button")
#JsNonModule
#JsName("default") // because it was exported as default
external val Button : RClass<ButtonProps>
and you can now use it with type safety and code completion as shown bellow
fun RBuilder.render() {
div {
Button {
attrs {
className = "submit-button"
onClick = {
window.alert("Vois La")
}
}
+"Submit"
}
}
}
Hope this helps. Happy coding
EDIT:
There is a community wrapper for material-ui components here
HINT:
Use way 1, as you can see, it is less verbose
The Kotlin way for importing dependencies is close to standard JS importing:
import React from 'react';
export function Welcome(props) {
return <h1>Hello, {props.name}</h1>;
}
Based on Creating a simple React component with Kotlin.
package hello
import react.*
import react.dom.*
fun RBuilder.hello(name: String) {
h1 {
+"Hello, $name"
}
}
Usually (as Kotlin is Java-based) it uses Gradle tool to handle dependencies:
// part of build.gradle
kotlinFrontend {
// ...
npm {
// ...
dependency("react")
dependency("react-dom")
dependency("react-router")
dependency("react-markdown")
devDependency("css-loader")
devDependency("babel-core")
// ...
}
And are referenced like above:
HomeView.kt:
// https://github.com/Kotlin/kotlin-fullstack-sample/blob/master/frontend/src/org/jetbrains/demo/thinkter/HomeView.kt
import kotlinx.html.*
import org.jetbrains.demo.thinkter.model.*
import react.*
import react.dom.*
import kotlinx.coroutines.experimental.launch
ReactMarkdown.kt:
// https://github.com/Kotlin/kotlin-fullstack-sample/blob/master/frontend/src/org/jetbrains/demo/thinkter/ReactMarkdown.kt
package org.jetbrains.demo.thinkter
import react.*
private val ReactMarkdown: dynamic = runtime.wrappers.require("react-markdown")
Based on: kotlin-fullstack-sample
In create-react-kotlin-app additionally faced the possibility of importing with #JsModule() annotation, while dependencies managing is handled in standard way via package.json:
// src/logo/Logo.kt (outcome of creating new app)
package logo
import react.*
import react.dom.*
import kotlinext.js.*
import kotlinx.html.style
#JsModule("src/logo/react.svg")
external val reactLogo: dynamic
#JsModule("src/logo/kotlin.svg")
external val kotlinLogo: dynamic
And can be also successfully used for JS libraries importing.
Another way would be to use kotlinext.js.*:
// index/index.kt
import kotlinext.js.*
fun main(args: Array<String>) {
requireAll(require.context("src", true, js("/\\.css$/")))
// ...
}
Which provides also require(module: String) function.

How to resolve module name conflict in react native

I have two module with the exact same name that belongs to two different apps, these two module are functionally quite similar except for the styling. I am creating a master component and try to import these two different module based on what app I am currently in.
I wonder if there is a way to conditionally import the module that I don't have to hard code a name space for the module, like module_app1 and module_app2 but instead to do
if (cond) {
import module from 'path1';
} else {
import module from 'path2';
}
I use 'as'. Example:
import Actions from '../actions';
import { Actions as Navigator } from 'react-native-router-flux';

Categories

Resources