mirror of
https://github.com/google-map-react/google-map-react.git
synced 2025-12-08 18:26:32 +00:00
Use shallowEqual and isEmpty as much as possible (#540)
* Use shallowCompare to compare objects * Use isEmpty as much as possible * Use our own shallowEqual * Remove fbjs * Just disable necessary line * Add eslint-disable where needed
This commit is contained in:
parent
8cb6939e6c
commit
486bccfc61
@ -2,10 +2,7 @@
|
||||
.*/coverage/.*
|
||||
.*/scripts/.*
|
||||
.*/node_modules/flow-bin/.*
|
||||
# .*/node_modules/fbjs/.*
|
||||
.*/node_modules/fbjs/lib/Deferred.js.flow
|
||||
.*/node_modules/.*/flow-bin.*/.*
|
||||
.*/node_modules/.*/fbjs.*/.*
|
||||
.*/node_modules/.*/broken.json
|
||||
.*/node_modules/fixed-data-table/*
|
||||
.*/node_modules/.*/fixtures/package.json
|
||||
|
||||
@ -48,7 +48,6 @@
|
||||
"dependencies": {
|
||||
"@mapbox/point-geometry": "^0.1.0",
|
||||
"eventemitter3": "^1.1.0",
|
||||
"fbjs": "^0.8.3",
|
||||
"scriptjs": "^2.5.7"
|
||||
},
|
||||
"devDependencies": {
|
||||
|
||||
@ -3,9 +3,6 @@ import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import ReactDOM from 'react-dom';
|
||||
|
||||
// libs
|
||||
import shallowEqual from 'fbjs/lib/shallowEqual';
|
||||
|
||||
// helpers
|
||||
import GoogleMapMap from './google_map_map';
|
||||
import MarkerDispatcher from './marker_dispatcher';
|
||||
@ -22,8 +19,10 @@ import raf from './utils/raf';
|
||||
import pick from './utils/pick';
|
||||
import omit from './utils/omit';
|
||||
import log2 from './utils/math/log2';
|
||||
import isEmpty from './utils/isEmpty';
|
||||
import isNumber from './utils/isNumber';
|
||||
import detectBrowser from './utils/detect';
|
||||
import shallowEqual from './utils/shallowEqual';
|
||||
import isPlainObject from './utils/isPlainObject';
|
||||
import isArraysEqualEps from './utils/isArraysEqualEps';
|
||||
import detectElementResize from './utils/detectElementResize';
|
||||
@ -209,18 +208,13 @@ export default class GoogleMap extends Component {
|
||||
);
|
||||
}
|
||||
|
||||
if (
|
||||
this.props.center === undefined &&
|
||||
this.props.defaultCenter === undefined
|
||||
) {
|
||||
if (isEmpty(this.props.center) && isEmpty(this.props.defaultCenter)) {
|
||||
console.warn(
|
||||
'GoogleMap: center or defaultCenter property must be defined' // eslint-disable-line no-console
|
||||
);
|
||||
}
|
||||
|
||||
if (
|
||||
this.props.zoom === undefined && this.props.defaultZoom === undefined
|
||||
) {
|
||||
if (isEmpty(this.props.zoom) && isEmpty(this.props.defaultZoom)) {
|
||||
console.warn(
|
||||
'GoogleMap: zoom or defaultZoom property must be defined' // eslint-disable-line no-console
|
||||
);
|
||||
@ -288,17 +282,15 @@ export default class GoogleMap extends Component {
|
||||
|
||||
componentWillReceiveProps(nextProps) {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
if (this.props.defaultCenter !== nextProps.defaultCenter) {
|
||||
if (!shallowEqual(this.props.defaultCenter, nextProps.defaultCenter)) {
|
||||
console.warn(
|
||||
'GoogleMap: defaultCenter prop changed. ' + // eslint-disable-line
|
||||
"You can't change default props."
|
||||
"GoogleMap: defaultCenter prop changed. You can't change default props."
|
||||
);
|
||||
}
|
||||
|
||||
if (this.props.defaultZoom !== nextProps.defaultZoom) {
|
||||
if (!shallowEqual(this.props.defaultZoom, nextProps.defaultZoom)) {
|
||||
console.warn(
|
||||
'GoogleMap: defaultZoom prop changed. ' + // eslint-disable-line
|
||||
"You can't change default props."
|
||||
"GoogleMap: defaultZoom prop changed. You can't change default props."
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -337,26 +329,24 @@ export default class GoogleMap extends Component {
|
||||
}
|
||||
}
|
||||
|
||||
if (nextProps.zoom !== undefined) {
|
||||
if (!isEmpty(nextProps.zoom)) {
|
||||
// if zoom chaged by user
|
||||
if (Math.abs(nextProps.zoom - this.props.zoom) > 0) {
|
||||
this.map_.setZoom(nextProps.zoom);
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
this.props.draggable !== undefined && nextProps.draggable === undefined
|
||||
) {
|
||||
if (!isEmpty(this.props.draggable) && isEmpty(nextProps.draggable)) {
|
||||
// reset to default
|
||||
this.map_.setOptions({ draggable: this.defaultDraggableOption_ });
|
||||
} else if (this.props.draggable !== nextProps.draggable) {
|
||||
} else if (!shallowEqual(this.props.draggable, nextProps.draggable)) {
|
||||
// also prevent this on window 'mousedown' event to prevent map move
|
||||
this.map_.setOptions({ draggable: nextProps.draggable });
|
||||
}
|
||||
|
||||
// use shallowEqual to try avoid calling map._setOptions if only the ref changes
|
||||
if (
|
||||
nextProps.options !== undefined &&
|
||||
!isEmpty(nextProps.options) &&
|
||||
!shallowEqual(this.props.options, nextProps.options)
|
||||
) {
|
||||
const mapPlainObjects = pick(this.maps_, isPlainObject);
|
||||
@ -374,7 +364,7 @@ export default class GoogleMap extends Component {
|
||||
this.map_.setOptions(options);
|
||||
}
|
||||
|
||||
if (nextProps.layerTypes !== this.props.layerTypes) {
|
||||
if (!shallowEqual(nextProps.layerTypes, this.props.layerTypes)) {
|
||||
Object.keys(this.layers_).forEach(layerKey => {
|
||||
this.layers_[layerKey].setMap(null);
|
||||
delete this.layers_[layerKey];
|
||||
@ -395,7 +385,7 @@ export default class GoogleMap extends Component {
|
||||
componentDidUpdate(prevProps) {
|
||||
this.markersDispatcher_.emit('kON_CHANGE');
|
||||
|
||||
if (this.props.hoverDistance !== prevProps.hoverDistance) {
|
||||
if (!shallowEqual(this.props.hoverDistance, prevProps.hoverDistance)) {
|
||||
this.markersDispatcher_.emit('kON_MOUSE_POSITION_CHANGE');
|
||||
}
|
||||
}
|
||||
@ -453,7 +443,7 @@ export default class GoogleMap extends Component {
|
||||
};
|
||||
|
||||
_computeMinZoom = minZoom => {
|
||||
if (minZoom !== undefined && minZoom !== null) {
|
||||
if (!isEmpty(minZoom)) {
|
||||
return minZoom;
|
||||
}
|
||||
return this._getMinZoom();
|
||||
@ -541,7 +531,7 @@ export default class GoogleMap extends Component {
|
||||
: this.props.options;
|
||||
const defaultOptions = defaultOptions_(mapPlainObjects);
|
||||
|
||||
const draggableOptions = this.props.draggable !== undefined && {
|
||||
const draggableOptions = !isEmpty(this.props.draggable) && {
|
||||
draggable: this.props.draggable,
|
||||
};
|
||||
|
||||
@ -555,7 +545,7 @@ export default class GoogleMap extends Component {
|
||||
...propsOptions,
|
||||
};
|
||||
|
||||
this.defaultDraggableOption_ = preMapOptions.draggable !== undefined
|
||||
this.defaultDraggableOption_ = !isEmpty(preMapOptions.draggable)
|
||||
? preMapOptions.draggable
|
||||
: this.defaultDraggableOption_;
|
||||
|
||||
|
||||
@ -1,9 +1,9 @@
|
||||
/* eslint-disable react/forbid-prop-types */
|
||||
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import shallowEqual from 'fbjs/lib/shallowEqual';
|
||||
|
||||
// utils
|
||||
import omit from './utils/omit';
|
||||
import shallowEqual from './utils/shallowEqual';
|
||||
|
||||
const mainStyle = {
|
||||
width: '100%',
|
||||
@ -25,6 +25,7 @@ const style = {
|
||||
};
|
||||
|
||||
export default class GoogleMapMarkers extends Component {
|
||||
/* eslint-disable react/forbid-prop-types */
|
||||
static propTypes = {
|
||||
geoService: PropTypes.any,
|
||||
style: PropTypes.any,
|
||||
@ -38,6 +39,7 @@ export default class GoogleMapMarkers extends Component {
|
||||
projectFromLeftTop: PropTypes.bool,
|
||||
prerender: PropTypes.bool,
|
||||
};
|
||||
/* eslint-enable react/forbid-prop-types */
|
||||
|
||||
static defaultProps = {
|
||||
projectFromLeftTop: false,
|
||||
|
||||
71
src/utils/shallowEqual.js
Normal file
71
src/utils/shallowEqual.js
Normal file
@ -0,0 +1,71 @@
|
||||
/**
|
||||
* Copyright (c) 2013-present, Facebook, Inc.
|
||||
*
|
||||
* This source code is licensed under the MIT license found in the
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*
|
||||
* @providesModule shallowEqual
|
||||
* @typechecks
|
||||
* @flow
|
||||
*/
|
||||
|
||||
const hasOwnProperty = Object.prototype.hasOwnProperty;
|
||||
|
||||
/**
|
||||
* inlined Object.is polyfill to avoid requiring consumers ship their own
|
||||
* https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
|
||||
*/
|
||||
function is(x: mixed, y: mixed): boolean {
|
||||
// SameValue algorithm
|
||||
if (x === y) {
|
||||
// Steps 1-5, 7-10
|
||||
// Steps 6.b-6.e: +0 != -0
|
||||
// Added the nonzero y check to make Flow happy, but it is redundant
|
||||
return x !== 0 || y !== 0 || 1 / x === 1 / y;
|
||||
}
|
||||
// Step 6.a: NaN == NaN
|
||||
// eslint-disable-next-line no-self-compare
|
||||
return x !== x && y !== y;
|
||||
}
|
||||
|
||||
/**
|
||||
* Performs equality by iterating through keys on an object and returning false
|
||||
* when any key has values which are not strictly equal between the arguments.
|
||||
* Returns true when the values of all keys are strictly equal.
|
||||
*/
|
||||
function shallowEqual(objA: mixed, objB: mixed): boolean {
|
||||
if (is(objA, objB)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (
|
||||
typeof objA !== 'object' ||
|
||||
objA === null ||
|
||||
typeof objB !== 'object' ||
|
||||
objB === null
|
||||
) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const keysA = Object.keys(objA);
|
||||
const keysB = Object.keys(objB);
|
||||
|
||||
if (keysA.length !== keysB.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Test for A's keys different from B.
|
||||
for (let i = 0; i < keysA.length; i++) {
|
||||
if (
|
||||
!hasOwnProperty.call(objB, keysA[i]) ||
|
||||
!is(objA[keysA[i]], objB[keysA[i]])
|
||||
) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
module.exports = shallowEqual;
|
||||
/* src: https://github.com/facebook/fbjs/blob/master/packages/fbjs/src/core/shallowEqual.js */
|
||||
@ -2277,7 +2277,7 @@ fastparse@^1.1.1:
|
||||
version "1.1.1"
|
||||
resolved "https://registry.yarnpkg.com/fastparse/-/fastparse-1.1.1.tgz#d1e2643b38a94d7583b479060e6c4affc94071f8"
|
||||
|
||||
fbjs@^0.8.1, fbjs@^0.8.16, fbjs@^0.8.3, fbjs@^0.8.9:
|
||||
fbjs@^0.8.1, fbjs@^0.8.16, fbjs@^0.8.9:
|
||||
version "0.8.16"
|
||||
resolved "https://registry.yarnpkg.com/fbjs/-/fbjs-0.8.16.tgz#5e67432f550dc41b572bf55847b8aca64e5337db"
|
||||
dependencies:
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user