React Native:页面跳转传值_react native startactivityforresult-程序员宅基地

技术标签: 页面跳转传值  react-native  native  react  

在app开发中,跳转页面的需求是最常见的。
Android原生跳转可以使用startActivityForResult、startActivity实现…
但是在React Native中呢?
作为得到前端青睐的React Native,使用Navigator结合路由的方式进行跳转。路由其实很好理解,就是一个url映射到具体的函数。
比如说:

# flask框架
@app.route("/login")
def login():
    # 只要是/login的网址,就会跳进这个函数

// Spring
@RequestMapping("/login")
public void login() {
    // 只要是/login的网址,就会跳进这个函数
}

例子太多太多了。。。其实,Android开发框架——Router、LiteRouter等等都是以路由的方式实现原生Android界面跳转。

扯远了,这里开始真正的学习React Native界面跳转。这里需要了解一个Navigator这个api了。
需要说明的是,我们需要先定义一个没有任何界面的Component,并在这个Component初始化Navigator。

// SplashComponent.js
class SplashComponent extends Component {
    

    constructor(props) {
        super(props);
    }

    render() {
        // 这里定义第一个界面的name和对应的Component
        const defaultName = "LoginComponent";
        const defaultComponent = LoginComponent;

        return (
            <Navigator
                // 初始化路由
                initialRoute={
   {name: defaultName, component: defaultComponent}}
                // 配置界面跳转的动画效果
                configureScene={
                    (route) => {
                        return Navigator.SceneConfigs.FloatFromBottom;
                    }
                }
                // 跳转后,渲染界面的函数
                renderScene={
                    (route, navigator) => {
                        let Component = route.component;
                        return <Component{...route.params} navigator={navigator}/>
                    }
                }
            />
        );
    }
}

我们将定义的SplashComponent作为第一个界面。实际上,SplashComponent并没有开始任何的View显示,只是将界面跳转到了LoginComponent。

别忘了这句话

AppRegistry.registerComponent('Animation', () => SplashComponent);

接下来就是LoginComponent的编写了,这里就是一个简单的Text,点击Text后,会跳转到RegisterComponent。

// LoginComponent.js
class LoginComponent extends Component {
    

    constructor(props) {
        super(props);
    }

    render() {
        return (
            <View>
                <Text onPress={
   this.onPress.bind(this)}>点击后跳转到Register</Text>
            </View>
        )
    }

    onPress() {
        const {navigator} = this.props;
        navigator.push({
            name: "RegisterComponent",
            component: RegisterComponent,
            // 传递参数,因为前面初始化Navigator的时候是使用了params,所以这里就用params
            params : {
                string : "login",
            }
        });
    }
}
class RegisterComponent extends Component {
    

    constructor(props) {
        super(props);
        // 这样获取参数
        console.log(props.string);
    }

    render() {
        return (
            <Text onPress={() => {
                const {navigator} = this.props;
                // 将该界面弹出栈
                navigator.pop();
            }}>注册</Text>
        )
    }
}

上面演示了如何在两个界面中传递参数。navigator有两个重要的方法——push、pop。也就是说,本质上React Native有一个保存Scene的栈,通过管理这个栈实现界面的跳转。
但是,我们按下返回键的时候,其实并不会调用Navigator.pop()。个人推测React Native的实现会将所有的Scene都显示在一个Activity上,并不存在Activity的交互,按下返回键才不会弹出Scene。

那我们可以通过监听返回键的方式,实现弹出Scene。参数资料:https://reactnative.cn/docs/0.43/backandroid.html#content

但是,我们通过navigtor.push是相当于实现了startActivity。还没有实现startActivityForResult。
我们可以通过以下方法实现:

    changeData(data) {
        this.setState({
            data : data
        });
    }

    // LoginComponent.js
    // 省略部分代码
    onPress() {
        const {navigator} = this.props;
        navigator.push({
            name: "RegisterComponent",
            component: RegisterComponent,
            params : {
                string : "login",
                // 将回调函数通过参数的形式传递过去
                changeData : changeData
            }
        });
    }
    // RegisterComponent.js
    // 省略部分代码
    const {navigator} = this.props;
    // 在这里调用那个函数
    this.props.changeData("回调");
    navigator.pop();

上述方式通过函数回调的方式解决了Navigator.pop无法传值得问题。这种方法基本解决了很多问题,但是总感觉写一个回调函数是很不妥的方式。

我们还可以通过React Native提供的DeviceEventEmitter的api实现传值。其实DeviceEventEmitter的本质实现是发布者与监听者模式。

// LoginComponent.js
// 省略部分代码
componentDidMount() {
    //这里监听的事件是changeData,监听到后会自动回调changeData函数
    DeviceEventEmitter.addListener('changeData', this.changData);
}

// 这里一定要移除事件的监听,避免内存泄漏
componentWillUnmount() {
    this.subscription.remove();
}
// RegisterComponent.js
// 省略部分代码
// 发布事件
DeviceEventEmitter.emit('changeData',val.data);
navigator.pop();
版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/new_Aiden/article/details/72566640

智能推荐

LLVM学习笔记(33)_selectcodecommon分析-程序员宅基地

文章浏览阅读1.1k次。3.4.4.3.5. OPC_MorphNodeTo等下面的OPC_EmitCopyToReg表示将值拷贝到一个物理寄存器的一个操作,3081行通过目标机器SelectionDAG实例的getCopyToReg()方法在Chain与glue的链上插入CopyToReg的节点。3093行的RunSDNodeXForm()是前面为目标机器生成的执行SDNodeXForm所代表操作的方法。Sel..._selectcodecommon分析

android 生成图片 分享,Android 布局生成分享图片-程序员宅基地

文章浏览阅读419次。package app.makemone.ky.com.testapplication;import android.graphics.Bitmap;import android.graphics.Canvas;import android.os.Environment;import android.util.Log;import android.view.View;import java.io...._android 集成图片生成

【计算机网络】网络通信基础_计算机网络通信基础-程序员宅基地

文章浏览阅读5.1k次,点赞2次,收藏27次。文章目录网络通信基础及网络参考模型网络通信基础网络通信基本概念信息的传递过程数据通信网络基本概念网络设备_计算机网络通信基础

[Python]保姆级win11环境安装Python_[python]保姆级win11环境安装python_魔都吴所谓的博客-csdn博客-程序员宅基地

文章浏览阅读3.5w次,点赞32次,收藏91次。Python环境安装及配置_[python]保姆级win11环境安装python_魔都吴所谓的博客-csdn博客

【通俗易懂】机器学习中 L1 和 L2 正则化的直观解释_正则化参数λ怎么算-程序员宅基地

文章浏览阅读10w+次,点赞180次,收藏908次。L=Ein+λ∑j|wj|L=Ein+λ∑j|wj|L=E_{in}+\lambda\sum_j |w_j|∑jw2j≤C∑jwj2≤C\sum_jw_j^2\leq C∇Ein∇Ein\nabla E_in∇Ein+λw=0∇Ein+λw=0\nabla E_{in}+\lambda w=0∂∂w(12λw2)=λw∂∂w(12λw2)=λw\frac{\partia..._正则化参数λ怎么算

友链-程序员宅基地

文章浏览阅读664次。同届chdystartaidouTyouchieblngmelodyAK-lsmillopeyycdebokegcferBIGBIGPPT神犇zkwbyvoidhzwerPoPoQQQmatrix67yybTangentercdecl学长Cydiaterchty137shoebillsxorexqywytmy_snowingstr..._遗传算法 分组背包

随便推点

FFT抄袭笔记-程序员宅基地

文章浏览阅读86次。你看我都不好意思说是学习笔记了,毕竟\(FFT\)我怎么可能学得会那就写一篇抄袭笔记吧ctrl+c真舒服先从多项式说起吧1.多项式我们定义一个多项式\[F(x)=\sum_{i=0}^{n-1}a_ix^i\]这就是一个\(n-1\)次的多项式了比如说\(F(x)=x^3+2x^2+x+1\)就是一个三次的多项式了我们还可以把多项式理解成函数,比如说上面那个多项式\(F(..._fft代替高斯积分

Linux(CentOS7)下rpm安装MySQL_8.0.25_linux双服务 rpm -ivh mysql-community-common-8.0.25-1.-程序员宅基地

文章浏览阅读649次,点赞3次,收藏2次。Linux(CentOS7)下rpm安装MySQL_8.0.25官网下载安装包,[https://dev.mysql.com/downloads/mysql/]:Red Hat Enterprise Linux 7 / Oracle Linux 7 (x86, 64-bit), RPM(mysql-8.0.25-1.el7.x86_64.rpm-bundle.tar)上传至 CentOS 系统 /usr/local/MySQL 目录下, 没有该目录的话,则先创建[外链图片转存失败,源站可_linux双服务 rpm -ivh mysql-community-common-8.0.25-1.el7.x86_64.rpm

NVIDIA-Jetson Nano SD卡扩容脚本_app partition size-程序员宅基地

文章浏览阅读5.8k次,点赞3次,收藏34次。用户自行烧写完成Jetson Nano的镜像后,需进行SD卡扩容,以完全利用SD卡存储空间。其实Jetson Nano是自带扩容的程序的。脚本路径在/usr/lib/nvidia/resizefs/nvresizefs.sh脚本如下#!/bin/bash# Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved.## Redistribution and use in source and binary forms, w_app partition size

解决 SQLite报错:OperationalError: row value misused-程序员宅基地

文章浏览阅读4.8k次。python操作sqlite时,写了这样一条语句:("""SELECT (content, describe, id) FROM DAILYTASK WHERE needcopy=? AND finish=? AND uid=?""", (1, 0, uid, ))报错:OperationalError: row value misused这个错误的原因是SELECT后面不小心加了括号,删..._row value misused

linuxbingc(进程通信)-程序员宅基地

文章浏览阅读172次。上一篇目录标题前言:为什么进程通信管道(匿名管道)管道符号管道本质管道接口PCB理解管道验证pipe函数结合父子进程管道通信前言:为什么进程通信每一个进程的数据都是存储在物理内存当中,进程通过各自的进程虚拟地址空间进行访问,访问的时候,通过各自的页表的映射关系,访问到物理内存。从进程的角度看,每个进程都认为自己拥有4g(32位)的空间,至于物理内存当中属于如何存储,页表如何映射,进程是不清楚。这也造就了进程的独立性。进程独立性:好处:让每一个进程在运行的时候,都是独立进行运行的,数据不会窜。坏处_bingc

SpringBoot学习总结_springbook课程的总结-程序员宅基地

文章浏览阅读2.3k次。目录1、我的第一个SpringBoot项目创建SpringBoot项目如何修改端口号2、SpringBoot自动装配原理3、yaml语法用yaml赋值配置文件占位符结论:4、JSR303数据校验及多环境切换5、整合JDBC,Druid,Mybatis1.整合JDBC2.整合Druid3.整合Mybatis6、SpringSecurity实验环境搭建认识SpringSecurity认证和授权1.引入 Spring Security 模块._springbook课程的总结