wake-up-neo.com

So beenden Sie die aktuelle Komponente, während Sie zur nächsten Komponente in Reactative navigieren

Hallo, ich versuche mit navigate zur nächsten Komponente zu navigieren. Ich verwende react-navigation für die Navigation zwischen mehreren Komponenten.

Angenommen, ich habe index.Android.js und DashboardScreen.js Komponente. Ich versuche, von der Indexkomponente zu der DashboardScreen.js-Komponente zu navigieren. 

Es navigiert, aber die Indexkomponente bleibt immer im Komponentenstapel. Wenn ich zurück drücke, öffnet sich index.Android.js, was nicht sein sollte. Weiß jemand, wie man dies in react-native verwaltet. In Android funktioniert finish() dafür.

navigate("DashboardScreen");

Wenn ich von SplashScreen zu EnableNotification navigiere, sollte SplashScreen zerstört werden, wenn ich von EnableNotification zu CreateMessage navigiere, sollte EnableNotification zerstört werden und wenn ich von CreateMessage zu DashboardScreen navigiere, dann CreateMessage. Bis jetzt wird keine Komponente zerstört.

index.Android.js

class SplashScreen extends Component {
  render() {
    if (__DEV__) {
      console.disableYellowBox = true;
    }

    const { navigate } = this.props.navigation;

    AsyncStorage.getItem("@ProductTour:key").then(value => {
      console.log(value);
      if (value) {
        navigate("DashboardScreen");
      }
    });

    return (
     ....
    );
  }
}

const App = StackNavigator(
  {
    Splash: {
      screen: SplashScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    },
    EnableNotification: {
      screen: EnableNotificationScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    },
    CreateMessage: {
      screen: CreateMessageScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    },
    DashboardScreen: {
      screen: DashboardScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    }
  },
  {
    initialRouteName: "Splash"
  }
);
14
N Sharma

Verwenden Sie einfach 'ersetzen' anstelle von 'navigieren'

this.props.navigation.replace('Your Next Component Name')
8
Surender Kumar

Zunächst einmal ist die Verwendung von AsyncStorage in einer synchronen Funktion (besonders im Lebenszyklus) eine so schlechte Idee. Normalerweise sollten Sie ASyncStorage an Orten in Ihrer Ordner-/App-Struktur belassen, die für den Ort, an dem Sie auf Daten zugreifen/aufbewahren, sinnvoll sind.

Grundsätzlich fragen Sie nach der Navigation, sobald sich die ASync-Methode auf JEDEM Rendern vollendet hat ... Diejenigen, die neu in RN sind, sollten wissen, dass eine Menge Dinge dazu führen können, dass ein Render ausgelöst wird. In einigen Fällen kann die Renderfunktion mindestens zehn Mal ausgelöst werden, bevor das letzte Rendering abgeschlossen wird. Dies bedeutet, dass Sie diese ASyncStorage-Methode 10-mal ausgelöst hätten ... definitiv etwas, worüber Sie nachdenken müssen, wenn Sie dieses Zeug implementieren. Der .then();-Teil der AsyncStorage-Funktion wird also mehr oder weniger lange ausgelöst, nachdem der Rendervorgang bereits abgeschlossen ist. Wenn es eine sinnvolle Vorgehensweise wäre, würde ich sagen, dass der return-Teil der Renderfunktion in die .then((value) => { return ( ... ); }); eingefügt wird. Dies ist jedoch eine noch schlechtere Idee. Grundsätzlich benötigen Sie hier die richtige Lifecycle-Methode und NICHT die Render-Methode.

Jedenfalls, da ich diese Komponentenbibliothek noch nie verwendet habe, kann ich nur helfen, Sie in die richtige Richtung zu bewegen, also hier ... Diese Dokumente auf ihrer Webseite scheinen zu sagen, dass Sie einen Verweis auf den übergebenen Requisitenavigator benötigen zu der Komponente, in der Sie es verwenden. Wenn Sie also den Navigator in dieser Klasse erstellt haben, würden Sie this.refs.whateverYouNamedTheNavigatorReference.navigate('SomeItemName') verwenden. Wenn Sie sich in der Klasse befinden, die dieser Navigator als Requisite übergeben wurde, verwenden Sie this.props.passNavigatorPropName.navigate('SomeItemName'). Wie Sie sehen, verwenden Sie die Variablendekonstruktion, um den navigate-Callback zu erhalten. Ich möchte dies jedoch auf diese Weise tun, da ich gesehen habe, dass Fehler verursacht wurden, indem Sie versehentlich eine alte Version der Navigationsfunktion oder ihrer übergeordneten Referenz abrissen und einen kaskadierenden Fehlereffekt verursachen .

Wenn Sie ASyncStorage in einer Komponentendatei verwenden (würde erneut empfehlen, dies in einer Komponente/Klasse zu speichern, in der auf Ihre Daten in der gesamten App zugegriffen wird ...), und Sie werden es verwenden, um die App zu entscheiden vorwärts/rückwärts navigieren ... definitiv aus der Renderfunktion entfernen und möglicherweise in die Lebenszyklusfunktionen constructor, componentWillReceiveProps, componentDidReceiveProps oder componentWillUpdate einfügen. Auf diese Weise wird es basierend auf einem Update, einem neu übergebenen Requisitobject oder einmalig ausgelöst, wenn die Komponente erstellt wird. Alles ist besser als jedes einzelne Rendering abzufeuern.

Schließlich weiß ich nicht, was Sie für Ihr StackNavigator-Routenstapelobjekt eingerichtet haben, aber Sie müssten das Schlüsselwort "DashboardScreen" verwenden, das auf eine Komponente verweist, die ordnungsgemäß importiert wurde. Das Schlüsselwort "DashboardScreen" würde höchstwahrscheinlich in Ihrem StackNavigator-Objekt eine Verbindung zu einem Komponentenimport herstellen, wie ...

import Dashboard from '../Views/DashboardScreenView';

StackNavigator({
  DashboardScreen: {
    screen: Dashboard,
    path: 'dashboard/:main',
    navigationOptions: null,
  },
});
4
GoreDefex

Aufgrund Ihrer Anforderungen empfehle ich folgende Einstellungen:

SplashNavigator.js

const SplashNavigator = StackNavigator({
  Splash: {
    screen: SplashScreen,
    navigationOptions: {
      header: {
        visible: false
      }
    }
  }
});

AppNavigator.js

const AppNavigator = StackNavigator(
  {
    EnableNotification: {
      screen: EnableNotificationScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    },
    CreateMessage: {
      screen: CreateMessageScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    },
    Dashboard: {
      screen: DashboardScreen,
      navigationOptions: {
        header: {
          visible: false
        }
      }
    }
  },
  {
    initialRouteName: "EnableNotification"
  }
);

In Ihrem index.Android.js rendern Sie die SplashNavigator.

Die SplashNavigator wird die SplashScreen rendern. Der Anfangsstatuswert isReady ist auf false gesetzt. Er gibt also einen Ladetext aus, bis der @ProductTour:key-Wert von AsyncStorage geladen wird (AsyncStorage ist eine async-Funktion, und Sie sollten ihn nicht in Ihre Renderfunktion einfügen. Es wird dann Ihren AppNavigator und Ihre EnableNotification als anfängliche Route darstellen.

class SplashScreen extends Component {
  constructor() {
    super(props);
    this.state = {
      isReady: false,
    }
  }

  componentDidMount() {
    AsyncStorage.getItem("@ProductTour:key").then(value => {
      console.log(value);
      // you will need to handle case when `@ProductTour:key` is not exists
      this.setState({
        isReady: true,
      });
    });
  }

  render() {
    const { isReady } = this.state;
    return (
      <View style={{flex: 1}}>
        {
          isReady ?
          <AppNavigator />
          : <Text>Loading</Text>
        }
      </View>
    );
  }
}

Dann ändern Sie auf EnableNotificationScreen und CreateMessageScreen Ihre Navigationsroutenfunktion, um NavigationActions.reset von doc zu verwenden.

Beispiel:

import { NavigationActions } from 'react-navigation';

handleOnPressButton = () => {
  const resetAction = NavigationActions.reset({
    index: 0,
    actions: [
      NavigationActions.navigate({ routeName: "CreateMessage" })
    ]
  });
  this.props.navigation.dispatch(resetAction);
}
3
alpha
this.props.navigation.replace('Your Next Component Name')
1
Pardeep Sharma

Ja, Sie können den aktuellen Bildschirm vor dem Navigieren zu einem neuen Bildschirm mit Hilfe von NavigationActions beenden. Bitte verweisen Sie auf diesen Link -

http://androidseekho.com/others/reactnative/finish-current-screen-on-navigating-another-in-react-native/

0
priyanka

Hier gibt es eine einfache Möglichkeit: Verwenden Sie "ersetzen" (Referenzlink repleace in navigation . Sie befinden sich beispielsweise auf dem Bildschirm "Login", Und möchten zum Bildschirm "Home" wechseln. Fügen Sie diesen ein Code im Bildschirm "Login"

                         <TouchableOpacity onPress={() => { this.login() }}>

                            <Text}>Click me to Login</Text>

                        </TouchableOpacity>

und method login: 

login(){
  this.props.navigation.replace('Home')
 }

Bildschirm "Login" wird durch "Home" ersetzt. Drücken Sie in Android die Zurück-Taste => App beenden, kein Bildschirm "Login".

0
truong luu

SplashNavigator.js

const SplashNavigator = StackNavigator({
  Splash: {
    screen: SplashScreen,
    navigationOptions: {
      header: null}
    }
  }
});
0
Danish Hussain