├── .gitignore ├── source-code.lodash ├── README.md └── src │ ├── isObjectLike.js │ ├── isObject.js │ ├── clamp.js │ ├── isFunction.js │ ├── create.js │ ├── isPlainObject.js │ ├── slice.js │ └── .internal │ └── stringToPath.js ├── source-code.lazyestload ├── README.md ├── lazyestload.png └── src │ ├── lazyload.js │ └── lazyestload.js ├── source-code.zepto └── README.md ├── source-code.stat ├── Stat.png ├── README.md └── src │ └── Stats.js ├── source-code.redux ├── Redux.png ├── README.md └── src │ ├── utils │ ├── warning.js │ ├── actionTypes.js │ └── isPlainObject.js │ ├── compose.js │ ├── index.js │ ├── bindActionCreators.js │ └── applyMiddleware.js ├── source-code.pubsub-js ├── PubSub.png └── README.md ├── source-code.reselect ├── reselect.png ├── README.md └── src │ └── index.js ├── source-code.unstated ├── unstated.png └── src │ └── unstated.js ├── source-code.hyperapp ├── hyperapp导图.jpg ├── hyperapp-patch导图.png └── README.md ├── source-code.fullpage └── README.md ├── source-code.jquery-mousewheel └── README.md ├── source-code.react-redux ├── React-Redux.png └── src │ ├── components │ ├── Context.js │ └── Provider.js │ ├── utils │ ├── wrapActionCreators.js │ ├── verifyPlainObject.js │ ├── isPlainObject.js │ ├── warning.js │ └── shallowEqual.js │ ├── index.js │ └── connect │ ├── mapStateToProps.js │ ├── verifySubselectors.js │ ├── mapDispatchToProps.js │ ├── mergeProps.js │ ├── wrapMapToProps.js │ ├── connect.js │ └── selectorFactory.js ├── source-code.reach-router ├── reachRouter.png ├── reachRouter-Focus.gif ├── src │ └── lib │ │ └── history.js └── README.md ├── source-code.react-motion ├── react-motion.png └── src │ ├── presets.js │ ├── spring.js │ ├── reorderKeys.js │ ├── mapToZero.js │ ├── react-motion.js │ ├── stripStyle.js │ ├── shouldStopAnimation.js │ ├── stepper.js │ ├── Types.js │ └── mergeDiff.js ├── source-code.signature_pad ├── signature_pad.png ├── src │ ├── point.ts │ ├── throttle.ts │ └── bezier.ts └── README.md ├── source-code.react-loadable ├── react-loadabel.png └── src │ ├── webpack.js │ └── babel.js ├── source-code.react-snapshot ├── react-snapshot.png ├── src │ ├── index.js │ ├── Writer.js │ ├── snapshot.js │ ├── Server.js │ ├── cli.js │ └── Crawler.js └── README.md ├── source-code.react-waypoint ├── react-waypoint.png ├── src │ ├── constants.js │ ├── debugLog.js │ ├── isDOMElement.js │ ├── resolveScrollableAncestorProp.js │ ├── ensureChildrenIsValid.js │ ├── computeOffsetPixels.js │ ├── ensureRefIsUsedByChild.js │ ├── parseOffsetAsPixels.js │ ├── parseOffsetAsPercentage.js │ ├── onNextTick.js │ └── getCurrentPosition.js └── README.md ├── source-code.redux-observable ├── redux-observable.png ├── redux-observable-next.png ├── redux-observable-pipe.png ├── redux-observable-subscribe.png └── src │ ├── index.js │ ├── utils │ └── console.js │ ├── operators.js │ ├── StateObservable.js │ ├── ActionsObservable.js │ ├── combineEpics.js │ └── createEpicMiddleware.js ├── source-code.fast-memoizeVSnano-memoize ├── fast-memoize.png ├── README.md └── src │ ├── fast-memoize.js │ └── nano-memoize.js ├── source-code.ant-design ├── src │ ├── tabs │ │ └── TabPane.md │ ├── _util │ │ ├── warning.md │ │ ├── getScroll.md │ │ └── throttleByAnimationFrame.md │ ├── card │ │ ├── Grid.md │ │ └── Meta.md │ ├── rc-animate │ │ ├── util.md │ │ ├── AnimateChild.md │ │ └── ChildrenUtils.md │ ├── rc-dialog │ │ ├── LazyRenderBox.md │ │ └── DialogWrap.md │ ├── rc-util │ │ ├── Portal.md │ │ └── getScrollBarSize.md │ ├── rc-tabs │ │ ├── TabPane.md │ │ ├── ScrollableInkTabBar.md │ │ └── TabContent.md │ ├── anchor │ │ └── AnchorLink.md │ └── modal │ │ └── Modal.md └── README.md ├── README.md ├── source-code.graphql-request ├── README.md └── src │ ├── types.ts │ └── index.ts ├── source-code.create-react-app(webpack配置) └── README.md └── navigation.md /.gitignore: -------------------------------------------------------------------------------- 1 | .idea/ -------------------------------------------------------------------------------- /source-code.lodash/README.md: -------------------------------------------------------------------------------- 1 | ## Lodash 源码注释 -------------------------------------------------------------------------------- /source-code.lazyestload/README.md: -------------------------------------------------------------------------------- 1 | 一个简单的图片延迟加载 2 | 3 |  -------------------------------------------------------------------------------- /source-code.zepto/README.md: -------------------------------------------------------------------------------- 1 | # source-code.zepto 2 | Zepto v1.2.0 3 | 4 | 阅读[zepto源码](./src/zepto.js) 5 | -------------------------------------------------------------------------------- /source-code.stat/Stat.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.stat/Stat.png -------------------------------------------------------------------------------- /source-code.redux/Redux.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.redux/Redux.png -------------------------------------------------------------------------------- /source-code.pubsub-js/PubSub.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.pubsub-js/PubSub.png -------------------------------------------------------------------------------- /source-code.reselect/reselect.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.reselect/reselect.png -------------------------------------------------------------------------------- /source-code.unstated/unstated.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.unstated/unstated.png -------------------------------------------------------------------------------- /source-code.hyperapp/hyperapp导图.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.hyperapp/hyperapp导图.jpg -------------------------------------------------------------------------------- /source-code.fullpage/README.md: -------------------------------------------------------------------------------- 1 | # source-code.fullpage 2 | 3 | fullPage 2.5.4 4 | 5 | 阅读[fullpage源码(依赖jquery)](src/jquery.fullPage.js) 6 | -------------------------------------------------------------------------------- /source-code.jquery-mousewheel/README.md: -------------------------------------------------------------------------------- 1 | # source-code.jquery-mousewheel 2 | v3.1.13 3 | 4 | 阅读[jquery-mousewheel源码](src/JQmousewheel.js) 5 | -------------------------------------------------------------------------------- /source-code.lazyestload/lazyestload.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.lazyestload/lazyestload.png -------------------------------------------------------------------------------- /source-code.react-redux/React-Redux.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.react-redux/React-Redux.png -------------------------------------------------------------------------------- /source-code.hyperapp/hyperapp-patch导图.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.hyperapp/hyperapp-patch导图.png -------------------------------------------------------------------------------- /source-code.reach-router/reachRouter.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.reach-router/reachRouter.png -------------------------------------------------------------------------------- /source-code.react-motion/react-motion.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.react-motion/react-motion.png -------------------------------------------------------------------------------- /source-code.signature_pad/signature_pad.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.signature_pad/signature_pad.png -------------------------------------------------------------------------------- /source-code.reach-router/reachRouter-Focus.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.reach-router/reachRouter-Focus.gif -------------------------------------------------------------------------------- /source-code.react-loadable/react-loadabel.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.react-loadable/react-loadabel.png -------------------------------------------------------------------------------- /source-code.react-snapshot/react-snapshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.react-snapshot/react-snapshot.png -------------------------------------------------------------------------------- /source-code.react-waypoint/react-waypoint.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.react-waypoint/react-waypoint.png -------------------------------------------------------------------------------- /source-code.redux-observable/redux-observable.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.redux-observable/redux-observable.png -------------------------------------------------------------------------------- /source-code.react-waypoint/src/constants.js: -------------------------------------------------------------------------------- 1 | export default { 2 | above: 'above', 3 | inside: 'inside', 4 | below: 'below', 5 | invisible: 'invisible', 6 | }; 7 | -------------------------------------------------------------------------------- /source-code.redux-observable/redux-observable-next.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.redux-observable/redux-observable-next.png -------------------------------------------------------------------------------- /source-code.redux-observable/redux-observable-pipe.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.redux-observable/redux-observable-pipe.png -------------------------------------------------------------------------------- /source-code.fast-memoizeVSnano-memoize/fast-memoize.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.fast-memoizeVSnano-memoize/fast-memoize.png -------------------------------------------------------------------------------- /source-code.redux-observable/redux-observable-subscribe.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stonehank/sourcecode-analysis/HEAD/source-code.redux-observable/redux-observable-subscribe.png -------------------------------------------------------------------------------- /source-code.react-redux/src/components/Context.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | export const ReactReduxContext = React.createContext(null) 4 | 5 | export default ReactReduxContext 6 | -------------------------------------------------------------------------------- /source-code.react-waypoint/src/debugLog.js: -------------------------------------------------------------------------------- 1 | export default function debugLog() { 2 | if (process.env.NODE_ENV !== 'production') { 3 | console.log(arguments); // eslint-disable-line no-console 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /source-code.react-redux/src/utils/wrapActionCreators.js: -------------------------------------------------------------------------------- 1 | import { bindActionCreators } from 'redux' 2 | 3 | export default function wrapActionCreators(actionCreators) { 4 | return dispatch => bindActionCreators(actionCreators, dispatch) 5 | } 6 | -------------------------------------------------------------------------------- /source-code.react-motion/src/presets.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | export default { 3 | noWobble: {stiffness: 170, damping: 26}, // the default, if nothing provided 4 | gentle: {stiffness: 120, damping: 14}, 5 | wobbly: {stiffness: 180, damping: 12}, 6 | stiff: {stiffness: 210, damping: 20}, 7 | }; 8 | -------------------------------------------------------------------------------- /source-code.stat/README.md: -------------------------------------------------------------------------------- 1 | 一个js性能监控器,使用canvas绘制,简洁美观,思想也不复杂 2 | 3 | 1. 通过`performance.now`获取当前开始时间,每次调用时,计算时间差,每隔1秒计算每一帧平均消耗的毫秒数,从而计算1000毫秒的帧数。 4 | 5 | 2. 根据传入的当前fps和给定的最高fps绘制canvas,分为整体层,字体层,柱状条层。 6 | 7 | 3. 因为不使用clearRect清除画布,每次新创建的柱状条不会被清除,从而展示出监测器的效果。 8 | 9 | stat: 10 | 11 |  -------------------------------------------------------------------------------- /source-code.react-redux/src/index.js: -------------------------------------------------------------------------------- 1 | import Provider from './components/Provider' 2 | import connectAdvanced from './components/connectAdvanced' 3 | import { ReactReduxContext } from './components/Context' 4 | import connect from './connect/connect' 5 | 6 | export { Provider, connectAdvanced, ReactReduxContext, connect } 7 | -------------------------------------------------------------------------------- /source-code.redux-observable/src/index.js: -------------------------------------------------------------------------------- 1 | export { createEpicMiddleware } from './createEpicMiddleware'; 2 | export { ActionsObservable } from './ActionsObservable'; 3 | export { StateObservable } from './StateObservable'; 4 | export { combineEpics } from './combineEpics'; 5 | export { ofType } from './operators'; 6 | 7 | -------------------------------------------------------------------------------- /source-code.ant-design/src/tabs/TabPane.md: -------------------------------------------------------------------------------- 1 | ### Tabs.TabPane 2 | 3 | * 作为```Tabs```的children使用 4 | * 在```Tabs```渲染的时候,会被传到rc-tabs的```ScrollableInkTabBar```和```TabContent```中 5 | * 在上面2个组件中会分别获取标签tab内容和children内容作为tab的菜单标题和tab的内容 6 | * 详细见[ScrollableInkTabBar](../rc-tabs/ScrollableInkTabBar.md)和[TabContent](../rc-tabs/TabContent.md) -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## 关于阅读项目 2 | 3 | * 所有源码文件(带注释)放到src目录中。 4 | 5 | * 不定期寻找一些较小的框架、库、工具等热门项目进行阅读分析,以后使用或者扩展都会方便许多。 6 | 7 | * 进行流程导图制作,能对其内部整体结构和执行流动有一个直观整体的认识。 8 | 9 | * 每次阅读项目会对学习到的新方法、新想法进行记录到[个人博客](https://stonehank.github.io)里面 10 | 11 | * 个人水平有限,阅读过程中也有遇到无法理解的,会用`//todo xxx`标注,如有发现纰漏,请不吝指正。 12 | 13 | 14 | [*进入目录*](./navigation.md) 15 | -------------------------------------------------------------------------------- /source-code.graphql-request/README.md: -------------------------------------------------------------------------------- 1 | `graphql-request`一个极小的`graphql`请求方法 2 | 3 | 如果不太了解`graphql`,看一下这个库,或许能知道它的请求就可以这么简单... 4 | 5 | 就是熟悉的`fetch`,这里使用了`cross-fetch`(兼容的fetch) 6 | 7 | 8 | 1. `Content-Type`设置为`application/json` 9 | 2. `method`设置为`POST` 10 | 3. 合并自定义`headers` 11 | 4. 传入`query`(`graphql`的查询模板),`variables`(查询模板中的变量,可选) 12 | 13 | 剩下的只需要等待数据返回。 14 | 15 | 16 | -------------------------------------------------------------------------------- /source-code.redux/README.md: -------------------------------------------------------------------------------- 1 | # source-code.redux 2 | 3 | v4.0.0 4 | 5 | redux源码设计真的很精妙 6 | 7 | 改变状态是从store一层一层往下找,找到对应的type修改状态,再一层一层返回 8 | 9 | middleware是链式调用,每一环的返回值作为下一环的dispatch,就像滚雪球一样,最终能得到一个强大的dispatch 10 | 11 | 那么读完了是否能将这种设计思想变为自己的? 12 | 13 | 不能...刚读完去回想整个流程,缺漏的很多,真的是环环相扣 14 | 15 | 但多读几遍,或许哪天写代码的时候灵光一现,用上了某种设计,或许就真的变成你自己的东西了 16 | 17 | 详细解释在源码注释中,思维导图: 18 | 19 |  -------------------------------------------------------------------------------- /source-code.react-redux/src/utils/verifyPlainObject.js: -------------------------------------------------------------------------------- 1 | import isPlainObject from './isPlainObject' 2 | import warning from './warning' 3 | 4 | export default function verifyPlainObject(value, displayName, methodName) { 5 | if (!isPlainObject(value)) { 6 | warning( 7 | `${methodName}() in ${displayName} must return a plain object. Instead received ${value}.` 8 | ) 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /source-code.react-motion/src/spring.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | import presets from './presets'; 3 | import type {OpaqueConfig, SpringHelperConfig} from './Types'; 4 | 5 | const defaultConfig = { 6 | ...presets.noWobble, 7 | precision: 0.01, 8 | }; 9 | 10 | export default function spring(val: number, config?: SpringHelperConfig): OpaqueConfig { 11 | return {...defaultConfig, ...config, val}; 12 | } 13 | -------------------------------------------------------------------------------- /source-code.ant-design/src/_util/warning.md: -------------------------------------------------------------------------------- 1 | ```js 2 | import warning from 'warning'; 3 | 4 | const warned: { [msg: string]: boolean} = {}; 5 | export default (valid: boolean, message: string): void => { 6 | // valid为false 并且 第一次warning 7 | if (!valid && !warned[message]) { 8 | // warning,当第一个参数为false,发出message 9 | warning(false, message); 10 | warned[message] = true; 11 | } 12 | }; 13 | 14 | ``` -------------------------------------------------------------------------------- /source-code.react-motion/src/reorderKeys.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | 3 | let hasWarned = false; 4 | export default function reorderKeys() { 5 | if (process.env.NODE_ENV === 'development') { 6 | if (!hasWarned) { 7 | hasWarned = true; 8 | console.error( 9 | '`reorderKeys` has been removed, since it is no longer needed for TransitionMotion\'s new styles array API.' 10 | ); 11 | } 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /source-code.react-motion/src/mapToZero.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | import type {PlainStyle, Style} from './Types'; 3 | 4 | // currently used to initiate the velocity style object to 0 5 | export default function mapToZero(obj: Style | PlainStyle): PlainStyle { 6 | let ret = {}; 7 | for (const key in obj) { 8 | if (Object.prototype.hasOwnProperty.call(obj, key)) { 9 | ret[key] = 0; 10 | } 11 | } 12 | return ret; 13 | } 14 | -------------------------------------------------------------------------------- /source-code.react-motion/src/react-motion.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | export {default as Motion} from './Motion'; 3 | export {default as StaggeredMotion} from './StaggeredMotion'; 4 | export {default as TransitionMotion} from './TransitionMotion'; 5 | export {default as spring} from './spring'; 6 | export {default as presets} from './presets'; 7 | export {default as stripStyle} from './stripStyle'; 8 | 9 | // deprecated, dummy warning function 10 | export {default as reorderKeys} from './reorderKeys'; 11 | -------------------------------------------------------------------------------- /source-code.react-waypoint/src/isDOMElement.js: -------------------------------------------------------------------------------- 1 | /** 2 | * When an element's type is a string, it represents a DOM node with that tag name 3 | * https://facebook.github.io/react/blog/2015/12/18/react-components-elements-and-instances.html#dom-elements 4 | * 5 | * @param {React.element} Component 6 | * @return {bool} Whether the component is a DOM Element 7 | */ 8 | export default function isDOMElement(Component) { 9 | // 确认是原生DOM 10 | return (typeof Component.type === 'string'); 11 | } 12 | -------------------------------------------------------------------------------- /source-code.react-waypoint/src/resolveScrollableAncestorProp.js: -------------------------------------------------------------------------------- 1 | export default function resolveScrollableAncestorProp(scrollableAncestor) { 2 | // When Waypoint is rendered on the server, `window` is not available. 3 | // To make Waypoint easier to work with, we allow this to be specified in 4 | // string form and safely convert to `window` here. 5 | // 当传入字符串`window`,返回server-rendering的window 6 | if (scrollableAncestor === 'window') { 7 | return global.window; 8 | } 9 | 10 | return scrollableAncestor; 11 | } 12 | -------------------------------------------------------------------------------- /source-code.create-react-app(webpack配置)/README.md: -------------------------------------------------------------------------------- 1 | * 7-29:更新至webpack-config-dev.js 2 | 3 | * 9-25:更新webpackDevServer.config.js 4 | 5 | * 10-16:更新webpack.config.prod.js 6 | 7 | 粗读了一遍`create-react-app.js`,主要是用node对检测和创建上的操作,还有安装依赖, 8 | 下次会将它粗略分析下,并且将导图画出 9 | 10 | `webpack-config-dev.js`是开发模式下的配置,基本上每一行都有注释,解释了代码的功能和相关插件的作用 11 | (等待后续更新) 12 | 13 | ---------- 14 | 看完config.prod和config.dev,觉得`CRA`的webpack配置真的是解决了大量的issue才能达到今天的优化地步,基本每一次选用插件或者 15 | 修改配置options都有独特的issue。 16 | 17 | 要真正做到理解`CRA`,还需要去理解这些问题的产生,去看一看他们的讨论,要不然以后遇到同样的问题,还要重新去寻求解决办法。 -------------------------------------------------------------------------------- /source-code.react-snapshot/src/index.js: -------------------------------------------------------------------------------- 1 | import ReactDOM from 'react-dom'; 2 | import ReactDOMServer from 'react-dom/server'; 3 | 4 | export const render = (rootComponent, domElement) => { 5 | // 是在Node的jsdom的环境下,并且window.reactSnapshotRender已经创建 6 | if (navigator.userAgent.match(/Node\.js/i) && window && window.reactSnapshotRender) { 7 | // 执行服务端渲染,插入innerHTML中 8 | domElement.innerHTML = ReactDOMServer.renderToString(rootComponent) 9 | // 改变flag 10 | window.reactSnapshotRender() 11 | } else { 12 | ReactDOM.render(rootComponent, domElement) 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /source-code.react-redux/src/utils/isPlainObject.js: -------------------------------------------------------------------------------- 1 | /** 2 | * @param {any} obj The object to inspect. 3 | * @returns {boolean} True if the argument appears to be a plain object. 4 | */ 5 | export default function isPlainObject(obj) { 6 | if (typeof obj !== 'object' || obj === null) return false 7 | 8 | let proto = Object.getPrototypeOf(obj) 9 | if (proto === null) return true 10 | 11 | let baseProto = proto 12 | while (Object.getPrototypeOf(baseProto) !== null) { 13 | baseProto = Object.getPrototypeOf(baseProto) 14 | } 15 | 16 | return proto === baseProto 17 | } 18 | -------------------------------------------------------------------------------- /source-code.ant-design/README.md: -------------------------------------------------------------------------------- 1 | # antd-comments 2 | 3 | 阅读ant-design源码(部分) 4 | 5 | ### 什么是整体? 6 | 7 | 在我们阅读项目源码之前,如果你对它的功能一无所知,那简直是最可怕的事情... 8 | 经常不知不觉就深入其中的逻辑,就像进入一团团迷雾,甚至会觉得有很多重复没必要的东西,完全不知道它们的区别。 9 | 10 | 当然,值的我们阅读的源码,绝大部分每个功能都是有意义的,而极少重复。 11 | 12 | 因此,不能一开始就深入其中,而往往先需要知道功能,会用功能,再去阅读源码。 13 | 14 | ant-design是一个华丽的项目,将最常用组件及其逻辑搭配大量css进行组装, 15 | 我们只需外部调用API,即可轻松搭建美观的界面,同时,ant-design也是可扩展的,底层是react-component, 16 | 更为复杂,功能也更加强大。 17 | 18 | 此项目的理想目的就是希望能从整体入手,除了源码细节注释外,在每一个页面的开头会有一段注释,对当前页面的整体功能做了个介绍, 19 | 如果需要自行配置,只看介绍就可以知道要去哪里细看进行配置;如果需要深入源码,看完整体介绍,再去细看源码, 20 | 能提升阅读效率。 21 | 22 | 23 | -------------------------------------------------------------------------------- /source-code.react-motion/src/stripStyle.js: -------------------------------------------------------------------------------- 1 | /* @flow */ 2 | // turn {x: {val: 1, stiffness: 1, damping: 2}, y: 2} generated by 3 | // `{x: spring(1, {stiffness: 1, damping: 2}), y: 2}` into {x: 1, y: 2} 4 | // 转换x或者y本身或者它的val 5 | 6 | import type {Style, PlainStyle} from './Types'; 7 | 8 | export default function stripStyle(style: Style): PlainStyle { 9 | let ret = {}; 10 | for (const key in style) { 11 | if (!Object.prototype.hasOwnProperty.call(style, key)) { 12 | continue; 13 | } 14 | ret[key] = typeof style[key] === 'number' ? style[key] : style[key].val; 15 | } 16 | return ret; 17 | } 18 | -------------------------------------------------------------------------------- /source-code.hyperapp/README.md: -------------------------------------------------------------------------------- 1 | # source-code.hyperapp 2 | 3 | v1.2.6 4 | 5 | 一个极小的(1kb)类react框架,实现了virtual-dom,diff比较(需要key),数据绑定到actions上,通过actions改变数据,会自动更新页面 6 | 7 | 主要步骤: 8 | * 通过app()对其参数进行处理 9 | * 克隆state(不在原state上修改) 10 | * 增强actions,当调用时会自动检查结果result和原state是否有变化,有变化进行render 11 | * 将state和增强actions绑定到view上 12 | * 初始化render,执行patch 13 | 14 | patch是hyperapp进行节点更新的核心,主要步骤: 15 | * 先判断node节点 16 | * 当节点相同--->进行key判断--->递归patch,直到指针到尾部 17 | * 最后判断是否需要删除节点 18 | * 返回更新的element 19 | 20 | 思维导图(整体): 21 | 22 |  23 | 24 | 思维导图(patch): 25 | 26 |  27 | 28 | [具体源码](./src/hyperapp.js) -------------------------------------------------------------------------------- /source-code.redux-observable/src/utils/console.js: -------------------------------------------------------------------------------- 1 | let deprecationsSeen = {}; 2 | export const resetDeprecationsSeen = () => { 3 | deprecationsSeen = {}; 4 | }; 5 | 6 | const consoleWarn = (typeof console === 'object' && typeof console.warn === 'function') 7 | ? (...args) => console.warn(...args) 8 | : () => { }; 9 | 10 | export const deprecate = msg => { 11 | if (!deprecationsSeen[msg]) { 12 | deprecationsSeen[msg] = true; 13 | consoleWarn(`redux-observable | DEPRECATION: ${msg}`); 14 | } 15 | }; 16 | 17 | export const warn = msg => { 18 | consoleWarn(`redux-observable | WARNING: ${msg}`); 19 | }; 20 | -------------------------------------------------------------------------------- /source-code.redux-observable/src/operators.js: -------------------------------------------------------------------------------- 1 | import { filter } from 'rxjs/operators'; 2 | 3 | const keyHasType = (type, key) => { 4 | return type === key || typeof key === 'function' && type === key.toString(); 5 | }; 6 | 7 | export const ofType = (...keys) => (source) => source.pipe( 8 | filter(({ type }) => { 9 | const len = keys.length; 10 | if (len === 1) { 11 | return keyHasType(type, keys[0]); 12 | } else { 13 | for (let i = 0; i < len; i++) { 14 | if (keyHasType(type, keys[i])) { 15 | return true; 16 | } 17 | } 18 | } 19 | return false; 20 | }) 21 | ); 22 | -------------------------------------------------------------------------------- /source-code.ant-design/src/card/Grid.md: -------------------------------------------------------------------------------- 1 | ### Card.Grid 2 | 3 | 整体: 4 | * 就是按默认宽度33%(如果未自定义,一行最多放3个)放置 5 | 6 | 源码: 7 | ```jsx 8 | import * as React from 'react'; 9 | import classNames from 'classnames'; 10 | 11 | export interface CardGridProps { 12 | prefixCls?: string; 13 | style?: React.CSSProperties; 14 | className?: string; 15 | } 16 | //div 默认宽度33% 左浮动,hover有效果 17 | export default (props: CardGridProps) => { 18 | const { prefixCls = 'ant-card', className, ...others } = props; 19 | const classString = classNames(`${prefixCls}-grid`, className); 20 | return
; 21 | }; 22 | 23 | ``` -------------------------------------------------------------------------------- /source-code.react-waypoint/src/ensureChildrenIsValid.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | 3 | export const errorMessage = 4 | '