最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - React: Wait until all assets are loaded - Stack Overflow

programmeradmin2浏览0评论

In a React.js project, I'm fetching svgs inside of the ponentWillMount() lifecycle method via a function called loadAllAssets(). These are then saved inside of the user's localStorage.

(1) Is there a more elegant way of checking whether all requested svg files have been indeed saved inside localStorage other than iterating over the number of requests made and paring them to the content of localStorage?

(2) Is there a nicer way to prevent the initialization of ponentDidMount as long as resources are still loading other than wrapping the entire code in a conditional? I am using Redux so that would e to mind as well but seems to me like using a sledgehammer to crack a nut.

index.js

import { loadAllAssets } from './utils/loadAllAssets';

class AppContainer extends React.Component {
  ponentWillMount() {
    loadAllAssets();
  }
//...
}
ReactDOM.render(<Provider store={store} ><AppContainer /></Provider>, 
document.getElementById('root'));

loadAllAssets.js

import { ajaxSVG } from './gfAssetsLoader';

export const loadAllAssets = () => {
  /* write to localStorage */
  ajaxSVG('closeScene', '/assets/svg/close-scene-ani.svg');
//...
}

gfAssetsLoader.js

export const ajaxSVG = (assetName, path) => {
  try {
    let request = new XMLHttpRequest();
    request.open("GET", path, true);
    request.onload = function (e) {
      if( request.status >= 200 && request.status < 400 ) {
        let data = request.responseText;
        localStorage.setItem(assetName, data);
      } else console.log('Bad request. request status: ' + request.status);
    }
    request.send();
  }
  catch (e) {
    console.log(e);
  }
};

In a React.js project, I'm fetching svgs inside of the ponentWillMount() lifecycle method via a function called loadAllAssets(). These are then saved inside of the user's localStorage.

(1) Is there a more elegant way of checking whether all requested svg files have been indeed saved inside localStorage other than iterating over the number of requests made and paring them to the content of localStorage?

(2) Is there a nicer way to prevent the initialization of ponentDidMount as long as resources are still loading other than wrapping the entire code in a conditional? I am using Redux so that would e to mind as well but seems to me like using a sledgehammer to crack a nut.

index.js

import { loadAllAssets } from './utils/loadAllAssets';

class AppContainer extends React.Component {
  ponentWillMount() {
    loadAllAssets();
  }
//...
}
ReactDOM.render(<Provider store={store} ><AppContainer /></Provider>, 
document.getElementById('root'));

loadAllAssets.js

import { ajaxSVG } from './gfAssetsLoader';

export const loadAllAssets = () => {
  /* write to localStorage */
  ajaxSVG('closeScene', '/assets/svg/close-scene-ani.svg');
//...
}

gfAssetsLoader.js

export const ajaxSVG = (assetName, path) => {
  try {
    let request = new XMLHttpRequest();
    request.open("GET", path, true);
    request.onload = function (e) {
      if( request.status >= 200 && request.status < 400 ) {
        let data = request.responseText;
        localStorage.setItem(assetName, data);
      } else console.log('Bad request. request status: ' + request.status);
    }
    request.send();
  }
  catch (e) {
    console.log(e);
  }
};
Share Improve this question asked Oct 15, 2017 at 16:24 gnzggnzg 3703 gold badges5 silver badges17 bronze badges 2
  • shouldn't the ajax requests by done in ponentDidMount ? – Rohit Kumar Commented Oct 15, 2017 at 16:30
  • 1 why not use promises? before rendering the app container, why dont you load the svg images first then only after the promise chain has been pleted do you actually render the app – Maru Commented Oct 15, 2017 at 16:51
Add a ment  | 

1 Answer 1

Reset to default 4

1-

export const loadAllAssets = () => {
  /* write to localStorage */
  return ajaxSVG('closeScene', '/assets/svg/close-scene-ani.svg');
  //...
}

export const ajaxSVG = (assetName, path) => {
  return new Promise((resolve, reject) => {
    try {
      let request = new XMLHttpRequest();
      request.open("GET", path, true);
      request.onload = function (e) {
        if( request.status >= 200 && request.status < 400 ) {
          let data = request.responseText;
          localStorage.setItem(assetName, data);
          resolve();
        } else reject('Bad request. request status: ' + request.status);
      }
      request.send();
    }
    catch (e) {
      reject(e);
    }
  });
};

Now you can concatenate a .then to loadAllAssets() and change the state there.

2- To show the a loading state just create a state of loading and change it to false when the data loaded, so it will show a loader while the data is loading and after it's done it will show the data.

import { loadAllAssets } from './utils/loadAllAssets';

class AppContainer extends React.Component {
  constructor() {
    super();

    this.state = {
       loading: false
    };
  }

  ponentWillMount() {
    loadAllAssets()
    .then(() => {
      this.setState({ loading: false });
    });
  }
//...
  render() {
    if (this.state.loading) {
       return (
         <div><h1>Loading...</h1></div>
       );
    }

    return (
       //...something else
    );
  }
}
ReactDOM.render(<Provider store={store} ><AppContainer /></Provider>, 
document.getElementById('root'));
发布评论

评论列表(0)

  1. 暂无评论