roundrobin
roundrobin

Reputation: 716

Prevent browser to scroll up when using visibilityChange event to trigger state update

In my react app I'm using the visibilityChange event to do some check of the logged in user, when he focuses the tab.

The problem is, that in my dashboard table view, I'm always jumping to the top of the page and loosing the scroll position when coming back to the tab (focusing). It seems to only happen when I'm updating the state of the application in one of the views.

Is there a way to prevent that behavior?

Here is the code:

//==================================================================
// External dep.
//==================================================================
import Reflux from "reflux";
import React from "react";
import {
    BrowserRouter as Router,
    Route,
    Switch
} from "react-router-dom";
//==================================================================
// External dep.
//==================================================================
import DefaultLayout from ".DefaultLayout.jsx";
import Actions from "./Actions";
import Dashboard from "./Dashboard.jsx";
//==================================================================
// Router Code
//==================================================================
const mountNode = document.getElementById("app");

function renderDOM() {
    ReactDOM.render(
        <Router>
            <DefaultLayout>
                <Switch>

                    <Route exact path="/" component={Dashboard} />
                </Switch>
            </DefaultLayout>

        </Router>
        , mountNode);
}




function addVisibilityHandler(){
    // Set the name of the hidden property and the change event for visibility
    var hidden, visibilityChange; 
    if (typeof document.hidden !== "undefined") { // Opera 12.10 and Firefox 18 and later support 
        hidden = "hidden";
        visibilityChange = "visibilitychange";
    } else if (typeof document.msHidden !== "undefined") {
        hidden = "msHidden";
        visibilityChange = "msvisibilitychange";
    } else if (typeof document.webkitHidden !== "undefined") {
        hidden = "webkitHidden";
        visibilityChange = "webkitvisibilitychange";
    }

    function handleVisibilityChange(e) {
        e.preventDefault(); // Didnt prevent the page from scrolling to top
        e.stopPropagation();
        e.stopImmediatePropagation();

        if (!document[hidden]) {
            // Check again if the use still has permissions to see this page
            Actions.userLoggedIn();            
        }


    }

    // Warn if the browser doesn't support addEventListener or the Page Visibility API
    if (typeof document.addEventListener === "undefined" || typeof document[hidden] === "undefined") {
        logger.log("addVisibilityHandler", "This demo requires a browser, such as Google Chrome or Firefox, that supports the Page Visibility API.");
    } else {
        // Handle page visibility change   
        document.addEventListener(visibilityChange, handleVisibilityChange, false);

    }
}

// Add the event handler for the visibility check
addVisibilityHandler();

// Trigger the login check
Actions.userLoggedIn();


Actions.userLoggedIn.completed.listen(function (currentUser) {
    renderDOM();
});

Upvotes: 5

Views: 587

Answers (1)

Swaroop Deval
Swaroop Deval

Reputation: 906

You are re-rendering you DOM every time user comes back to the page.

It is happening because you check if user is logged when he/she comes into the Tab and there is a listener at the end of your code that renders the DOM if user completes the login.

if (!document[hidden]) {
    // Check again if the use still has permissions to see this page
    Actions.userLoggedIn();
}       
Actions.userLoggedIn.completed.listen(function (currentUser) {
    renderDOM();
});

One of the soluction to this problem can be, you pass a flag that says that user loggedIn first time or came back to the tab.

Actions.userLoggedIn.completed.listen(function (currentUser, flag) {
    if(flag) {
        renderDOM();
    }
});

Upvotes: 1

Related Questions