ONE DOM helper library for react
npm install dt2react;
const { addClass } = dt2react;
- cancelAnimationFramePolyfill
- nativeRequestAnimationFrame
- requestAnimationFramePolyfill
- cssAnimation
- throttleAnamition { throttleAnamition, throttleAnamitionDecorator }
- addClass
- classList
- classList2
- hasClass
- removeClass
- toggleClass
hasClass(node, className)
addClass(node, className)
removeClass(node, className)
on()
off()
onFocus()
getOffsetPosition(domEle): { top: number, left: number};
getWindowSize(): { width: number, height: number};
- Align
- childrenToArray
- mapSelf
- immutableUpdate
- enhancePortal
- Portal
- reactEvents
- getDefaultContainer
- PureRenderDeepMixin
- PureRenderMixin
- ResizeDetector
- RemoteViewer
- ScriptViewer
Make setState easily and immutably. more info immutability-helper.
- No need to call setState manually
- No need to build syntactic sugar like `{x: {y: {$set: 1}}}`, just pass `x.y` and `1`
- example
import { immutableUpdate as update } from 'dt2react';
class Todos extends Component {
constructor() {
super()
this.update = update.bind(this)
this.state = {
text: '',
items: []
}
}
render() {
const { text, items } = this.state
const update = this.update
return (
<div>
<input type="text" value={text} onChange={e => update('set', 'text', e.target.value)} />
<button onClick={() => update('push', 'items', { text })}>Add</button>
<ul>
{items.map((item, i) => {
return (
<li key={i}>
{item.text}
<button onClick={() => update('splice', 'items', i)}></button>
</li>
)
})}
</ul>
</div>
)
}
}
-
api
Bind component and execute setState automatically
import { immutableUpdate as update } from 'dt2react';
class App extends Component {
constructor() {
super()
this.update = update.bind(this)
this.state = {
name: 'John',
relation: {
family: 0,
friend: 1
},
honor: ['1', '2', '3']
}
}
someUsage() {
this.update('set', 'name', 'Wall')
this.update('set', 'relation.family', 1)
this.update('set', ['relation', 'family'], 0)
this.update('set', {
name: 'Jamas',
'relation.friend': 0
})
this.update('push', 'honor', '4') // ['1', '2', '3', '4']
this.update('splice', 'honor', 0) // ['2', '3', '4']
// All above actions just render once and all state has changed.
}
}
- Silent usage
which would not execute setState automatically
import { immutableUpdate as update } from 'dt2react';
const myData = { x: { y: 0 } }
const newData = update(myData, 'set', 'x.y', 1)
console.log(newData) // {x: {y: 1}}
wrapper of eventlistener
import addEventListener from 'dt2react/lib/events/eventlistener';
var handler = addEventListener(document.body, 'click', function(e){
console.log(e.target); // works for ie
console.log(e.nativeEvent); // native dom event
});
handler.remove(); // detach event listener
use. (target: ReactNode, eventType: string, listener: Function): { remove: Function }
import addEventlistener from 'dt2react/lib/react/reactEvents';
create default container
const rootDiv = getDefaultContainer();
import PureRenderMixin from 'dt2react/lib/react/PureRenderMixin';
shouldComponentUpdate(nextProps, nextState) {
return PureRenderMixin.shouldComponentUpdate.call(this, nextProps, nextState);
}
// or
shouldComponentUpdate(...args) {
return PureRenderMixin.shouldComponentUpdate.apply(this, args);
}
deep compare
import PureRenderDeepMixin from 'dt2react/lib/react/PureRenderDeepMixin';
shouldComponentUpdate(nextProps, nextState) {
return PureRenderDeepMixin.shouldComponentUpdate.call(this, nextProps, nextState);
}
// or
shouldComponentUpdate(...args) {
return PureRenderDeepMixin.shouldComponentUpdate.apply(this, args);
}
import withResize, { ResizeDetector } from 'dt2react/lib/react/withResize';
import RemoteViewer, { getRemoteComponent, getRemoteModule } from 'dt2react/lib/react/RemoteViewer';
export const WebStudioExecutor = getRemoteComponent({
scriptConfig: {
key: 'amosasp',
url: getMfUrl('amosasp_dist/remoteEntry.js')
},
scope: 'amosasp',
module: './amos-webstudio',
onDone: (d) => d.WebStudioExecutor
});
直接使用远程模块
import { getRemoteModule } from 'dt2react/lib/react/RemoteViewer';
function getMfUrl(entry) {
// 注意 __mf_prefix_url__ ,结尾不能写后缀 `/`
// 如下方式,支持设置 `__mf_prefix_url__=''`
if (window.__mf_prefix_url__ !== undefined || window.__mf_prefix_url__ !== null){
return `${window.__mf_prefix_url__}/${entry}`;
}
return `/mf_lib/${entry}`;
}
export const mfRV = getRemoteModule({
scriptConfig: {
key: 'amosmf',
url: getMfUrl('amosmf_dist/remoteEntry.js')
},
scope: 'amosmf',
module: './handsontable',
onDone: (d) => ({
HotTable: d.HotTable,
HotColumn: d.HotColumn
}),
debugConfig
});
// demo
class HTableDemo extends Component {
constructor(props) {
super(props);
this.state = {
laoding: true,
HotTable: null,
HotColumn: null
};
this._asyncInit();
}
_asyncInit = () => {
mfRV.loadMf(({ HotTable, HotColumn }) => {
this.setState({
laoding: false,
HotTable,
HotColumn
});
});
}
render() {
const { laoding, HotTable, HotColumn } = this.state;
if (laoding){
return null;
}
return (
<div className="demo-content">
<HotTable rowHeaders height="50%" data={dataList} licenseKey="non-commercial-and-evaluation">
<HotColumn title="时间" />
<HotColumn title="值" />
<HotColumn title="其它" />
</HotTable>
<h3>单独使用 HotTable </h3>
<HotTable height="50%" data={dataList} licenseKey="non-commercial-and-evaluation" />
</div>
);
}
}
import ScriptViewer, { getScriptComponent } from 'dt2react/lib/react/ScriptViewer';
import { BaseMap } from 'amos-amap';
function MyMap(){
return (
<div style={{width: '100%', height: '400px'}}>
<BaseMap zoom={5} center={{ longitude: 120, latitude: 30 }}/>
</div>
);
}
// 外部直接使用 MapViewer
const MapViewer = getScriptComponent({
scriptConfig: [
{ key: 'amap', url: 'http://webapi.amap.com/maps?v=1.4.3&key=xxxxxxxx' }
],
useBody: true,
deferred: true,
component: MyMap
});
calcScrollBarSize(fresh);// 获取当前浏览器滚动条宽度,推荐
getScrollbarWidth();
addPxToStyle(name, value);
domCss: { set, get };
getInnerHeight(el);
getInnerWidth(el);
getScroll(target, top);
prefixStyle(prop);
getStyle(node, property)
removeStyle(node, property)
addStyle(node, property, value)
-
warning
-
invariant
-
shallowEqual
-
arrayTreeFilter
-
createChainFunc
-
debounce
-
deprecated
-
devtoolsCheck
import { startCheck } from 'dt2react/lib/utils/devtoolsCheck'; startCheck({ redirect, afterOpen, delay })
。可用window.enableDevtoolCheck
直接进行控制 -
env
check is dev: set NODE_ENV=development or NODE_ENV=production
-
stringFormatter
-
toCamelCase
-
trim
-
loadScripts
直接用于react
componentDidMount() { const script = { key: 'amapscripts', url: 'http://webapi.amap.com/maps?v=1.4.3&key=xxx' }; document.getElementById('app').style.display = 'none'; tools.asyncLoadScript(script, () => { document.getElementById('app').style.display = 'block'; render(<Container navs={navs} defaultNav="amapdemo" logo="amos amap" />, document.getElementById('app')); }); // tools.asyncLoadScripts(scripts, cb) 加载多个 [{key, url}, {key, url}] }
- loadcss
LoadCss.asyncLoadOne({ key: 'amosframework', url: '/node_modules/amos-framework/dist/amosframework.css' }); // 数组最前面的样式,优先级最低 LoadCss.asyncLoadList([ { key: 'amosframework', url: '/node_modules/amos-framework/dist/amosframework.css' } ]);
- get
dt2react/lib/utils/get
import get from 'dt2react/lib/utils/get'; const object = { 'a': [{ 'b': { 'c': 3 } }] }; get(object, 'a[0].b.c'); // 3 get(object, ['a', '0', 'b', 'c']); // 3 get(object, 'a.b.c', 'default'); // default
- getCacheRequest
dt2react/lib/utils/cacheRequest
import { getCacheRequest } from 'dt2react/lib/utils/cacheRequest'; function getInfoAction(){ return commonGet(url); } const cacheGetInfoAction = getCacheRequest(getInfoAction, url); // 使用时: cacheGetInfoAction().then(data => { ... }); // 有参数的 function getUserAction(userId){ const _url = formatUrl(userInfoUrl, { userId }); return commonGet(_url); } const tags = formatUrl(userInfoUrl, { userId: 333 }); const cacheUserAction = getCacheRequest(getUserAction, tags); // 有参数,动态生成 actionTag const globalActionMapping = {}; function cacheUserAction2(userId){ const tags = formatUrl(userInfoUrl, { userId }); if (!globalActionMapping[tags]){ globalActionMapping[tags] = getCacheRequest(getUserAction, tags); } return globalActionMapping[tags](userId); } // 使用 cacheUserAction2('112233').then(data => { ... });
------ utils end
/**
* @return {bool} True if browser supports css animations.
*/
BrowserSupportCore.hasCSSAnimations();
/**
* @return {bool} True if browser supports css transforms.
*/
BrowserSupportCore.hasCSSTransforms();
/**
* @return {bool} True if browser supports css 3d transforms.
*/
BrowserSupportCore.hasCSS3DTransforms();
/**
* @return {bool} True if browser supports css transitions.
*/
BrowserSupportCore.hasCSSTransitions();
/**
* @param {string} property Name of a css property to check for.
* @return {?string} property name supported in the browser, or null if not
* supported.
*/
getVendorPrefixedName(property);
canUseDOM
activeElement()
contains(context, node)
getContainer(container, defaultContainer)
getHeight(node, client)
getOffset(node): { top, left, width, height }
getOffsetParent(node)
getPosition(node, offsetParent)
getScrollbarSize(recalc)
getWidth(node, client)
getWindow(node)
isOverflowing(container)
nodeName(node)
ownerDocument(componentOrElement)
ownerWindow(componentOrElement)
scrollLeft(node, val)
scrollTop(node, val)
use es modules
modify LoadScripts
, Optimize lib pkg
add style/clientRect
add style/lineHeight
MIT