点击进入GitHub仓库 (欢迎来star、提pr哦!)css
点击进入项目上线地址 项目支持PWA,点击chrome或者safari浏览器的添加至主屏幕,便可在桌面跟App同样以图标形式访问,体验如丝滑般流畅:)html
首先说一说为何要作这样一个React开源项目:前端
一、后端接口和文档完整,你们都知道开发一个产品毫不仅仅是前端一我的的活,须要花大量的时间和后端沟通,商讨数据接口的形式,最终作成文档并以此为依据开发。而如今github已经有很是成熟的抓取网易云音乐服务端的接口,不只在与时俱进地不断更新接口,并且文档写的也很是完善,用这样的真实数据接口能够大大方便咱们进行前端的开发,大大下降了咱们开发前端的成本。vue
二、React Hooks现在可谓前端界"当红小生", 因其API简洁性、逻辑复用性等特性逐渐被开发者所应用,将来的vue3.0也是采用相似的Function Based的模式,所以学习React Hooks也是将来的大趋势,经过一个具体的项目来实践、应用hooks特性,我以为比干啃文档要强太多,而且在实践的过程当中会遇到一些坑,经过坑驱动来学习,能够加深咱们对于hooks原理的理解。react
三、把Redux和不可变数据结合也是react性能优化的一个重要的手段,我很早就想用Redux结合Facebook开源的一款不可变数据结构库immutable.js来开发,因此经过这个项目来具体地实践一把。ios
一、 首先在这个项目发出时,我就已经作了一个Promise, 拆解文章必定会出来,这是直接缘由。git
二、 我相信这个系列出来可以帮助很多的前端开发者,可以经过本身的才华和努力影响一批人,我以为这原本就是一件很是有成就感的事情。es6
三、 输出倒逼输入。这个项目不是我一切准备就绪才开始开发的,而是一步步尝试、不断学新的东西,才得以呈现如今的效果。我想写拆解文章复盘,也是这样一个过程,让本身可以不断产生新的想法,而后去尝试,对本身自己也是一种成长。github
这是咱们即将开发的版本,你们能够看到,这个项目仍是稍微有一些复杂的,相信你们跟着作完会有很是大的收获。web
react v16.8
: 用于构建用户界面的 MVVM 框架redux
: 著名JavaScript状态管理容器redux-thunk
: 处理异步逻辑的redux中间件immutable
: Facebook历时三年开发出的进行持久性数据结构处理的库 (它和memo、Redux搭配就是神器,memo包裹函数组件跟PureComponent是同样的效果,在组件更新前进行数据的浅层比较,具体请参考这篇文章当 PureComponent 赶上 ImmutableJS)react-lazyload
: react懒加载库better-scroll
: 提高移动端滑动体验的知名库styled-components
: 处理样式,体现css in js的前端工程化神器(详情请移步我以前的文章styled-components:前端组件拆分新思路)axios
: 用来请求后端api的数据在开始这个项目以前,我有必要强调一个这个项目工程的开发规范和我我的的编码风格,提早告知一下,我这么作也是有本身充分的理由的,让项目可读性和可维护性尽量高,但愿后面看到一些奇葩的操做不要感到奇怪。
一、class组件再也不用,全面拥抱hooks,统一用函数组件。
二、组件内部状态用hooks处理,凡是业务数据所有放在redux中管理。
三、ajax请求以及后续数据处理的具体代码所有放在actionCreator中,由redux-thunk进行处理,尽量精简组件代码。
四、每个容器组件都有本身独立的reducer,而后再全局的store下经过redux的combineReducer方法合并。
五、JS变量名(包括函数名)采用小驼峰的方式,组件名或者styled-components导出的样式容器名都采用大驼峰,常量名全部字母大写。
六、普通CSS类名所有用英语小写,单词间用下划线链接,CSS动画钩子类名中单词用-链接。
七、凡是props中有数据的,所有在组件最前面提早解构赋值,而且,得到的属性名和方法名要分开声明,从父组件得到的props和经过react-redux中映射得到的props也要分开声明。
八、useEffect统一写在最前面,而且紧跟着props解构赋值代码后面。
九、凡是负责返回JSX的函数,统一汇集在函数最后面,中间不要穿插事件处理函数和其余逻辑。
十、mapDispatchToProps返回的函数中,函数名格式为xxxDispatch,以避免和现有action名冲突。
看到这里你是否是有一点心动?哈哈,别高兴的太早。其实要掌握这些内容着实不容易,要经历的还有不少不少,我我的能力也有限,没法保证你100%可以消化掉这些东西,但我惟一能够保证的是:
这个系列拆解文章我会百分之百地投入,将我在开发中所经历的坑和解决问题的过程毫无保留地分享给各位,对于一些你们可能会感到陌生的概念和语法都会一五一十地摊开来讲,作到真正的"手摸手"。对于里面涉及的代码,我首先会再markdown中本身写一遍,而后把本身看成小白,对照vuepress博客的开发界面再本身从头至尾实现一遍,给你们足够的技术安全感。
可是本系列拆解文章也不是针对前端纯小白的,因为基础部分过于科普太多基础内容不少小伙伴会厌倦,因此须要你有必定的前端知识的储备,具体来讲是指CSS经常使用的布局方式和属性,原生JavaScript的基础,ES6的经常使用语法,React和Redux的基本使用。
若是有些你还不会,我推荐你先去学习一下这些资料:
本小节代码你们能够去参考GitHub仓库chapter1分支。传送门
首先经过create-react-app这个脚手架工具生成项目的初始化化结构,在命令行中输入如下命令:
create-react-app cloud-music
复制代码
完成后,根据提示:
cd cloud-music
复制代码
启动项目:
npm start
复制代码
开始这个项目以前,咱们须要对目录进行一下改造。以下(主要针对src目录):
├─api // 网路请求代码、工具类函数和相关配置
├─application // 项目核心功能
├─assets // 字体配置及全局样式
├─baseUI // 基础UI轮子
├─components // 可复用的UI组件
├─routes // 路由配置文件
└─store // redux相关文件
App.js // 根组件
index.js // 入口文件
serviceWorker.js // PWA离线应用配置
style.js // 默认样式
复制代码
脚手架生成的无用文件已经删除,你们注意也把相关的引入语句也删除。目前应该是整个应用的最终工程目录,之后的开发都会基于这个目录结构进行。
本项目的样式采用styled-components来进行开发,也就是利用css in js的方式,我为何要这么作,有兴趣的同窗能够阅读一下我以前在掘金写的文章styled-components:前端组件拆分新思路。固然后面有人看了个人项目后给我提了这个库的一些缺点,但我依然坚持用它进行开发,由于它在工程化方面的优点依然很是明显,并且大部分缺点咱们也能够有意识的去避开,这个具体在后面的章节里面再说吧。
其实styled-components的使用是至关简单的,不须要额外专门的学习,因此你们跟着我写一遍,熟悉一下就好了。
不知道你有没有发现一个问题,上面目录中默认样式文件是style.js,而不是.css,没错,这就是使用了styled-components后的结果。
咱们先安装这个库:
npm install styled-components --save
复制代码
在刚刚的style.js中,
import { createGlobalStyle } from 'styled-components';
export const GlobalStyle = createGlobalStyle` html, body, div, span, applet, object, iframe, h1, h2, h3, h4, h5, h6, p, blockquote, pre, a, abbr, acronym, address, big, cite, code, del, dfn, em, img, ins, kbd, q, s, samp, small, strike, strong, sub, sup, tt, var, b, u, i, center, dl, dt, dd, ol, ul, li, fieldset, form, label, legend, table, caption, tbody, tfoot, thead, tr, th, td, article, aside, canvas, details, embed, figure, figcaption, footer, header, hgroup, menu, nav, output, ruby, section, summary, time, mark, audio, video { margin: 0; padding: 0; border: 0; font-size: 100%; font: inherit; vertical-align: baseline; } /* HTML5 display-role reset for older browsers */ article, aside, details, figcaption, figure, footer, header, hgroup, menu, nav, section { display: block; } body { line-height: 1; } html, body{ background: #f2f3f4;; } ol, ul { list-style: none; } blockquote, q { quotes: none; } blockquote:before, blockquote:after, q:before, q:after { content: ''; content: none; } table { border-collapse: collapse; border-spacing: 0; } a{ text-decoration: none; color: #fff; } `
复制代码
这就是styled-components建立全局样式并导出的代码。
这段代码导出到哪里去呢?导入到App.js中。
//App.js中添加这一句
import { GlobalStyle } from './style';
复制代码
咱们继续来引入字体图标文件,这里的字体图标是采用的阿里图标库地址
选择好图标以后下载至本地(本项目下载unicode模式)。这个操做不属于本项目的重点,也过于简单,就不在这浪费篇幅了。
在assets目录下新建一个名为iconfont的文件夹, 将.css, .eot, .svg, .ttf, .woff为后缀的文件放到这个文件夹中。 而后将这个css文件作一些手脚,须要改为js代码。
因此如今的iconfont.css须要改为iconfont.js,这里作了一些省略,具体代码你们直接看GitHub仓库chapter1分支吧。
import {createGlobalStyle} from 'styled-components';
export const IconStyle = createGlobalStyle` @font-face {font-family: "iconfont"; src: url('iconfont.eot?t=1565320061289'); /* IE9 */ src: url('iconfont.eot?t=1565320061289#iefix' ...省略base64巨长字符) format('embedded-opentype'), /* IE6-IE8 */ url('data:application/x-font-woff2;charset=utf-8) format('woff2'), url('iconfont.woff?t=1565320061289') format('woff'), url('iconfont.ttf?t=1565320061289') format('truetype'), /* chrome, firefox, opera, Safari, Android, iOS 4.2+ */ url('iconfont.svg?t=1565320061289#iconfont') format('svg'); /* iOS 4.1- */ } .iconfont { font-family: "iconfont" !important; font-size: 16px; font-style: normal; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; } ... `
复制代码
接下来,我们把字体引入App.js中。
//App.js
import React from 'react';
import { IconStyle } from './assets/iconfont/iconfont';
import { GlobalStyle } from './style';
function App() {
return (
<div className="App"> <GlobalStyle></GlobalStyle> <IconStyle></IconStyle> <i className="iconfont"></i> </div>
);
}
export default App;
复制代码
接下来你们打开页面能够看到一个小小的放大镜,背景变为浅灰色,字体图标和默认样式起到了效果。
到此为止,默认样式和字体图标就算一同引入到了项目中。你们可能会字体图标的用法有了了解,可是中间的unicode编码怎么来的呢?别担忧,我专门在iconfont文件夹中放了demo_index.html文件,打开便能索引不一样图标的unicode值啦。