web-dev-qa-db-ja.com

ToolkitAndroidを介してDrawerLayoutAndroidを表示=> onIconClicked

私はReactネイティブ(およびReact)に不慣れで、少し遊んでいます。

画面の左側からドラッグできるDrawerLayoutを追加することができました。ただし、ToolbarAndroidのメニューアイコンをクリックしたときに開きたいのですが。

「refs」を使おうとしましたが、うまくいかないようです

私は十分に明確であることを願っています。

ありがとうございました

18
Maslow

あなたが述べたようにあなたは「refs」を使うべきです。これを行うには、ドロワーコンポーネントに「ref」属性を設定します。

<DrawerLayoutAndroid
   ...
   ref={'DRAWER_REF'}
   ...
/>

次に、コンポーネントでthis.refsを使用してアクセスし、その参照でopenDrawerまたはcloseDrawerを呼び出します(たとえば、この呼び出しをトリガーするTouchable要素が必要な場合があります)::

this.refs['DRAWER_REF'].openDrawer();
33
kzzzf

ReactNativeサンプルを使用すると、次のように実行できます。

var DrawerTest = React.createClass({
  openDrawer:function() {
    this.refs['DRAWER'].openDrawer()
  },
  render: function() {
    var navigationView = (
        <View style={{flex: 1, backgroundColor: '#fff'}}>
          <Text style={{margin: 10, fontSize: 15, textAlign: 'left'}}>I'm in the Drawer!</Text>
        </View>
    );
    return (
          <DrawerLayoutAndroid
              drawerWidth={300}
              ref={'DRAWER'}
              drawerPosition={DrawerLayoutAndroid.positions.Left}
              renderNavigationView={() => navigationView}>
            <View style={{flex: 1, alignItems: 'center'}}>
              <Text style={{margin: 10, fontSize: 15, textAlign: 'right'}}>Hello</Text>
              <Text style={{margin: 10, fontSize: 15, textAlign: 'right'}}>World!</Text>
              <TouchableHighlight onPress={this.openDrawer}>
                <Text>{'Open Drawer'}</Text>
              </TouchableHighlight>
            </View>
          </DrawerLayoutAndroid>
    );

  }
});

完全なファイルの要点

8
Tiago Gouvêa

特にナビゲーターを使用してシーンをレンダリングする場合は、別のソリューションを追加したいだけです。

この場合、上記のソリューションはDrawerLayoutAndroidで指定されたrefにアクセスできないため機能せず、実際には

"undefined is not an object (evaluating 'this.refs['DRAWER_REF']')"

またはそのようなもの。

解決:

独自のツールバーを作成して、レンダリングコンポーネントをツールバーに渡すことができるようにします。

MyToolbar.js

... import stuff ...

module.exports = React.createClass({
  render: function() {
    return (
      <ToolbarAndroid
        title={this.props.title}
        navIcon = {{uri: "ic_menu_white_24dp", isStatic: true}}
        style = {styles.toolbar}
        titleColor='#FFFFFF'
        onIconClicked={this._onIconClicked}/>
    );
  },

  _onIconClicked: function(){
    this.props.sidebarRef.refs['DRAWER'].openDrawer();
    // sidebarRef is the rendering component we're passing
  }
});

OpenDrawerFromToolbar.js

...
module.exports = React.createClass({
  render: function() {
    var navigationView = (
      <View style={{flex: 1, backgroundColor: '#fff'}}>
        <Text style={{margin: 10, fontSize: 15, textAlign: 'left'}}>In the Drawer!</Text>
      </View>
    );

    return (
      <View style={styles.container}>
        <DrawerLayoutAndroid drawerWidth = {300}
                         drawerPosition = {DrawerLayoutAndroid.positions.Left}
                         renderNavigationView = {() => navigationView}
                         ref={'DRAWER'}>
        <MyToolbar style={styles.toolbar}
                   title={'My Awesome App'}
                   navigator={this.props.navigator}
                   sidebarRef={this}/> // pass the component to MyToolbar
        <View style = {{flex: 1, alignItems: 'center'}}>
          <Text style = {{margin: 10, fontSize: 15, textAlign: 'right'}}>Hello</Text>
          <Text style = {{margin: 10, fontSize: 15, textAlign: 'right'}}>World!</Text>
        </View>
      </DrawerLayoutAndroid>
    </View>
  );
  },

  _setDrawer: function() {
    this.refs['DRAWER'].openDrawer();
  }
});

次に、renderingScene関数を備えたナビゲーターコンポーネントが機能します。

module.exports = React.createClass({
  render: function() {
    return (
      <Navigator
        style = {styles.container}
        initialRoute = {{ name: 'openDrawerFromToolbar', index: 0 }}
        renderScene = {this.navigatorRenderScene}
        configureScene={ () => { return Navigator.SceneConfigs.PushFromRight; }}/>
  );
},

navigatorRenderScene: function(route, navigator) {
  _navigator = navigator;
      return (
          <OpenDrawerFromToolbar
            route={route}
            navigator={navigator}
            data={route.data}/>
      );
  }
});
2
Fadils

"undefined is not a object"-私たちのほとんどは、上記の解決策でここに行き着きました。

以下に説明するように、ES6構文が正しく使用されていることを確認してください。

構文が正しくありません:

onPress={this.drawer()}

正しい構文:

onPress={() => this.drawer()}

コード:

<DrawerLayoutAndroid
   ...
   ref={'DRAWER_REF'}
   ...
/>

--------------------------------------------------

//Write this just before render() method

drawer = () => {
  this.refs['DRAWER_REF'].openDrawer();
}

--------------------------------------------------

<TouchableHighlight onPress={() => this.drawer()}>
   <Icon name="bars" size={30} color="#900"/>
</TouchableHighlight>
1
Edison D'souza

これらすべてのスニペットをたどっても、undefined is not an objectエラーが発生します。

次に、GitHubで このスレッド が見つかりました。これは最終的に私の問題を解決し、refsの問題を完全に説明しています。

Reactネイティブドキュメント( http://facebook.github.io/react-native/docs/drawerlayoutandroid.html )のDrawerLayoutAndroidの例に従うには=)、これは機能するコードです:

constructor() {
  super();
  this.openDrawer = this.openDrawer.bind(this);
} 

openDrawer() {
  this.drawer.openDrawer();
}

render() {
  var navigationView = (
    <View style={{flex: 1, backgroundColor: '#fff'}}>
      <Text style={{margin: 10, fontSize: 15, textAlign: 'left'}}>I'm in the Drawer!</Text>
    </View>
  );
  return (
    <DrawerLayoutAndroid
      drawerWidth={300}
      ref={(_drawer) => this.drawer = _drawer}
      drawerPosition={DrawerLayoutAndroid.positions.Left}
      renderNavigationView={() => navigationView}>
      <View style={{flex: 1, alignItems: 'center'}}>
        <Text style={{margin: 10, fontSize: 15, textAlign: 'right'}}>Hello</Text>
        <Text style={{margin: 10, fontSize: 15, textAlign: 'right'}}>World!</Text>
        <TouchableHighlight onPress={this.openDrawer}>
          <Text>{'Open Drawer'}</Text>
        </TouchableHighlight>
      </View>
    </DrawerLayoutAndroid>
  );
}
0
GuGuss