另一个组件的门户

时间:2019-08-09 15:01:27

标签: javascript reactjs

我在官方网站上找到了此example,其中描述了如何使用portal。在此示例中,正在使用ReactDOM.createPortal()为模态创建新的'root' div。有没有一种方法可以将组件传送到另一个组件(不仅仅是根)。

使用portal可能无法完成-我只是认为它可能对这种解决方案有用


我正在尝试使用对MyComponentA或MyComponentB具有逻辑依赖性的按钮“扩展”导航(不同的按钮,不同的行为由不同的组件控制,但位于导航的DOM中)。

这是我要实现的目标的简化示例:

应用

这是我的应用程序的根组件,其中包括导航,MyComponentA和MyComponentB

class App extends React.Component {
   render() {
       return (
          <Navigation/>
          <MyComponentA/>
          <MyComponentB/>
       );
    }
}

导航

这是我要放置门户输出的组件。

class Navigation extends React.Component {
   render() {
      return (
         <OutputOfPortal>
            {/* I want to teleport something here from another component */}
         </OutputOfPortal>
      );
   }
}

MyComponentA

这是我要放置门户源的组件。与MyComponentB相同,但内容不同。

class MyComponentA extends React.Component {
   render() {
      return (
         {/* Another code */}
         <InputOfPortal>
            {/* I want to teleport something from here to navigation */}
            <button onClick={this.functionInThisComponent}> click me </button>
         </InputOfPortal>
         {/* Another code */}
      );
   }
}

2 个答案:

答案 0 :(得分:0)

  • 我认为您忘记使用 render()方法
  • 如果我无法正确理解自己想要的https://www.npmjs.com/package/react-router-dom
  • ,则必须使用react router dom
  • 并且您必须使用道具,并使用react router dom发送道具
  • 通常,您使用布局页面在其中放置导航栏,然后在同一页面中添加 props.childern 以在导航栏下方呈现页面

    import React, { Component } from "react";
    import NavBar from "./NavBar"
    class Layout extends Component {
    constructor(props){
    super(props);
    }
    
    render(){
    return (
      <div>
          <NavBar/>
    
      <div className="container">
        {this.props.children}
      </div>
    
    
      </div>
    
    );
    }}
    
    export default Layout;
    
  • 这是reacr路由器dom的示例

     import React, { Component } from 'react';
     import Layout from "./components/layout/Layout"
     import { Switch,Route } from "react-router-dom";
     import DashBoard from './components/dashboard/DashBoard'
     import ShopDetails from './components/shops/ShopDetails'
     import SignIn from './components/auth/SignIn'
     import CreateShop from './components/shops/CreateShop'
     import CreateProduct from './components/shops/CreateProduct'
     import './App.css';
    
     class App extends Component { 
        render(){
          const route=(
           <Switch>
              <Route exact path="/" component={DashBoard} />
              <Route path="/shop/:id" component={ShopDetails} />
              <Route  path="/signin" component={SignIn} />
              <Route  path="/createshop" component={CreateShop} />
              <Route  path="/createproduct" component={CreateProduct} />
              {/* <Route  path="/login" component={Login} />
             <Route  path="/shoppage" component={ShopPage} /> */}
          </Switch>
        )
      return (
      <Layout>
        {route}
      </Layout>);}}
    export default App;
    

之后,您便可以按照自己的路线去到想要的路线 一些像localhost3000 / 本地主机3000 /登录 本地主机3000 / user /:id

答案 1 :(得分:0)

我已将ID navigation-controls设置为Navigation中的元素。比起我,我创建了另一个名为NavigationExtension的组件,该组件用作Navigation的门户。该门户网站的每个子级都将其功能保留在创建它的原始组件中。

导航

我刚刚在要传送的地方创建了div,其ID为

class Navigation extends React.Component {
   render() {
      return (
        // some code ... 
        <div id="navigation-controls">
            // some buttons ... 
        </div>
        // some code ...
      );
   }
}

NavigationExtension

这将传送包裹在导航中的任何东西

class NavExtension extends React.Component
{
    el = document.createElement("div");

    componentDidMount() {
        // nav element is selected here by id
        this.targetEl = document.getElementById("navigation-controls");
        this.targetEl.appendChild(this.el);
    }

    componentWillUnmount() {
        this.targetEl.removeChild(this.el);
    }

    render() {
        return ReactDOM.createPortal(
            <React.Fragment>
                {this.props.children}
            </React.Fragment>, this.el);
    }
}

MyComponentA

最后声明我的按钮并将其传送到导航。

class MyComponentA extends React.Component {
   render() {
      return (
         // some code ...
         <NavigationExtension>
            <button onClick={this.functionInThisComponent}> I'm in navigation! </button>
         </NavigationExtension>
         // some code ...
      );
   }
}

我不确定我是否不明白其他答案,但这正是我想要的。