├── JueJin ├── src │ ├── api │ │ └── api.js │ ├── store │ │ └── index.js │ ├── assets │ │ └── img │ │ │ ├── ad-ali.jpg │ │ │ ├── ad-tencent.jpg │ │ │ ├── icon_good.png │ │ │ ├── icon_notice.png │ │ │ ├── icon_comment.png │ │ │ ├── 404_not_found_1.png │ │ │ ├── 404_not_found_2.png │ │ │ ├── 404_not_found_3.png │ │ │ ├── 404_not_found_4.png │ │ │ ├── icon_search.svg │ │ │ ├── icon_search_active.svg │ │ │ └── logo.svg │ ├── styles │ │ ├── index.css │ │ ├── common.css │ │ ├── icon.css │ │ └── reset.css │ ├── index.js │ ├── App.js │ ├── pages │ │ ├── 404 │ │ │ ├── index.js │ │ │ └── index.css │ │ └── TimeLine │ │ │ ├── index.js │ │ │ ├── components │ │ │ ├── Nav.js │ │ │ ├── RightRecommend.js │ │ │ └── leftList.js │ │ │ └── index.css │ └── components │ │ └── Header │ │ ├── index.js │ │ └── index.css ├── public │ ├── mock │ │ └── index.json │ ├── favicon.ico │ └── index.html ├── .gitignore ├── .vscode │ └── launch.json ├── package.json └── README.md ├── JianShu ├── src │ ├── index.css │ ├── pages │ │ ├── detail │ │ │ ├── index.css │ │ │ └── index.js │ │ └── home │ │ │ ├── store │ │ │ ├── actionTypes.js │ │ │ ├── index.js │ │ │ ├── reducer.js │ │ │ └── actionCreators.js │ │ │ ├── index.js │ │ │ ├── components │ │ │ ├── TopNav.js │ │ │ ├── RightRecommend.js │ │ │ └── LeftList.js │ │ │ └── index.css │ ├── resources │ │ └── img │ │ │ ├── ad-ali.jpg │ │ │ ├── icon-home.png │ │ │ ├── ad-tencent.jpg │ │ │ ├── header-home.png │ │ │ ├── icon-change.png │ │ │ ├── icon-search.png │ │ │ ├── icon-write.png │ │ │ └── icon-download.png │ ├── common │ │ └── header │ │ │ ├── store │ │ │ ├── index.js │ │ │ ├── actionTypes.js │ │ │ ├── reducer.js │ │ │ └── actionCreators.js │ │ │ ├── index.css │ │ │ └── index.js │ ├── index.js │ ├── store │ │ ├── reducer.js │ │ └── index.js │ ├── App.js │ ├── common.css │ └── reset.css ├── public │ ├── favicon.ico │ ├── api │ │ ├── headerList.json │ │ ├── rightRecommendAuthor.json │ │ └── leftList.json │ └── index.html ├── .gitignore ├── package.json └── README.md ├── Simplify ├── public │ ├── favicon.ico │ └── index.html ├── src │ ├── index.js │ └── App.js ├── .gitignore ├── package.json └── README.md ├── TodoList ├── public │ ├── favicon.ico │ └── index.html ├── src │ ├── style.css │ ├── index.js │ ├── TodoItem.js │ └── TodoList.js ├── .gitignore ├── package.json └── README.md ├── TodoListUpgrade ├── React-Redux │ ├── public │ │ ├── favicon.ico │ │ └── index.html │ ├── src │ │ ├── store │ │ │ ├── index.js │ │ │ └── reducer.js │ │ ├── index.js │ │ ├── index.css │ │ └── TodoList.js │ ├── .gitignore │ ├── package.json │ └── README.md ├── Redux-Base │ ├── public │ │ ├── favicon.ico │ │ └── index.html │ ├── src │ │ ├── index.js │ │ ├── store │ │ │ ├── actionTypes.js │ │ │ ├── index.js │ │ │ ├── actionCreators.js │ │ │ └── reducer.js │ │ ├── index.css │ │ ├── TodoListUI.js │ │ └── TodoList.js │ ├── .gitignore │ └── package.json ├── Redux-Saga │ ├── public │ │ ├── favicon.ico │ │ └── index.html │ ├── src │ │ ├── index.js │ │ ├── store │ │ │ ├── actionTypes.js │ │ │ ├── index.js │ │ │ ├── actionCreators.js │ │ │ ├── reducer.js │ │ │ └── sagas.js │ │ ├── index.css │ │ ├── TodoListUI.js │ │ └── TodoList.js │ ├── .gitignore │ └── package.json ├── Redux-Thunk │ ├── public │ │ ├── favicon.ico │ │ └── index.html │ ├── src │ │ ├── index.js │ │ ├── store │ │ │ ├── actionTypes.js │ │ │ ├── index.js │ │ │ ├── reducer.js │ │ │ └── actionCreators.js │ │ ├── index.css │ │ ├── TodoListUI.js │ │ └── TodoList.js │ ├── .gitignore │ └── package.json └── README.md ├── .gitignore └── README.md /JueJin/src/api/api.js: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /JueJin/src/store/index.js: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /JueJin/public/mock/index.json: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /JianShu/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | background: #f4f5f5; 3 | } -------------------------------------------------------------------------------- /JianShu/src/pages/detail/index.css: -------------------------------------------------------------------------------- 1 | .container { 2 | margin-top: 100px; 3 | } -------------------------------------------------------------------------------- /JianShu/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/public/favicon.ico -------------------------------------------------------------------------------- /JueJin/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/public/favicon.ico -------------------------------------------------------------------------------- /Simplify/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/Simplify/public/favicon.ico -------------------------------------------------------------------------------- /TodoList/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/TodoList/public/favicon.ico -------------------------------------------------------------------------------- /JueJin/src/assets/img/ad-ali.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/ad-ali.jpg -------------------------------------------------------------------------------- /TodoList/src/style.css: -------------------------------------------------------------------------------- 1 | .icon-close { 2 | font-size: 1.2em; 3 | color: deepskyblue; 4 | margin-left: 10px; 5 | } -------------------------------------------------------------------------------- /JianShu/src/resources/img/ad-ali.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/ad-ali.jpg -------------------------------------------------------------------------------- /JueJin/src/assets/img/ad-tencent.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/ad-tencent.jpg -------------------------------------------------------------------------------- /JueJin/src/assets/img/icon_good.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/icon_good.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/icon_notice.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/icon_notice.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/icon-home.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/icon-home.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/icon_comment.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/icon_comment.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/ad-tencent.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/ad-tencent.jpg -------------------------------------------------------------------------------- /JianShu/src/resources/img/header-home.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/header-home.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/icon-change.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/icon-change.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/icon-search.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/icon-search.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/icon-write.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/icon-write.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/404_not_found_1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/404_not_found_1.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/404_not_found_2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/404_not_found_2.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/404_not_found_3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/404_not_found_3.png -------------------------------------------------------------------------------- /JueJin/src/assets/img/404_not_found_4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JueJin/src/assets/img/404_not_found_4.png -------------------------------------------------------------------------------- /JianShu/src/resources/img/icon-download.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/JianShu/src/resources/img/icon-download.png -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/TodoListUpgrade/React-Redux/public/favicon.ico -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/TodoListUpgrade/Redux-Base/public/favicon.ico -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/TodoListUpgrade/Redux-Saga/public/favicon.ico -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/LiangJunrong/React/HEAD/TodoListUpgrade/Redux-Thunk/public/favicon.ico -------------------------------------------------------------------------------- /JianShu/src/pages/home/store/actionTypes.js: -------------------------------------------------------------------------------- 1 | export const GET_LEFT_LIST = 'home/get_left_list'; 2 | export const GET_RIGHT_RECOMMEND_AUTHOR = 'home/get_right_recommend_author'; -------------------------------------------------------------------------------- /Simplify/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import App from './App'; 4 | 5 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoList/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import TodoList from './TodoList'; 4 | 5 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { createStore } from 'redux'; 2 | import reducer from './reducer'; 3 | 4 | const store = createStore(reducer); 5 | 6 | export default store; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import TodoList from './TodoList'; 4 | 5 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import TodoList from './TodoList'; 4 | 5 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import TodoList from './TodoList'; 4 | 5 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /JianShu/src/pages/home/store/index.js: -------------------------------------------------------------------------------- 1 | import * as actionCreators from './actionCreators'; 2 | import * as actionTypes from './actionTypes'; 3 | import reducer from './reducer'; 4 | 5 | export { actionCreators, actionTypes, reducer }; -------------------------------------------------------------------------------- /JianShu/src/common/header/store/index.js: -------------------------------------------------------------------------------- 1 | import * as actionCreators from './actionCreators'; 2 | import * as actionTypes from './actionTypes'; 3 | import reducer from './reducer'; 4 | 5 | export { actionCreators, actionTypes, reducer }; -------------------------------------------------------------------------------- /JueJin/src/styles/index.css: -------------------------------------------------------------------------------- 1 | html { 2 | background: #f4f5f5; 3 | color: #333; 4 | } 5 | a { 6 | color: #71777c; 7 | } 8 | #root { 9 | position: relative; 10 | margin: 0 auto; 11 | width: 100%; 12 | max-width: 960px; 13 | } -------------------------------------------------------------------------------- /JianShu/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import App from './App'; 4 | import './reset.css'; 5 | import './index.css'; 6 | import './common.css'; 7 | 8 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/store/actionTypes.js: -------------------------------------------------------------------------------- 1 | export const CHANGE_INPUT_VALUE = 'change_input_value'; 2 | export const ADD_TODO_ITEM = 'add_todo_item'; 3 | export const DELETE_TODO_ITEM = 'delete_todo_item'; 4 | export const INIT_LIST_ACTION = 'init_list_action'; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/store/actionTypes.js: -------------------------------------------------------------------------------- 1 | export const CHANGE_INPUT_VALUE = 'change_input_value'; 2 | export const ADD_TODO_ITEM = 'add_todo_item'; 3 | export const DELETE_TODO_ITEM = 'delete_todo_item'; 4 | export const INIT_LIST_ACTION = 'init_list_action'; -------------------------------------------------------------------------------- /JueJin/src/styles/common.css: -------------------------------------------------------------------------------- 1 | .text-center { /* 文本居中 */ 2 | text-align: center; 3 | } 4 | .show { /* 显示 */ 5 | display: inline-block; 6 | } 7 | .hide { /* 隐藏 */ 8 | display: none; 9 | } 10 | .hot { 11 | color: red; 12 | } 13 | .purple { 14 | color: #b71ed7; 15 | } -------------------------------------------------------------------------------- /Simplify/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | 3 | class App extends Component { 4 | render() { 5 | return ( 6 |
7 | Hello React! 8 |
9 | ); 10 | } 11 | } 12 | 13 | export default App; 14 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { createStore } from 'redux'; 2 | import reducer from './reducer'; 3 | 4 | const store = createStore( 5 | reducer, 6 | window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__() 7 | ); 8 | 9 | export default store; -------------------------------------------------------------------------------- /JianShu/src/pages/detail/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import './index.css'; 3 | 4 | class Detail extends Component { 5 | render() { 6 | return ( 7 |
8 | Detail 9 |
10 | ) 11 | } 12 | } 13 | 14 | export default Detail; -------------------------------------------------------------------------------- /JianShu/public/api/headerList.json: -------------------------------------------------------------------------------- 1 | { 2 | "code": 0, 3 | "list": ["区块链","小程序","vue","毕业","PHP","故事","flutter","理财","美食","投稿","手帐","书法","PPT","穿搭","打碗碗花","简书","姥姥的澎湖湾","设计","创业","交友","籽盐","教育","思维导图","疯哥哥","梅西","时间管理","golang","连载","自律","职场","考研","慢世人","悦欣","一纸vr","spring","eos","足球","程序员","林露含","彩铅","金融","木风杂谈","日更","成长","外婆是方言","docker"] 4 | } -------------------------------------------------------------------------------- /JueJin/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import App from './App'; 4 | 5 | // 引入初始化样式和公用样式 6 | import './styles/reset.css'; 7 | import './styles/index.css'; 8 | import './styles/common.css'; 9 | import './styles/icon.css'; 10 | 11 | ReactDOM.render(, document.getElementById('root')); -------------------------------------------------------------------------------- /JianShu/src/store/reducer.js: -------------------------------------------------------------------------------- 1 | import { combineReducers } from 'redux-immutable'; 2 | import { reducer as headerReducer } from '../common/header/store'; 3 | import { reducer as homeReducer } from '../pages/home/store'; 4 | 5 | const reducer = combineReducers({ 6 | header: headerReducer, 7 | home: homeReducer, 8 | }) 9 | 10 | export default reducer; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/store/actionTypes.js: -------------------------------------------------------------------------------- 1 | export const CHANGE_INPUT_VALUE = 'change_input_value'; 2 | export const ADD_TODO_ITEM = 'add_todo_item'; 3 | export const DELETE_TODO_ITEM = 'delete_todo_item'; 4 | export const INIT_LIST_ACTION = 'init_list_action'; 5 | // 4. 定义 GET_INIT_LIST 并导出给 actionTypes.js 使用 6 | export const GET_INIT_LIST = 'get_init_list'; -------------------------------------------------------------------------------- /JianShu/src/common/header/store/actionTypes.js: -------------------------------------------------------------------------------- 1 | export const SEARCH_FOCUS = 'header/search_focus'; 2 | export const SEARCH_BLUR = 'header/search_blur'; 3 | export const GET_LIST = 'header/get_list'; 4 | export const ON_MOUSE_ENTER_HOT = 'header/on_mouse_enter_hot'; 5 | export const ON_MOUSE_LEAVE_HOT = 'header/on_mouse_leave_hot'; 6 | export const CHANGE_PAGE = 'header/change_page'; 7 | -------------------------------------------------------------------------------- /JianShu/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { createStore, compose, applyMiddleware } from 'redux'; 2 | import thunk from 'redux-thunk'; 3 | import reducer from './reducer'; 4 | 5 | const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose; 6 | 7 | const store = createStore(reducer, composeEnhancers( 8 | applyMiddleware(thunk) 9 | )); 10 | 11 | export default store; -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import TodoList from './TodoList'; 4 | import { Provider } from 'react-redux'; 5 | import store from './store'; 6 | 7 | const App = ( 8 | 9 | 10 | 11 | ) 12 | 13 | ReactDOM.render(App, document.getElementById('root')); -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/src/index.css: -------------------------------------------------------------------------------- 1 | .todo { 2 | width: 1000px; 3 | margin: 20px auto 0; 4 | padding: 30px; 5 | border: 1px solid #ccc; 6 | border-radius: 10px; 7 | } 8 | .todo-title { 9 | text-align: center; 10 | } 11 | .todo-action .todo-input { 12 | width: 200px; 13 | } 14 | .todo-action .todo-submit { 15 | margin-left: 10px; 16 | } 17 | .todo-list { 18 | margin-top: 30px; 19 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/index.css: -------------------------------------------------------------------------------- 1 | .todo { 2 | width: 1000px; 3 | margin: 20px auto 0; 4 | padding: 30px; 5 | border: 1px solid #ccc; 6 | border-radius: 10px; 7 | } 8 | .todo-title { 9 | text-align: center; 10 | } 11 | .todo-action .todo-input { 12 | width: 200px; 13 | } 14 | .todo-action .todo-submit { 15 | margin-left: 10px; 16 | } 17 | .todo-list { 18 | margin-top: 30px; 19 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/index.css: -------------------------------------------------------------------------------- 1 | .todo { 2 | width: 1000px; 3 | margin: 20px auto 0; 4 | padding: 30px; 5 | border: 1px solid #ccc; 6 | border-radius: 10px; 7 | } 8 | .todo-title { 9 | text-align: center; 10 | } 11 | .todo-action .todo-input { 12 | width: 200px; 13 | } 14 | .todo-action .todo-submit { 15 | margin-left: 10px; 16 | } 17 | .todo-list { 18 | margin-top: 30px; 19 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/index.css: -------------------------------------------------------------------------------- 1 | .todo { 2 | width: 1000px; 3 | margin: 20px auto 0; 4 | padding: 30px; 5 | border: 1px solid #ccc; 6 | border-radius: 10px; 7 | } 8 | .todo-title { 9 | text-align: center; 10 | } 11 | .todo-action .todo-input { 12 | width: 200px; 13 | } 14 | .todo-action .todo-submit { 15 | margin-left: 10px; 16 | } 17 | .todo-list { 18 | margin-top: 30px; 19 | } -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /JianShu/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* -------------------------------------------------------------------------------- /JueJin/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /TodoList/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* -------------------------------------------------------------------------------- /Simplify/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /JueJin/src/styles/icon.css: -------------------------------------------------------------------------------- 1 | .icon { 2 | display: inline-block; 3 | } 4 | .icon-notice { 5 | background: url('../assets/img/icon_notice.png') no-repeat center; 6 | background-size: 100%; 7 | } 8 | .icon-good { 9 | background: url('../assets/img/icon_good.png') no-repeat center; 10 | background-size: 100% 100%; 11 | } 12 | .icon-comment { 13 | background: url('../assets/img/icon_comment.png') no-repeat center; 14 | background-size: 100% 100%; 15 | } -------------------------------------------------------------------------------- /Simplify/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoList/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /JianShu/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | 简书 - 创作你的创作 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | Todolist 11 | 12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { createStore, applyMiddleware, compose } from 'redux'; 2 | import reducer from './reducer'; 3 | import thunk from 'redux-thunk'; 4 | 5 | const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ ? window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__({}) : compose; 6 | 7 | const enhancer = composeEnhancers( 8 | applyMiddleware(thunk), 9 | ); 10 | 11 | const store = createStore( 12 | reducer, 13 | enhancer 14 | ); 15 | 16 | export default store; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/store/actionCreators.js: -------------------------------------------------------------------------------- 1 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION } from './actionTypes'; 2 | 3 | export const getChangeInputValue = (value) => ({ 4 | type: CHANGE_INPUT_VALUE, 5 | value 6 | }) 7 | 8 | export const getAddTodoItem = () => ({ 9 | type: ADD_TODO_ITEM 10 | }) 11 | 12 | export const getDeleteTodoItem = (index) => ({ 13 | type: DELETE_TODO_ITEM, 14 | index 15 | }) 16 | 17 | export const initListAction = (data) => ({ 18 | type: INIT_LIST_ACTION, 19 | data 20 | }) -------------------------------------------------------------------------------- /JianShu/src/pages/home/store/reducer.js: -------------------------------------------------------------------------------- 1 | import * as actionTypes from './actionTypes' 2 | import { fromJS } from 'immutable'; 3 | 4 | const defaultState = fromJS({ 5 | leftNav: [], 6 | rightRecommend: [], 7 | }) 8 | 9 | export default (state = defaultState, action) => { 10 | switch(action.type) { 11 | case actionTypes.GET_LEFT_LIST: 12 | return state.set('leftNav', action.data); 13 | case actionTypes.GET_RIGHT_RECOMMEND_AUTHOR: 14 | return state.set('rightRecommend', action.data); 15 | default: 16 | return state; 17 | } 18 | } -------------------------------------------------------------------------------- /JianShu/src/pages/home/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import LeftList from './components/LeftList'; 3 | import RightRecommend from './components/RightRecommend'; 4 | import TopNav from './components/TopNav'; 5 | import './index.css'; 6 | 7 | class Home extends Component { 8 | render() { 9 | return ( 10 |
11 | 12 |
13 | 14 | 15 |
16 |
17 | ) 18 | } 19 | } 20 | 21 | export default Home; -------------------------------------------------------------------------------- /TodoList/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.8.4", 7 | "react-dom": "^16.8.4", 8 | "react-scripts": "2.1.8" 9 | }, 10 | "scripts": { 11 | "start": "react-scripts start", 12 | "build": "react-scripts build", 13 | "test": "react-scripts test", 14 | "eject": "react-scripts eject" 15 | }, 16 | "eslintConfig": { 17 | "extends": "react-app" 18 | }, 19 | "browserslist": [ 20 | ">0.2%", 21 | "not dead", 22 | "not ie <= 11", 23 | "not op_mini all" 24 | ] 25 | } -------------------------------------------------------------------------------- /Simplify/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.8.4", 7 | "react-dom": "^16.8.4", 8 | "react-scripts": "2.1.8" 9 | }, 10 | "scripts": { 11 | "start": "react-scripts start", 12 | "build": "react-scripts build", 13 | "test": "react-scripts test", 14 | "eject": "react-scripts eject" 15 | }, 16 | "eslintConfig": { 17 | "extends": "react-app" 18 | }, 19 | "browserslist": [ 20 | ">0.2%", 21 | "not dead", 22 | "not ie <= 11", 23 | "not op_mini all" 24 | ] 25 | } 26 | -------------------------------------------------------------------------------- /TodoList/src/TodoItem.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react' 2 | 3 | class TodoItem extends Component { 4 | 5 | constructor(props) { 6 | super(props); 7 | // 这种写法可以节省性能 8 | this.handleClick = this.handleClick.bind(this); 9 | } 10 | 11 | render() { 12 | const { item } = this.props; 13 | return ( 14 |
  • 15 | {item} 16 | X 17 |
  • 18 | ) 19 | } 20 | 21 | handleClick() { 22 | const { handleItemDelete, index } = this.props; 23 | handleItemDelete(index); 24 | } 25 | 26 | } 27 | 28 | export default TodoItem; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { createStore, applyMiddleware, compose } from 'redux'; 2 | import reducer from './reducer'; 3 | import createSagaMiddleware from 'redux-saga'; 4 | import todoSaga from './sagas'; 5 | 6 | const sagaMiddleware = createSagaMiddleware(); 7 | 8 | const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ ? window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__({}) : compose; 9 | 10 | const enhancer = composeEnhancers( 11 | applyMiddleware(sagaMiddleware), 12 | ); 13 | 14 | const store = createStore( 15 | reducer, 16 | enhancer 17 | ); 18 | 19 | sagaMiddleware.run(todoSaga); 20 | 21 | export default store; -------------------------------------------------------------------------------- /JueJin/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Fragment } from 'react'; 2 | import { BrowserRouter, Route, Switch, Redirect } from 'react-router-dom'; 3 | import Header from './components/Header'; 4 | import TimeLine from './pages/TimeLine'; 5 | import NotFound from './pages/404'; 6 | 7 | function App() { 8 | return ( 9 | 10 | 11 |
    12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | ); 20 | } 21 | 22 | export default App; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "antd": "^3.16.1", 7 | "axios": "^0.18.0", 8 | "react": "^16.8.4", 9 | "react-dom": "^16.8.4", 10 | "react-scripts": "2.1.8", 11 | "redux": "^4.0.1" 12 | }, 13 | "scripts": { 14 | "start": "react-scripts start", 15 | "build": "react-scripts build", 16 | "test": "react-scripts test", 17 | "eject": "react-scripts eject" 18 | }, 19 | "eslintConfig": { 20 | "extends": "react-app" 21 | }, 22 | "browserslist": [ 23 | ">0.2%", 24 | "not dead", 25 | "not ie <= 11", 26 | "not op_mini all" 27 | ] 28 | } 29 | -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "antd": "^3.16.1", 7 | "react": "^16.8.4", 8 | "react-dom": "^16.8.4", 9 | "react-redux": "^6.0.1", 10 | "react-scripts": "2.1.8", 11 | "redux": "^4.0.1" 12 | }, 13 | "scripts": { 14 | "start": "react-scripts start", 15 | "build": "react-scripts build", 16 | "test": "react-scripts test", 17 | "eject": "react-scripts eject" 18 | }, 19 | "eslintConfig": { 20 | "extends": "react-app" 21 | }, 22 | "browserslist": [ 23 | ">0.2%", 24 | "not dead", 25 | "not ie <= 11", 26 | "not op_mini all" 27 | ] 28 | } 29 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/store/actionCreators.js: -------------------------------------------------------------------------------- 1 | // 2. 导入 actionTypes.js 中的 GET_INIT_LIST 2 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION, GET_INIT_LIST } from './actionTypes'; 3 | 4 | export const getChangeInputValue = (value) => ({ 5 | type: CHANGE_INPUT_VALUE, 6 | value 7 | }) 8 | 9 | export const getAddTodoItem = () => ({ 10 | type: ADD_TODO_ITEM 11 | }) 12 | 13 | export const getDeleteTodoItem = (index) => ({ 14 | type: DELETE_TODO_ITEM, 15 | index 16 | }) 17 | 18 | export const initListAction = (data) => ({ 19 | type: INIT_LIST_ACTION, 20 | data 21 | }) 22 | 23 | // 3. 使用 GET_INIT_LIST 24 | export const getInitList = () => ({ 25 | type: GET_INIT_LIST 26 | }); -------------------------------------------------------------------------------- /JianShu/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { Provider } from 'react-redux'; 3 | import Header from './common/header'; 4 | import store from './store'; 5 | import { BrowserRouter, Route } from 'react-router-dom'; 6 | import Home from './pages/home'; 7 | import Detail from './pages/detail'; 8 | 9 | class App extends Component { 10 | render() { 11 | return ( 12 | 13 |
    14 | 15 | 16 | 17 | 18 | 19 | ); 20 | } 21 | } 22 | 23 | export default App; -------------------------------------------------------------------------------- /JianShu/src/common.css: -------------------------------------------------------------------------------- 1 | .icon { 2 | display: inline-block; 3 | width: 20px; 4 | height: 21px; 5 | margin-right: 5px; 6 | } 7 | .icon-home { 8 | background: url('./resources/img/icon-home.png') no-repeat center; 9 | background-size: 100%; 10 | } 11 | .icon-write { 12 | background: url('./resources/img/icon-write.png') no-repeat center; 13 | background-size: 100%; 14 | } 15 | .icon-download { 16 | background: url('./resources/img/icon-download.png') no-repeat center; 17 | background-size: 100%; 18 | } 19 | .icon-search { 20 | background: url('./resources/img/icon-search.png') no-repeat center; 21 | background-size: 100%; 22 | } 23 | .display-hide { 24 | display: none; 25 | } 26 | .display-show { 27 | display: block; 28 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "antd": "^3.16.1", 7 | "axios": "^0.18.0", 8 | "react": "^16.8.4", 9 | "react-dom": "^16.8.4", 10 | "react-scripts": "2.1.8", 11 | "redux": "^4.0.1", 12 | "redux-saga": "^1.0.2" 13 | }, 14 | "scripts": { 15 | "start": "react-scripts start", 16 | "build": "react-scripts build", 17 | "test": "react-scripts test", 18 | "eject": "react-scripts eject" 19 | }, 20 | "eslintConfig": { 21 | "extends": "react-app" 22 | }, 23 | "browserslist": [ 24 | ">0.2%", 25 | "not dead", 26 | "not ie <= 11", 27 | "not op_mini all" 28 | ] 29 | } 30 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "todolist", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "antd": "^3.16.1", 7 | "axios": "^0.18.0", 8 | "react": "^16.8.4", 9 | "react-dom": "^16.8.4", 10 | "react-scripts": "2.1.8", 11 | "redux": "^4.0.1", 12 | "redux-thunk": "^2.3.0" 13 | }, 14 | "scripts": { 15 | "start": "react-scripts start", 16 | "build": "react-scripts build", 17 | "test": "react-scripts test", 18 | "eject": "react-scripts eject" 19 | }, 20 | "eslintConfig": { 21 | "extends": "react-app" 22 | }, 23 | "browserslist": [ 24 | ">0.2%", 25 | "not dead", 26 | "not ie <= 11", 27 | "not op_mini all" 28 | ] 29 | } 30 | -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/src/store/reducer.js: -------------------------------------------------------------------------------- 1 | const defaultState = { 2 | inputValue: '', 3 | list: [] 4 | } 5 | 6 | export default (state = defaultState, action) => { 7 | 8 | if(action.type === 'change_input_value') { 9 | const newState = JSON.parse(JSON.stringify(state)); 10 | newState.inputValue = action.value; 11 | return newState; 12 | } 13 | 14 | if(action.type === 'add_list_item') { 15 | const newState = JSON.parse(JSON.stringify(state)); 16 | newState.list.push(newState.inputValue); 17 | newState.inputValue = ''; 18 | return newState; 19 | } 20 | 21 | if(action.type === 'delete_list_item') { 22 | const newState = JSON.parse(JSON.stringify(state)); 23 | newState.list.splice(action.index, 1); 24 | return newState; 25 | } 26 | 27 | return state; 28 | 29 | } -------------------------------------------------------------------------------- /JueJin/.vscode/launch.json: -------------------------------------------------------------------------------- 1 | // { 2 | // // 使用 IntelliSense 了解相关属性。 3 | // // 悬停以查看现有属性的描述。 4 | // // 欲了解更多信息,请访问: https://go.microsoft.com/fwlink/?linkid=830387 5 | // "version": "0.2.0", 6 | // "configurations": [ 7 | // { 8 | // "type": "chrome", 9 | // "request": "launch", 10 | // "name": "Launch Chrome against localhost", 11 | // "url": "http://localhost:8080", 12 | // "webRoot": "${workspaceFolder}" 13 | // } 14 | // ] 15 | // } 16 | { 17 | "version": "0.2.0", 18 | "configurations": [ 19 | 20 | { 21 | "name": "Chrome", 22 | "type": "chrome", 23 | "request": "launch", 24 | "url": "http://localhost:3000", 25 | "webRoot": "${workspaceRoot}/src", 26 | "sourceMapPathOverrides": { 27 | "webpack:///src/*": "${webRoot}/*" 28 | } 29 | } 30 | ] 31 | } -------------------------------------------------------------------------------- /JianShu/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "jianshu", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "antd": "^3.16.1", 7 | "axios": "^0.18.0", 8 | "react": "^16.8.4", 9 | "react-dom": "^16.8.4", 10 | "react-redux": "^6.0.1", 11 | "react-router-dom": "^5.0.0", 12 | "react-scripts": "2.1.8", 13 | "react-transition-group": "^2.9.0", 14 | "redux": "^4.0.1", 15 | "redux-immutable": "^4.0.0", 16 | "redux-thunk": "^2.3.0" 17 | }, 18 | "scripts": { 19 | "start": "react-scripts start", 20 | "build": "react-scripts build", 21 | "test": "react-scripts test", 22 | "eject": "react-scripts eject" 23 | }, 24 | "eslintConfig": { 25 | "extends": "react-app" 26 | }, 27 | "browserslist": [ 28 | ">0.2%", 29 | "not dead", 30 | "not ie <= 11", 31 | "not op_mini all" 32 | ] 33 | } 34 | -------------------------------------------------------------------------------- /JueJin/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "juejin", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "axios": "^0.18.0", 7 | "react": "^16.8.6", 8 | "react-dom": "^16.8.6", 9 | "react-loadable": "^5.5.0", 10 | "react-redux": "^7.0.2", 11 | "react-router-dom": "^5.0.0", 12 | "react-scripts": "3.0.0", 13 | "redux": "^4.0.1", 14 | "redux-saga": "^1.0.2" 15 | }, 16 | "scripts": { 17 | "start": "react-scripts start", 18 | "build": "react-scripts build", 19 | "test": "react-scripts test", 20 | "eject": "react-scripts eject" 21 | }, 22 | "eslintConfig": { 23 | "extends": "react-app" 24 | }, 25 | "browserslist": { 26 | "production": [ 27 | ">0.2%", 28 | "not dead", 29 | "not op_mini all" 30 | ], 31 | "development": [ 32 | "last 1 chrome version", 33 | "last 1 firefox version", 34 | "last 1 safari version" 35 | ] 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /JueJin/src/pages/404/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from "react"; 2 | import './index.css'; 3 | import NotFountOne from '../../assets/img/404_not_found_1.png'; 4 | import NotFountTwo from '../../assets/img/404_not_found_2.png'; 5 | import NotFountThree from '../../assets/img/404_not_found_3.png'; 6 | import NotFountFour from '../../assets/img/404_not_found_4.png'; 7 | 8 | class NotFound extends Component { 9 | render() { 10 | return ( 11 |
    12 |
    13 | 查找不到页面 14 | 查找不到页面 15 | 查找不到页面 16 | 查找不到页面 17 |
    18 | 19 |
    20 | ) 21 | } 22 | } 23 | 24 | export default NotFound; -------------------------------------------------------------------------------- /JueJin/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 掘金 9 | 10 | 11 | 12 | 13 | 14 |
    15 | 16 | 17 | -------------------------------------------------------------------------------- /JianShu/src/common/header/store/reducer.js: -------------------------------------------------------------------------------- 1 | import * as actionTypes from './actionTypes' 2 | import { fromJS } from 'immutable'; 3 | 4 | const defaultState = fromJS({ 5 | inputFocus: false, 6 | mouseInHot: false, 7 | list: [], 8 | page: 1, 9 | totalPage: 1, 10 | }); 11 | 12 | export default (state = defaultState, action) => { 13 | switch(action.type) { 14 | case actionTypes.SEARCH_FOCUS: 15 | return state.set('inputFocus', true); 16 | case actionTypes.SEARCH_BLUR: 17 | return state.set('inputFocus', false); 18 | case actionTypes.GET_LIST: 19 | return state.merge({ 20 | list: action.data, 21 | totalPage: action.totalPage 22 | }); 23 | case actionTypes.ON_MOUSE_ENTER_HOT: 24 | return state.set('mouseInHot', true); 25 | case actionTypes.ON_MOUSE_LEAVE_HOT: 26 | return state.set('mouseInHot', false); 27 | case actionTypes.CHANGE_PAGE: 28 | return state.set('page', action.page + 1); 29 | default: 30 | return state; 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/store/reducer.js: -------------------------------------------------------------------------------- 1 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION } from './actionTypes'; 2 | 3 | const defaultState = { 4 | inputValue: '', 5 | todoList: [] 6 | } 7 | 8 | export default (state = defaultState, action) => { 9 | 10 | if(action.type === CHANGE_INPUT_VALUE) { 11 | const newState = JSON.parse(JSON.stringify(state)); 12 | newState.inputValue = action.value; 13 | return newState; 14 | } 15 | 16 | if(action.type === ADD_TODO_ITEM) { 17 | const newState = JSON.parse(JSON.stringify(state)); 18 | newState.todoList.push(newState.inputValue); 19 | newState.inputValue = ''; 20 | return newState; 21 | } 22 | 23 | if(action.type === DELETE_TODO_ITEM) { 24 | const newState = JSON.parse(JSON.stringify(state)); 25 | newState.todoList.splice(action.index, 1); 26 | return newState; 27 | } 28 | 29 | if(action.type === INIT_LIST_ACTION) { 30 | const newState = JSON.parse(JSON.stringify(state)); 31 | newState.todoList = action.data; 32 | return newState; 33 | } 34 | 35 | return state; 36 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/store/reducer.js: -------------------------------------------------------------------------------- 1 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION } from './actionTypes'; 2 | 3 | const defaultState = { 4 | inputValue: '', 5 | todoList: [] 6 | } 7 | 8 | export default (state = defaultState, action) => { 9 | 10 | if(action.type === CHANGE_INPUT_VALUE) { 11 | const newState = JSON.parse(JSON.stringify(state)); 12 | newState.inputValue = action.value; 13 | return newState; 14 | } 15 | 16 | if(action.type === ADD_TODO_ITEM) { 17 | const newState = JSON.parse(JSON.stringify(state)); 18 | newState.todoList.push(newState.inputValue); 19 | newState.inputValue = ''; 20 | return newState; 21 | } 22 | 23 | if(action.type === DELETE_TODO_ITEM) { 24 | const newState = JSON.parse(JSON.stringify(state)); 25 | newState.todoList.splice(action.index, 1); 26 | return newState; 27 | } 28 | 29 | if(action.type === INIT_LIST_ACTION) { 30 | const newState = JSON.parse(JSON.stringify(state)); 31 | newState.todoList = action.data; 32 | return newState; 33 | } 34 | 35 | return state; 36 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/store/reducer.js: -------------------------------------------------------------------------------- 1 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION } from './actionTypes'; 2 | 3 | const defaultState = { 4 | inputValue: '', 5 | todoList: [] 6 | } 7 | 8 | export default (state = defaultState, action) => { 9 | 10 | if(action.type === CHANGE_INPUT_VALUE) { 11 | const newState = JSON.parse(JSON.stringify(state)); 12 | newState.inputValue = action.value; 13 | return newState; 14 | } 15 | 16 | if(action.type === ADD_TODO_ITEM) { 17 | const newState = JSON.parse(JSON.stringify(state)); 18 | newState.todoList.push(newState.inputValue); 19 | newState.inputValue = ''; 20 | return newState; 21 | } 22 | 23 | if(action.type === DELETE_TODO_ITEM) { 24 | const newState = JSON.parse(JSON.stringify(state)); 25 | newState.todoList.splice(action.index, 1); 26 | return newState; 27 | } 28 | 29 | if(action.type === INIT_LIST_ACTION) { 30 | const newState = JSON.parse(JSON.stringify(state)); 31 | newState.todoList = action.data; 32 | return newState; 33 | } 34 | 35 | return state; 36 | } -------------------------------------------------------------------------------- /JianShu/src/common/header/store/actionCreators.js: -------------------------------------------------------------------------------- 1 | import * as actionTypes from './actionTypes' 2 | import axios from 'axios'; 3 | import { fromJS } from 'immutable'; 4 | 5 | export const searchFocus = () => ({ 6 | type: actionTypes.SEARCH_FOCUS 7 | }) 8 | 9 | export const searchBlur = () => ({ 10 | type: actionTypes.SEARCH_BLUR 11 | }) 12 | 13 | export const onMouseEnterHot = () => ({ 14 | type: actionTypes.ON_MOUSE_ENTER_HOT, 15 | }) 16 | 17 | export const onMouseLeaveHot = () => ({ 18 | type: actionTypes.ON_MOUSE_LEAVE_HOT, 19 | }) 20 | 21 | export const getList = () => { 22 | return (dispatch) => { 23 | axios.get('/api/headerList.json').then( (res) => { 24 | if(res.data.code === 0) { 25 | const data = res.data.list; 26 | dispatch(changeList(data)); 27 | } 28 | }).catch( (error) => { 29 | console.log(error); 30 | }); 31 | } 32 | } 33 | 34 | const changeList = (data) => ({ 35 | type: actionTypes.GET_LIST, 36 | data: fromJS(data), 37 | totalPage: Math.ceil(data.length / 10) 38 | }) 39 | 40 | export const changePage = (page) => ({ 41 | type: actionTypes.CHANGE_PAGE, 42 | page: page, 43 | }) 44 | -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/store/sagas.js: -------------------------------------------------------------------------------- 1 | // 6. 引用 redux-saga/effets 中的 takeEvery 2 | // 13. 由于我们在 sagas.js 中没有引用到 store,所以不能使用 store.dispatch(),但是 redux-saga 给我们提供了 put 方法来代替 store.dispatch() 方法 3 | import { takeEvery, put } from 'redux-saga/effects'; 4 | // 7. 引入 GET_INIT_LIST 类型 5 | import { GET_INIT_LIST } from './actionTypes'; 6 | // 11. 将 TodoList.js 的 axios 引入迁移到 sagas.js 中 7 | import axios from 'axios'; 8 | // 12. 引入 actionCreator.js 中的 initListAction 9 | import { initListAction } from './actionCreators' 10 | 11 | // 8. 使用 generator 函数 12 | function* todoSaga() { 13 | // 9. 这行代码表示,只要我们接收到 GET_INIT_LIST 的类型,我们就执行 getInitList 方法 14 | yield takeEvery(GET_INIT_LIST, getInitList); 15 | } 16 | 17 | // 10. 定义 getInitList 方法 18 | function* getInitList() { 19 | try { 20 | // 14. 在 sagas.js 中处理异步函数 21 | const res = yield axios.get('https://www.easy-mock.com/mock/5ca803587e5a246db3d100cb/todolis'); 22 | const action = initListAction(res.data.todolist); 23 | // 15. 等 action 处理完之后,在执行 put 方法 24 | yield put(action); 25 | } catch (error) { 26 | console.log("接口请求失败,请检查 todolist 接口。"); 27 | } 28 | 29 | } 30 | 31 | export default todoSaga; -------------------------------------------------------------------------------- /JianShu/src/pages/home/store/actionCreators.js: -------------------------------------------------------------------------------- 1 | import * as actionTypes from './actionTypes'; 2 | import axios from 'axios'; 3 | import { fromJS } from 'immutable'; 4 | 5 | export const getLeftList = () => { 6 | return (dispatch) => { 7 | axios.get('/api/leftList.json').then((res) => { 8 | if(res.data.code === 0) { 9 | const data = res.data.data.articleFeed; 10 | dispatch(setLeftList(data)); 11 | } 12 | }).catch((error) => { 13 | console.log(error); 14 | }) 15 | } 16 | } 17 | 18 | const setLeftList = (data) => ({ 19 | type: actionTypes.GET_LEFT_LIST, 20 | data: fromJS(data), 21 | }) 22 | 23 | export const getRightRecommendAuthor = () => { 24 | return (dispatch) => { 25 | axios.get('/api/rightRecommendAuthor.json').then((res) => { 26 | if(res.data.code === 0) { 27 | const data = res.data.data.recommendationCard; 28 | dispatch(setRightRecommendAuthor(data)) 29 | } 30 | }).catch((error) => { 31 | console.log(error); 32 | }) 33 | } 34 | } 35 | 36 | const setRightRecommendAuthor = (data) => ({ 37 | type: actionTypes.GET_RIGHT_RECOMMEND_AUTHOR, 38 | data: fromJS(data), 39 | }) -------------------------------------------------------------------------------- /JueJin/src/pages/TimeLine/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from "react"; 2 | import './index.css'; 3 | import Loadable from 'react-loadable'; 4 | 5 | const Loading = () =>
    Loading...
    ; 6 | 7 | const Nav = Loadable({ 8 | loader: () => import('./components/Nav'), 9 | loading: Loading, 10 | }); 11 | 12 | const LeftList = Loadable({ 13 | loader: () => import('./components/LeftList'), 14 | loading: Loading, 15 | }); 16 | 17 | const RightRecommend = Loadable({ 18 | loader: () => import('./components/RightRecommend'), 19 | loading: Loading, 20 | }) 21 | 22 | class TimeLine extends Component { 23 | constructor(props) { 24 | super(props); 25 | this.backTop = this.backTop.bind(this); 26 | } 27 | 28 | render() { 29 | return ( 30 |
    31 |
    38 | ) 39 | } 40 | 41 | backTop() { 42 | console.log(document) 43 | // window.body.scrollTop = 0; 44 | } 45 | 46 | } 47 | 48 | export default TimeLine; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/TodoListUI.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import { Input, Button, List } from 'antd'; 3 | 4 | const TodoListUI = (props) => { 5 | return ( 6 |
    7 |
    8 |

    TodoList

    9 |
    10 |
    11 | 18 | 25 |
    26 |
    27 | ( 32 | {props.handleDeleteItem(index)}}> 33 | {index + 1} - {item} 34 | 35 | )} 36 | /> 37 |
    38 |
    39 | ); 40 | } 41 | 42 | export default TodoListUI; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/store/actionCreators.js: -------------------------------------------------------------------------------- 1 | import { CHANGE_INPUT_VALUE, ADD_TODO_ITEM, DELETE_TODO_ITEM, INIT_LIST_ACTION } from './actionTypes'; 2 | // 1. 把 axios 从 TodoList.js 中剪切到 actionCreators.js 中 3 | import axios from 'axios'; 4 | 5 | export const getChangeInputValue = (value) => ({ 6 | type: CHANGE_INPUT_VALUE, 7 | value 8 | }) 9 | 10 | export const getAddTodoItem = () => ({ 11 | type: ADD_TODO_ITEM 12 | }) 13 | 14 | export const getDeleteTodoItem = (index) => ({ 15 | type: DELETE_TODO_ITEM, 16 | index 17 | }) 18 | 19 | export const initListAction = (data) => ({ 20 | type: INIT_LIST_ACTION, 21 | data 22 | }) 23 | 24 | // 2. 把 TodoList 文件中 componentDidMount() 的 axios.get() 挪到 actionCreators.js 中 25 | // 3. 在没使用 redux-thunk 之前,我们仅可以在 actionCreators.js 中使用对象,现在我们也可以使用函数了。 26 | export const getTodoList = () => { 27 | // 7. 当我们使用 getTodoList 的时候,我们也能传递 store 的 dispatch,从而在下面代码中使用 28 | return (dispatch) => { 29 | axios.get('https://www.easy-mock.com/mock/5ca803587e5a246db3d100cb/todolist').then( (res) => { 30 | // 8. 直接使用 actionCreators.js 中的 initListAction 方法,并 dispatch 该 action 31 | const action = initListAction(res.data.todolist); 32 | dispatch(action); 33 | }) 34 | } 35 | } -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/TodoListUI.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import { Input, Button, List } from 'antd'; 3 | 4 | const TodoListUI = (props) => { 5 | return ( 6 |
    7 |
    8 |

    TodoList

    9 |
    10 |
    11 | 18 | 25 |
    26 |
    27 | ( 32 | {props.handleDeleteItem(index)}}> 33 | {index + 1} - {item} 34 | 35 | )} 36 | /> 37 |
    38 |
    39 | ); 40 | } 41 | 42 | export default TodoListUI; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/TodoListUI.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import { Input, Button, List } from 'antd'; 3 | 4 | const TodoListUI = (props) => { 5 | return ( 6 |
    7 |
    8 |

    TodoList

    9 |
    10 |
    11 | 18 | 25 |
    26 |
    27 | ( 32 | {props.handleDeleteItem(index)}}> 33 | {index + 1} - {item} 34 | 35 | )} 36 | /> 37 |
    38 |
    39 | ); 40 | } 41 | 42 | export default TodoListUI; -------------------------------------------------------------------------------- /JueJin/src/pages/404/index.css: -------------------------------------------------------------------------------- 1 | .not-found { 2 | text-align: center; 3 | width: 100%; 4 | height: 100%; 5 | background: #fff; 6 | position: fixed; 7 | top: 0; 8 | left: 0; 9 | } 10 | .not-found-img { 11 | position: relative; 12 | width: 624px; 13 | height: 460px; 14 | margin: 80px auto 0; 15 | } 16 | .not-found-img img { 17 | position: absolute; 18 | top: 35%; 19 | left: 50%; 20 | } 21 | .not-found-img-1 { 22 | width: 484px; 23 | height: 307px; 24 | transform: translate(-50%, -50%); 25 | } 26 | .not-found-img-2 { 27 | width: 131px; 28 | height: 153px; 29 | transform: translate(-55%, 32%); 30 | animation: float-up-down 2s ease-in-out infinite alternate; 31 | } 32 | @keyframes float-up-down{ 33 | from{ 34 | transform: translate(-55%, 32%); 35 | } 36 | to{ 37 | transform: translate(-55%, 28%); 38 | } 39 | } 40 | .not-found-img-3 { 41 | width: 619px; 42 | height: 167px; 43 | transform: translate(-50%, 75.3%); 44 | opacity: .7; 45 | } 46 | .not-found-img-4 { 47 | width: 253px; 48 | height: 85px; 49 | transform: translate(-55%, 162%); 50 | opacity: .4; 51 | } 52 | .go-home { 53 | width: 120px; 54 | height: 50px; 55 | margin-top: 30px; 56 | padding: 13.2px 24px; 57 | font-size: 17px; 58 | color: #fff; 59 | background-color: #007fff; 60 | border-radius: 5px; 61 | } -------------------------------------------------------------------------------- /JueJin/src/assets/img/icon_search.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | B97EB10A-8F34-4AB5-ABAF-41D933741ED0 5 | Created with sketchtool. 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /JianShu/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - Demo Three - 简书 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-22 11:16:34** 5 | > Recently revised in **2019-4-7 19:45:38** 6 | 7 | 该项目是简书网站的仿建: 8 | 9 | * 开发模式:`npm start` 10 | * 打包模式: `npm build` 11 | 12 | 需要了解更多,请看: 13 | 14 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 15 | 16 | --- 17 | 18 | > **jsliang** 广告推送: 19 | > 也许小伙伴想了解下云服务器 20 | > 或者小伙伴想买一台云服务器 21 | > 或者小伙伴需要续费云服务器 22 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 23 | 24 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /JueJin/src/assets/img/icon_search_active.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | B97EB10A-8F34-4AB5-ABAF-41D933741ED0 5 | Created with sketchtool. 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /JueJin/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - Demo Four - 掘金 2 | === 3 | 4 | > Create by **jsliang** on **2019-04-24 08:25:55** 5 | > Recently revised in **2019-04-25 15:40:26** 6 | 7 | 该项目仅用作测试使用: 8 | 9 | * 安装依赖:`npm i` 10 | * 开发模式:`npm start` 11 | * 打包模式: `npm build` 12 | 13 | 需要了解更多,请看: 14 | 15 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 16 | 17 | --- 18 | 19 | > **jsliang** 广告推送: 20 | > 也许小伙伴想了解下云服务器 21 | > 或者小伙伴想买一台云服务器 22 | > 或者小伙伴需要续费云服务器 23 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 24 | 25 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /Simplify/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - 简化 create-react-app 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-22 11:16:34** 5 | > Recently revised in **2019-3-22 11:16:38** 6 | 7 | 该项目是对 create-react-app 的简化: 8 | 9 | * 开发模式:`npm start` 10 | * 打包模式: `npm build` 11 | 12 | 需要了解更多,请看: 13 | 14 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 15 | 16 | --- 17 | 18 | > **jsliang** 广告推送: 19 | > 也许小伙伴想了解下云服务器 20 | > 或者小伙伴想买一台云服务器 21 | > 或者小伙伴需要续费云服务器 22 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 23 | 24 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /TodoList/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - Demo One - TodoList 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-22 11:16:34** 5 | > Recently revised in **2019-3-22 11:16:38** 6 | 7 | 初入 React 大门,编写了一个简单的 TodoList: 8 | 9 | * 开发模式:`npm start` 10 | * 打包模式: `npm build` 11 | 12 | 需要了解更多,请看: 13 | 14 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 15 | 16 | --- 17 | 18 | > **jsliang** 广告推送: 19 | > 也许小伙伴想了解下云服务器 20 | > 或者小伙伴想买一台云服务器 21 | > 或者小伙伴需要续费云服务器 22 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 23 | 24 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | React 系列 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-22 11:10:32** 5 | > Recently revised in **2019-3-22 13:07:07** 6 | 7 | Hello 小伙伴们,这是 **jsliang** 编写的关于 React 系列的 Demo 代码,小伙伴们可以下载查看。 8 | 9 | 如果小伙伴们想查看文章,了解编写过程详细,可以到: 10 | 11 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 12 | 13 | 找到 React 系列的文章,如果觉得不错,记得给个 star,非常感谢~ 14 | 15 | --- 16 | 17 | > **jsliang** 广告推送: 18 | > 也许小伙伴想了解下云服务器 19 | > 或者小伙伴想买一台云服务器 20 | > 或者小伙伴需要续费云服务器 21 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 22 | 23 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - 简化 create-react-app 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-22 11:16:34** 5 | > Recently revised in **2019-3-22 11:16:38** 6 | 7 | 该项目是对 create-react-app 的简化: 8 | 9 | * 开发模式:`npm start` 10 | * 打包模式: `npm build` 11 | 12 | 需要了解更多,请看: 13 | 14 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 15 | 16 | --- 17 | 18 | > **jsliang** 广告推送: 19 | > 也许小伙伴想了解下云服务器 20 | > 或者小伙伴想买一台云服务器 21 | > 或者小伙伴需要续费云服务器 22 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 23 | 24 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /JianShu/src/pages/home/components/TopNav.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { Link } from 'react-router-dom'; 3 | 4 | class TopNav extends Component { 5 | render() { 6 | return ( 7 |
    8 |
      9 |
    • 10 | 推荐 11 |
    • 12 |
    • 13 | 关注 14 |
    • 15 |
    • 16 | 后端 17 |
    • 18 |
    • 19 | 前端 20 |
    • 21 |
    • 22 | Android 23 |
    • 24 |
    • 25 | IOS 26 |
    • 27 |
    • 28 | 人工智能 29 |
    • 30 |
    • 31 | 开发工具 32 |
    • 33 |
    • 34 | 代码人生 35 |
    • 36 |
    • 37 | 阅读 38 |
    • 39 |
    • 40 | 标签管理 41 |
    • 42 |
    43 |
    44 | ) 45 | } 46 | } 47 | 48 | export default TopNav; -------------------------------------------------------------------------------- /TodoListUpgrade/README.md: -------------------------------------------------------------------------------- 1 | React 系列 - Demo Two - TodoList 升级 2 | === 3 | 4 | > Create by **jsliang** on **2019-3-26 10:23:47** 5 | > Recently revised in **2019-4-6 11:46:38** 6 | 7 | 我们对 TodoList 进行了 Redux 升级,该份文件夹下有四个目录: 8 | 9 | * Redux-Base —— 记录 Redux 基础内容 10 | * Redux-Thunk —— 在 Redux-Base 基础上进行 `redux-thunk` 的中间件配置 11 | * Redux-Saga —— 在 Redux-Base 基础上进行 `redux-saga` 的中间件配置 12 | * React-Redux —— 对 TodoList 进行 `react-redux` 重新改造 13 | 14 | 它们的打开方式是: 15 | 16 | * 安装依赖:`npm i` 17 | * 开发模式:`npm start` 18 | * 打包模式: `npm build` 19 | 20 | 需要了解更多,请前往下面链接进行查看: 21 | 22 | * [jsliang 的文档库](https://github.com/LiangJunrong/document-library) 23 | 24 | --- 25 | 26 | > **jsliang** 广告推送: 27 | > 也许小伙伴想了解下云服务器 28 | > 或者小伙伴想买一台云服务器 29 | > 或者小伙伴需要续费云服务器 30 | > 欢迎点击 **[云服务器推广](https://github.com/LiangJunrong/document-library/blob/master/other-library/Monologue/%E7%A8%B3%E9%A3%9F%E8%89%B0%E9%9A%BE.md)** 查看! 31 | 32 | > 知识共享许可协议
    jsliang 的文档库梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
    基于https://github.com/LiangJunrong/document-library上的作品创作。
    本许可协议授权之外的使用权限可以从 https://creativecommons.org/licenses/by-nc-sa/2.5/cn/ 处获得。 -------------------------------------------------------------------------------- /JueJin/src/pages/TimeLine/components/Nav.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { NavLink } from 'react-router-dom'; 3 | 4 | class Nav extends Component { 5 | render() { 6 | return ( 7 | 44 | ) 45 | } 46 | } 47 | 48 | export default Nav; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Base/src/TodoList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import './index.css'; 3 | import 'antd/dist/antd.css'; 4 | import store from './store'; 5 | import { getChangeInputValue, getAddTodoItem, getDeleteTodoItem, initListAction } from './store/actionCreators'; 6 | import TodoListUI from './TodoListUI'; 7 | import axios from 'axios'; 8 | 9 | class TodoList extends Component { 10 | 11 | constructor(props) { 12 | super(props); 13 | this.state = store.getState(); 14 | this.handleInputChange = this.handleInputChange.bind(this); 15 | this.handleAddItem = this.handleAddItem.bind(this); 16 | this.handleInputKeyUp = this.handleInputKeyUp.bind(this); 17 | this.handleDeleteItem = this.handleDeleteItem.bind(this); 18 | 19 | this.handleStoreChange = this.handleStoreChange.bind(this); 20 | store.subscribe(this.handleStoreChange); 21 | } 22 | 23 | render() { 24 | return ( 25 | 33 | ); 34 | } 35 | 36 | componentDidMount() { 37 | axios.get('https://www.easy-mock.com/mock/5ca803587e5a246db3d100cb/todolist').then( (res) => { 38 | const action = initListAction(res.data.todolist); 39 | store.dispatch(action); 40 | }) 41 | } 42 | 43 | handleInputChange(e) { 44 | const action = getChangeInputValue(e.target.value); 45 | store.dispatch(action); 46 | } 47 | 48 | handleStoreChange() { 49 | this.setState(store.getState()); 50 | } 51 | 52 | handleAddItem() { 53 | const action = getAddTodoItem(); 54 | store.dispatch(action); 55 | } 56 | 57 | handleInputKeyUp(e) { 58 | if(e.keyCode === 13) { 59 | this.handleAddItem(); 60 | } 61 | } 62 | 63 | handleDeleteItem(index) { 64 | const action = getDeleteTodoItem(index); 65 | store.dispatch(action); 66 | } 67 | 68 | } 69 | 70 | export default TodoList; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Saga/src/TodoList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import './index.css'; 3 | import 'antd/dist/antd.css'; 4 | import store from './store'; 5 | // 1. 删除 initListAction 以及下面的 axios,并引入 actionCreators.js 中的 getInitList 6 | import { getChangeInputValue, getAddTodoItem, getDeleteTodoItem, getInitList } from './store/actionCreators'; 7 | import TodoListUI from './TodoListUI'; 8 | 9 | class TodoList extends Component { 10 | 11 | constructor(props) { 12 | super(props); 13 | this.state = store.getState(); 14 | this.handleInputChange = this.handleInputChange.bind(this); 15 | this.handleAddItem = this.handleAddItem.bind(this); 16 | this.handleInputKeyUp = this.handleInputKeyUp.bind(this); 17 | this.handleDeleteItem = this.handleDeleteItem.bind(this); 18 | 19 | this.handleStoreChange = this.handleStoreChange.bind(this); 20 | store.subscribe(this.handleStoreChange); 21 | } 22 | 23 | render() { 24 | return ( 25 | 33 | ); 34 | } 35 | 36 | componentDidMount() { 37 | // 5. 调用 getInitList,并使用 dispatch 将 action 派发出去。这时候不仅 reducer.js 可以接收到这个 action,我们的 sagas.js 也可以接收到这个 action。 38 | const action = getInitList(); 39 | store.dispatch(action); 40 | } 41 | 42 | handleInputChange(e) { 43 | const action = getChangeInputValue(e.target.value); 44 | store.dispatch(action); 45 | } 46 | 47 | handleStoreChange() { 48 | this.setState(store.getState()); 49 | } 50 | 51 | handleAddItem() { 52 | const action = getAddTodoItem(); 53 | store.dispatch(action); 54 | } 55 | 56 | handleInputKeyUp(e) { 57 | if(e.keyCode === 13) { 58 | this.handleAddItem(); 59 | } 60 | } 61 | 62 | handleDeleteItem(index) { 63 | const action = getDeleteTodoItem(index); 64 | store.dispatch(action); 65 | } 66 | 67 | } 68 | 69 | export default TodoList; -------------------------------------------------------------------------------- /TodoListUpgrade/Redux-Thunk/src/TodoList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import './index.css'; 3 | import 'antd/dist/antd.css'; 4 | import store from './store'; 5 | // 4. 在 TodoList.js 中引用 actionCreators.js 中的 getTodoList,并去除没再引用的 initListAction 6 | import { getChangeInputValue, getAddTodoItem, getDeleteTodoItem, getTodoList } from './store/actionCreators'; 7 | import TodoListUI from './TodoListUI'; 8 | 9 | class TodoList extends Component { 10 | 11 | constructor(props) { 12 | super(props); 13 | this.state = store.getState(); 14 | this.handleInputChange = this.handleInputChange.bind(this); 15 | this.handleAddItem = this.handleAddItem.bind(this); 16 | this.handleInputKeyUp = this.handleInputKeyUp.bind(this); 17 | this.handleDeleteItem = this.handleDeleteItem.bind(this); 18 | 19 | this.handleStoreChange = this.handleStoreChange.bind(this); 20 | store.subscribe(this.handleStoreChange); 21 | } 22 | 23 | render() { 24 | return ( 25 | 33 | ); 34 | } 35 | 36 | componentDidMount() { 37 | // 5. 在 componentDidMount 中调用 getTodoList。如果我们没使用 redux-thunk,我们只能使用对象,但是现在我们可以使用函数了。 38 | const action = getTodoList(); 39 | // 6. 当我们 dispatch 了 action 的时候,我们就调用了步骤 1 的 getTodoList(),从而获取了数据 40 | store.dispatch(action); 41 | } 42 | 43 | handleInputChange(e) { 44 | const action = getChangeInputValue(e.target.value); 45 | store.dispatch(action); 46 | } 47 | 48 | handleStoreChange() { 49 | this.setState(store.getState()); 50 | } 51 | 52 | handleAddItem() { 53 | const action = getAddTodoItem(); 54 | store.dispatch(action); 55 | } 56 | 57 | handleInputKeyUp(e) { 58 | if(e.keyCode === 13) { 59 | this.handleAddItem(); 60 | } 61 | } 62 | 63 | handleDeleteItem(index) { 64 | const action = getDeleteTodoItem(index); 65 | store.dispatch(action); 66 | } 67 | 68 | } 69 | 70 | export default TodoList; -------------------------------------------------------------------------------- /JianShu/src/pages/home/components/RightRecommend.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { connect } from 'react-redux'; 3 | import { actionCreators } from '../store'; 4 | 5 | class RightRecommend extends Component { 6 | render() { 7 | return ( 8 |
    9 | 17 |
    18 |
    掘金优秀作者
    19 |
    20 | { 21 | this.props.author.map((item) => { 22 | return ( 23 |
    24 | 头像 25 |
    26 | {item.get('author').get('username')} 27 | {item.get('author').get('jobTitle')} 28 | {item.get('description')} 29 |
    30 |
    31 | ) 32 | }) 33 | } 34 |
    35 |
    36 |
    37 | ) 38 | } 39 | 40 | componentDidMount() { 41 | this.props.getRightRecommendAuthor(); 42 | } 43 | 44 | } 45 | 46 | const mapStateToProps = (state) => { 47 | return { 48 | author: state.get('home').get('rightRecommend') 49 | } 50 | } 51 | 52 | const mapDispathToProps = (dispatch) => { 53 | return { 54 | getRightRecommendAuthor() { 55 | dispatch(actionCreators.getRightRecommendAuthor()); 56 | } 57 | } 58 | } 59 | 60 | export default connect(mapStateToProps, mapDispathToProps)(RightRecommend); -------------------------------------------------------------------------------- /JianShu/src/reset.css: -------------------------------------------------------------------------------- 1 | /* 2 | * reset 的目的不是让默认样式在所有浏览器下一致,而是减少默认样式有可能带来的问题。 3 | * The purpose of reset is not to allow default styles to be consistent across all browsers, but to reduce the potential problems of default styles. 4 | * create by jsliang 5 | */ 6 | 7 | /** 清除内外边距 - clearance of inner and outer margins **/ 8 | body, h1, h2, h3, h4, h5, h6, hr, p, blockquote, /* 结构元素 - structural elements */ 9 | dl, dt, dd, ul, ol, li, /* 列表元素 - list elements */ 10 | pre, /* 文本格式元素 - text formatting elements */ 11 | form, fieldset, legend, button, input, textarea, /* 表单元素 - from elements */ 12 | th, td /* 表格元素 - table elements */ { 13 | margin: 0; 14 | padding: 0; 15 | } 16 | 17 | /** 设置默认字体 - setting the default font **/ 18 | body, button, input, select, textarea { 19 | font: 18px/1.5 '黑体', Helvetica, sans-serif; 20 | } 21 | h1, h2, h3, h4, h5, h6, button, input, select, textarea { font-size: 100%; } 22 | 23 | /** 重置列表元素 - reset the list element **/ 24 | ul, ol { list-style: none; } 25 | 26 | /** 重置文本格式元素 - reset the text format element **/ 27 | a, a:hover { text-decoration: none; } 28 | 29 | /** 重置表单元素 - reset the form element **/ 30 | button { cursor: pointer; } 31 | input { font-size: 18px; outline: none; } 32 | 33 | /** 重置表格元素 - reset the table element **/ 34 | table { border-collapse: collapse; border-spacing: 0; } 35 | 36 | /* 37 | * 图片自适应 - image responsize 38 | * 1. 清空浏览器对图片的设置 39 | * 2.
    图片
    的情况下,图片会撑高 div,这么设置可以清除该影响 40 | */ 41 | img { border: 0; display: inline-block; width: 100%; max-width: 100%; height: auto; vertical-align: middle; } 42 | 43 | /* 44 | * 默认box-sizing是content-box,该属性导致padding会撑大div,使用border-box可以解决该问题 45 | * set border-box for box-sizing when you use div, it solve the problem when you add padding and don't want to make the div width bigger 46 | */ 47 | div, input { box-sizing: border-box; } 48 | 49 | /** 清除浮动 - clear float **/ 50 | .jsliang-clear:after, .clear:after { 51 | content: '\20'; 52 | display: block; 53 | height: 0; 54 | clear: both; 55 | } 56 | .jsliang-clear, .clear { 57 | *zoom: 1; 58 | } 59 | 60 | /** 设置input的placeholder - set input placeholder **/ 61 | input::-webkit-input-placeholder { color: #919191; font-size: 1em } /* Webkit browsers */ 62 | input::-moz-placeholder { color: #919191; font-size: 1em } /* Mozilla Firefox */ 63 | input::-ms-input-placeholder { color: #919191; font-size: 1em } /* Internet Explorer */ -------------------------------------------------------------------------------- /TodoListUpgrade/React-Redux/src/TodoList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import './index.css'; 3 | import { Input, Button, List } from 'antd'; 4 | import 'antd/dist/antd.css'; 5 | import { connect } from 'react-redux'; 6 | 7 | class TodoList extends Component { 8 | 9 | render() { 10 | return ( 11 |
    12 |
    13 |

    TodoList

    14 |
    15 |
    16 | 23 | 30 |
    31 |
    32 | ( 37 | {this.props.handleDeleteItem(index)}}> 38 | {index + 1} - {item} 39 | 40 | )} 41 | /> 42 |
    43 |
    44 | ); 45 | } 46 | 47 | handleInputEnter(e){ 48 | if(e.keyCode === 13) { 49 | this.props.handleAddItem(); 50 | } 51 | } 52 | 53 | } 54 | 55 | const mapStateToProps = (state) => { 56 | return { 57 | inputValue: state.inputValue, 58 | list: state.list 59 | } 60 | } 61 | 62 | const mapDispatchToProps = (dispatch) => { 63 | return { 64 | handleInputChange(e) { 65 | const action = { 66 | type: 'change_input_value', 67 | value: e.target.value 68 | } 69 | dispatch(action); 70 | }, 71 | handleAddItem() { 72 | const action = { 73 | type: 'add_list_item' 74 | } 75 | dispatch(action); 76 | }, 77 | handleDeleteItem(index) { 78 | console.log(index); 79 | const action = { 80 | type: 'delete_list_item', 81 | index 82 | } 83 | dispatch(action); 84 | }, 85 | } 86 | } 87 | 88 | export default connect(mapStateToProps, mapDispatchToProps)(TodoList); -------------------------------------------------------------------------------- /JueJin/src/components/Header/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from "react"; 2 | import { Link, NavLink } from 'react-router-dom'; 3 | import './index.css'; 4 | import Logo from '../../assets/img/logo.svg'; 5 | import Search from '../../assets/img/icon_search.svg'; 6 | 7 | class Header extends Component { 8 | render() { 9 | return ( 10 |
    11 |
    12 | Logo 13 |
      14 |
    • 15 | 首页 16 |
    • 17 |
    • 18 | 沸点 19 |
    • 20 |
    • 21 | 话题 22 |
    • 23 |
    • 24 | 小册 25 |
    • 26 |
    • 27 | 活动 28 |
    • 29 |
    30 |
      31 |
    • 32 |
      33 | 34 | 搜索 35 |
      36 |
    • 37 |
    • 38 |
      39 | 40 |
      41 | 42 |
      43 |
      44 |
    • 45 | 46 | 47 | 5.2K 48 | 49 | 50 | 头像 51 | 52 |
    53 |
    54 |
    55 | ) 56 | } 57 | } 58 | 59 | export default Header; -------------------------------------------------------------------------------- /JueJin/src/styles/reset.css: -------------------------------------------------------------------------------- 1 | /* 2 | * reset 的目的不是让默认样式在所有浏览器下一致,而是减少默认样式有可能带来的问题。 3 | * The purpose of reset is not to allow default styles to be consistent across all browsers, but to reduce the potential problems of default styles. 4 | * create by jsliang 5 | */ 6 | 7 | /** 清除内外边距 - clearance of inner and outer margins **/ 8 | body, h1, h2, h3, h4, h5, h6, hr, p, blockquote, /* 结构元素 - structural elements */ 9 | dl, dt, dd, ul, ol, li, /* 列表元素 - list elements */ 10 | pre, /* 文本格式元素 - text formatting elements */ 11 | form, fieldset, legend, button, input, textarea, /* 表单元素 - from elements */ 12 | th, td /* 表格元素 - table elements */ { 13 | margin: 0; 14 | padding: 0; 15 | } 16 | 17 | /** 设置默认字体 - setting the default font **/ 18 | body, button, input, select, textarea { 19 | font-family: -apple-system, system-ui, BlinkMacSystemFont, "Helvetica Neue", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", Arial, sans-serif; 20 | } 21 | h1, h2, h3, h4, h5, h6, button, input, select, textarea { font-size: 100%; } 22 | 23 | /** 重置列表元素 - reset the list element **/ 24 | ul, ol { list-style: none; } 25 | 26 | /** 重置文本格式元素 - reset the text format element **/ 27 | a, a:hover { text-decoration: none; } 28 | 29 | /** 重置表单元素 - reset the form element **/ 30 | button { cursor: pointer; margin: 0; padding: 0; border: 1px solid transparent; outline: none } 31 | input { font-size: 16px; outline: none; border: none; } 32 | 33 | /** 重置表格元素 - reset the table element **/ 34 | table { border-collapse: collapse; border-spacing: 0; } 35 | 36 | /* 37 | * 图片自适应 - image responsize 38 | * 1. 清空浏览器对图片的设置 39 | * 2.
    图片
    的情况下,图片会撑高 div,这么设置可以清除该影响 40 | */ 41 | img { border: 0; display: inline-block; width: 100%; max-width: 100%; height: auto; vertical-align: middle; } 42 | 43 | /* 44 | * 默认box-sizing是content-box,该属性导致padding会撑大div,使用border-box可以解决该问题 45 | * set border-box for box-sizing when you use div, it solve the problem when you add padding and don't want to make the div width bigger 46 | */ 47 | div, input { box-sizing: border-box; } 48 | 49 | /** 清除浮动 - clear float **/ 50 | .jsliang-clear:after, .clear:after { 51 | content: '\20'; 52 | display: block; 53 | height: 0; 54 | clear: both; 55 | } 56 | .jsliang-clear, .clear { 57 | *zoom: 1; 58 | } 59 | 60 | /** 设置input的placeholder - set input placeholder **/ 61 | input::-webkit-input-placeholder { color: #919191; font-size: 14px; } /* Webkit browsers */ 62 | input::-moz-placeholder { color: #919191; font-size: 14px; } /* Mozilla Firefox */ 63 | input::-ms-input-placeholder { color: #919191; font-size: 14px; } /* Internet Explorer */ -------------------------------------------------------------------------------- /TodoList/src/TodoList.js: -------------------------------------------------------------------------------- 1 | // Fragment 是一种占位符形式,类似于 Vue 的 Template 2 | import React, { Component, Fragment } from 'react'; 3 | 4 | // 引入组件 5 | import TodoItem from './TodoItem'; 6 | 7 | // 引用样式 8 | import './style.css'; 9 | 10 | class TodoList extends Component { 11 | 12 | // 构造函数 13 | constructor(props) { 14 | super(props); 15 | // 定义数据 16 | this.state = { 17 | inputValue: '', 18 | list: [] 19 | } 20 | this.handleInputChange = this.handleInputChange.bind(this); 21 | this.handleBtnClick = this.handleBtnClick.bind(this); 22 | this.handleItemDelete = this.handleItemDelete.bind(this); 23 | } 24 | 25 | // 渲染页面 26 | render() { 27 | return ( 28 | 29 |
    30 | 31 | {/* 单项数据绑定 */} 32 | {/* 在 React 中,绑定时间的,一般为半驼峰形式 */} 33 | 39 | 40 |
    41 |
      42 | {/* 精简 JSX,将部分抽取出来 */} 43 | { this.getTodoItem() } 44 |
    45 |
    46 | ) 47 | } 48 | 49 | // 获取单独项 50 | getTodoItem() { 51 | return this.state.list.map( (item, index) => { 52 | return ( 53 | 59 | ) 60 | }) 61 | } 62 | 63 | // 方法体 - 输入内容 64 | handleInputChange(e) { 65 | const value = e.target.value; 66 | this.setState( () => ({ 67 | inputValue: value 68 | })) 69 | } 70 | 71 | // 方法体 - 点击提交 72 | handleBtnClick() { 73 | const list = this.state.list, 74 | inputValue = this.state.inputValue; 75 | this.setState( () => ({ 76 | list: [...list, inputValue], 77 | inputValue: '' 78 | })) 79 | 80 | // 或者可以这样写: 81 | // this.setState( (prevState) => ({ 82 | // list: [...prevState.list, prevState.inputValue], 83 | // inputValue: '' 84 | // })) 85 | 86 | } 87 | 88 | // 方法体 - 删除项目 89 | handleItemDelete(index) { 90 | // immutable - state 不允许做任何改变 91 | const list = [...this.state.list]; 92 | list.splice(index, 1); 93 | 94 | this.setState( () => ({ 95 | list: list 96 | })) 97 | } 98 | 99 | } 100 | 101 | export default TodoList; -------------------------------------------------------------------------------- /JianShu/src/pages/home/components/LeftList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { Link } from 'react-router-dom'; 3 | import { connect } from 'react-redux'; 4 | import { actionCreators } from '../store'; 5 | 6 | class LeftList extends Component { 7 | render() { 8 | return ( 9 |
    10 |
    11 |
      12 |
    • 13 | 热门 14 |
    • 15 | | 16 |
    • 17 | 最新 18 |
    • 19 | | 20 |
    • 21 | 评论 22 |
    • 23 |
    24 |
      25 |
    • 26 | 本周最热 27 |
    • 28 | · 29 |
    • 30 | 本月最热 31 |
    • 32 | · 33 |
    • 34 | 历史最热 35 |
    • 36 |
    37 |
    38 |
    39 | { 40 | this.props.list.map((item) => { 41 | return ( 42 |
    43 |
    44 | · 45 | 专栏· 46 | 47 | { 48 | item.get('user').get('username') 49 | } 50 | · 51 | 一天前· 52 | 53 | { 54 | item.get('tags').map((tagsItem, index) => { 55 | if (index === 0) { 56 | return tagsItem.get('title'); 57 | } else { 58 | return null; 59 | } 60 | }) 61 | } 62 | 63 |
    64 |

    65 | {item.get('title')} 66 |

    67 |
    68 | {item.get('likeCount')} 69 | {item.get('commentsCount')} 70 |
    71 |
    72 | ) 73 | }) 74 | } 75 |
    76 |
    77 | ) 78 | } 79 | 80 | componentDidMount() { 81 | this.props.getLeftList(); 82 | } 83 | } 84 | 85 | const mapStateToProps = (state) => { 86 | return { 87 | list: state.get('home').get('leftNav') 88 | } 89 | }; 90 | 91 | const mapDispathToProps = (dispatch) => { 92 | return { 93 | getLeftList() { 94 | dispatch(actionCreators.getLeftList()); 95 | } 96 | } 97 | }; 98 | 99 | export default connect(mapStateToProps, mapDispathToProps)(LeftList); -------------------------------------------------------------------------------- /JianShu/src/pages/home/index.css: -------------------------------------------------------------------------------- 1 | /* 主体 */ 2 | .container { 3 | width: 960px; 4 | margin: 0 auto; 5 | } 6 | .main-container { 7 | display: flex; 8 | } 9 | 10 | /* 顶部 */ 11 | .top-nav { 12 | position: fixed; 13 | left: 0; 14 | top: 59px; 15 | width: 100%; 16 | height: 46px; 17 | line-height: 46px; 18 | z-index: 100; 19 | box-shadow: 0 1px 2px 0 rgba(0,0,0,.05); 20 | font-size: 15px; 21 | background: #fff; 22 | } 23 | .top-nav-list { 24 | display: flex; 25 | width: 960px; 26 | margin: auto; 27 | position: relative; 28 | } 29 | .top-nav-list-item a { 30 | height: 100%; 31 | align-items: center; 32 | display: flex; 33 | flex-shrink: 0; 34 | color: #71777c; 35 | padding-right: 12px; 36 | } 37 | .active a { 38 | color: #007fff; 39 | } 40 | .top-nav-list-right { 41 | position: absolute; 42 | top: 0; 43 | right: 0; 44 | } 45 | 46 | /* 主内容 */ 47 | .main-container { 48 | margin-top: 120px; 49 | margin-bottom: 120px; 50 | } 51 | 52 | /* 左侧 */ 53 | .left-list { 54 | width: 650px; 55 | padding: 0 12px; 56 | background: #fff; 57 | } 58 | .left-list-top { 59 | display: flex; 60 | justify-content: space-between; 61 | height: 46px; 62 | line-height: 46px; 63 | font-size: 14px; 64 | border-bottom: 1px solid hsla(0,0%,59.2%,.1); 65 | } 66 | .left-list-top-left { 67 | display: flex; 68 | } 69 | .left-list-top-left li { 70 | margin-left: 10px; 71 | } 72 | .left-list-top-left span { 73 | color: #ccc; 74 | margin-left: 10px; 75 | } 76 | .left-list-top-right { 77 | display: flex; 78 | } 79 | li a { 80 | color: #5f6468; 81 | } 82 | .left-list-item { 83 | display: flex; 84 | flex-direction: column; 85 | padding: 18px 24px; 86 | border-bottom: 1px solid rgba(178,186,194,.15) 87 | } 88 | .left-list-item-tag { 89 | font-size: 14px; 90 | } 91 | .hot { 92 | color: red; 93 | } 94 | .special { 95 | color: #b71ed7; 96 | } 97 | .left-list-item-title { 98 | font-size: 16px; 99 | margin-top: 5px; 100 | } 101 | .left-list-item-interactive { 102 | margin-top: 5px; 103 | font-size: 14px; 104 | } 105 | .left-list-item-interactive span { 106 | display: inline-block; 107 | width: 56px; 108 | text-align: center; 109 | height: 24px; 110 | line-height: 24px; 111 | color: #b2bac2; 112 | border-radius: 1px; 113 | border: 1px solid #edeeef; 114 | } 115 | 116 | /* 右侧 */ 117 | .right-recommend { 118 | display: inline-table; 119 | width: 295px; 120 | margin-left: 15px; 121 | background: #fff; 122 | } 123 | .right-recommend-ad { 124 | width: 100%; 125 | } 126 | .right-recommend-ad a { 127 | display: inline-block; 128 | } 129 | .right-recommend-ad img { 130 | height: 40px; 131 | } 132 | .right-recommend-ad a:nth-child(2) { 133 | margin-top: 10px; 134 | } 135 | .right-recommend-author { 136 | margin-top: 10px; 137 | font-size: 15px; 138 | } 139 | .right-recommend-author-top { 140 | padding: 10px 13px; 141 | border-bottom: 1px solid hsla(0,0%,59.2%,.1); 142 | } 143 | .right-recommend-author-container { 144 | padding: 0 20px; 145 | } 146 | .right-recommend-author-item { 147 | display: flex; 148 | align-items: center; 149 | font-size: 14px; 150 | color: #909090; 151 | height: 80px; 152 | } 153 | .right-recommend-author-item img { 154 | width: 45px; 155 | height: 45px; 156 | border-radius: 50%; 157 | } 158 | .right-recommend-author-detail { 159 | margin-left: 10px; 160 | display: flex; 161 | flex-direction: column; 162 | } 163 | .right-recommend-author-title { 164 | font-size: 16px; 165 | color: #333; 166 | } -------------------------------------------------------------------------------- /JueJin/src/components/Header/index.css: -------------------------------------------------------------------------------- 1 | /* 总样式 */ 2 | header { 3 | position: fixed; 4 | top: 0; 5 | left: 0; 6 | width: 100%; 7 | height: 59px; 8 | background: #fff; 9 | border-bottom: 1px solid #f1f1f1; 10 | z-index: 99; 11 | } 12 | .header-container { 13 | display: flex; 14 | align-items: center; 15 | width: 100%; 16 | height: 100%; 17 | line-height: 60px; 18 | max-width: 960px; 19 | margin: 0 auto; 20 | } 21 | /* Logo 图标 */ 22 | .header-container-logo { 23 | width: 98px; 24 | height: 41px; 25 | margin-right: 24px; 26 | } 27 | /* ul 列表 - 左侧 */ 28 | .header-container-nav { 29 | display: flex; 30 | } 31 | .header-container-nav-active { 32 | color: #007fff; 33 | } 34 | .header-container-nav li { 35 | width: 68px; 36 | height: 60px; 37 | text-align: center; 38 | } 39 | 40 | /* ul 列表 - 右侧 */ 41 | .header-container-right { 42 | display: flex; 43 | justify-content: flex-end; 44 | width: 100%; 45 | } 46 | /* 搜索框 */ 47 | .header-container-search { 48 | display: flex; 49 | align-items: center; 50 | width: 148px; 51 | height: 60px; 52 | padding: 0 14px; 53 | } 54 | .header-container-search form { 55 | display: flex; 56 | align-items: center; 57 | position: relative; 58 | width: 130px; 59 | height: 32px; 60 | border: 1px solid rgba(151, 151, 151, 0.2); 61 | border-radius: 2px; 62 | } 63 | .header-container-search input { 64 | width: 130px; 65 | height: 32px; 66 | color: rgb(102, 102, 102); 67 | padding: 0 28px 0 12px; 68 | background-color: rgba(227,231,236,.1); 69 | } 70 | /* Search 图标 */ 71 | .icon-search { 72 | position: absolute; 73 | right: 0; 74 | width: 22px; 75 | height: 22px; 76 | padding: 0 6px; 77 | } 78 | /* 写文章 */ 79 | .header-container-add { 80 | display: flex; 81 | align-items: center; 82 | width: 80px; 83 | height: 60px; 84 | padding: 0 14px; 85 | } 86 | .header-container-add-group { 87 | display: flex; 88 | align-items: center; 89 | width: 80px; 90 | height: 32px; 91 | } 92 | .add-article { 93 | width: 64px; 94 | height: 32px; 95 | padding: 0 10px; 96 | font-size: 14px; 97 | border-radius: 3px; 98 | border-top-right-radius: 0; 99 | border-bottom-right-radius: 0; 100 | background: #0876e4; 101 | color: #fff; 102 | } 103 | .header-container-add-group div { 104 | width: 16px; 105 | text-align: center; 106 | height: 32px; 107 | line-height: 26px; 108 | border-radius: 3px; 109 | border-top-left-radius: 0; 110 | border-bottom-left-radius: 0; 111 | border-left: 1px solid hsla(0,0%,100%,.1); 112 | cursor: pointer; 113 | background: #0876e4; 114 | } 115 | .add-more { 116 | width: 0; 117 | height: 0; 118 | border-width: 3px 3px 0; 119 | border-style: solid; 120 | border-color: #fff #0876e4 #0876e4 ;/* 红 透明 透明 */ 121 | } 122 | /* 通知 */ 123 | .header-container-notice { 124 | width: 46px; 125 | height: 60px; 126 | position: relative; 127 | display: flex; 128 | align-items: center; 129 | justify-content: center; 130 | } 131 | .header-container-notice i { 132 | width: 20px; 133 | height: 36px; 134 | } 135 | .header-container-notice span { 136 | display: inline-block; 137 | box-sizing: border-box; 138 | width: 46px; 139 | text-align: center; 140 | height: 26px; 141 | line-height: 24px; 142 | position: absolute; 143 | right: -20px; 144 | top: 6px; 145 | border-radius: 23px; 146 | border: 2px solid #fff; 147 | font-size: 12px; 148 | word-break: normal; 149 | color: #f1f1f1; 150 | background-color: #007fff; 151 | } 152 | /* 用户头像 */ 153 | .header-container-user { 154 | width: 44px; 155 | text-align: right; 156 | height: 60px; 157 | margin-left: 10px; 158 | } 159 | .header-container-user img { 160 | width: 30px; 161 | height: 30px; 162 | border-radius: 44px; 163 | } -------------------------------------------------------------------------------- /JianShu/src/common/header/index.css: -------------------------------------------------------------------------------- 1 | header { 2 | position: fixed; 3 | top: 0; 4 | left: 0; 5 | width: 100%; 6 | height: 58px; 7 | display: flex; 8 | align-items: center; 9 | border-bottom: 1px solid #f1f1f1; 10 | font-size: 17px; 11 | background: #fff; 12 | } 13 | 14 | /* 头部左边 */ 15 | .header_left-img { 16 | width: 100px; 17 | height: 56px; 18 | } 19 | 20 | /* 头部中间 */ 21 | .header_center { 22 | width: 1000px; 23 | margin: 0 auto; 24 | display: flex; 25 | justify-content: space-between; 26 | } 27 | .nav-item { 28 | margin-right: 30px; 29 | display: flex; 30 | align-items: center; 31 | } 32 | 33 | /* 头部中间左部 */ 34 | .header_center-left { 35 | display: flex; 36 | } 37 | 38 | /* 头部中间左部 - 首页 */ 39 | .header_center-left-home { 40 | color: #ea6f5a; 41 | } 42 | 43 | /* 头部中间左部 - 搜索框 */ 44 | .header_center-left-search { 45 | position: relative; 46 | } 47 | .slide-enter { 48 | transition: all .2s ease-out; 49 | } 50 | .slide-enter-active { 51 | width: 280px; 52 | } 53 | .slide-exit { 54 | transition: all .2s ease-out; 55 | } 56 | .silde-exit-active { 57 | width: 240px; 58 | } 59 | .header_center-left-search { 60 | z-index: 999; 61 | } 62 | .header_center-left-search input { 63 | width: 240px; 64 | padding: 0 45px 0 20px; 65 | height: 38px; 66 | font-size: 14px; 67 | border: 1px solid #eee; 68 | border-radius: 40px; 69 | background: #eee; 70 | } 71 | .header_center-left-search .input-active { 72 | width: 280px; 73 | } 74 | .header_center-left-search .icon-search { 75 | position: absolute; 76 | top: 8px; 77 | right: 10px; 78 | } 79 | .header_center-left-search .icon-active { 80 | padding: 3px; 81 | top: 4px; 82 | border-radius: 15px; 83 | border: 1px solid #ea6f5a; 84 | } 85 | 86 | /* 头部中间左部 - 热搜 */ 87 | .header_center-left-search .icon-active:hover { 88 | cursor: pointer; 89 | } 90 | .header_center-left-hot-search:before { 91 | content: ""; 92 | left: 27px; 93 | width: 10px; 94 | height: 10px; 95 | transform: rotate(45deg); 96 | top: -5px; 97 | z-index: -1; 98 | position: absolute; 99 | background-color: #fff; 100 | box-shadow: 0 0 8px rgba(0,0,0,.2); 101 | } 102 | .header_center-left-hot-search { 103 | position: absolute; 104 | width: 250px; 105 | left: 0; 106 | top: 125%; 107 | padding: 15px; 108 | font-size: 14px; 109 | background: #fff; 110 | border-radius: 4px; 111 | box-shadow: 0 0 8px rgba(0, 0, 0, 0.2); 112 | } 113 | .header_center-left-hot-search-title { 114 | display: flex; 115 | justify-content: space-between; 116 | color: #969696; 117 | } 118 | .header_center-left-hot-search-change { 119 | display: flex; 120 | justify-content: space-between; 121 | align-items: center; 122 | } 123 | .icon-change { 124 | display: inline-block; 125 | width: 20px; 126 | height: 14px; 127 | background: url('../../resources/img/icon-change.png') no-repeat center; 128 | background-size: 100%; 129 | transition: all .2s ease-in; 130 | transform-origin: center center; 131 | } 132 | .icon-change:hover { 133 | cursor: pointer; 134 | } 135 | .span-change:hover { 136 | cursor: pointer; 137 | } 138 | .header_center-left-hot-search-content span { 139 | display: inline-block; 140 | margin-top: 10px; 141 | margin-right: 10px; 142 | padding: 2px 6px; 143 | font-size: 12px; 144 | color: #787878; 145 | border: 1px solid #ddd; 146 | border-radius: 3px; 147 | } 148 | .header_center-left-hot-search-content span:hover { 149 | cursor: pointer; 150 | } 151 | 152 | /* 头部中间右部 */ 153 | .header_center-right { 154 | display: flex; 155 | color: #969696; 156 | } 157 | 158 | /* 头部右边 */ 159 | .header_right-register, .header_right-write { 160 | width: 80px; 161 | text-align: center; 162 | height: 38px; 163 | line-height: 38px; 164 | border: 1px solid rgba(236,97,73,.7); 165 | border-radius: 20px; 166 | font-size: 15px; 167 | color: #ea6f5a; 168 | background-color: transparent; 169 | } 170 | .header_right-write { 171 | margin-left: 10px; 172 | padding-left: 10px; 173 | margin-right: 0px; 174 | color: #fff; 175 | background-color: #ea6f5a; 176 | } 177 | -------------------------------------------------------------------------------- /JueJin/src/pages/TimeLine/components/RightRecommend.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from "react"; 2 | import { Link } from 'react-router-dom'; 3 | 4 | const number = Math.round(Math.random() + 1); 5 | 6 | class RightRecommend extends Component { 7 | render() { 8 | return ( 9 | 84 | ) 85 | } 86 | } 87 | 88 | export default RightRecommend; -------------------------------------------------------------------------------- /JueJin/src/pages/TimeLine/index.css: -------------------------------------------------------------------------------- 1 | /* 顶部 */ 2 | .top-nav { 3 | position: fixed; 4 | top: 60px; 5 | left: 0; 6 | width: 100%; 7 | height: 46px; 8 | line-height: 46px; 9 | z-index: 100; 10 | box-shadow: 0 1px 2px 0 rgba(0,0,0,.05); 11 | font-size: 14px; 12 | background: #fff; 13 | } 14 | .top-nav-list { 15 | display: flex; 16 | width: 960px; 17 | margin: auto; 18 | position: relative; 19 | } 20 | .top-nav-list-item a { 21 | height: 100%; 22 | display: flex; 23 | align-items: center; 24 | flex-shrink: 0; 25 | color: #71777c; 26 | padding-right: 24px; 27 | } 28 | .top-nav-list-item .active { 29 | color: #007fff; 30 | } 31 | .top-nav-list-right { 32 | position: absolute; 33 | top: 0; 34 | right: 0; 35 | } 36 | .top-nav-list-right a { 37 | padding-right: 0; 38 | } 39 | 40 | /* 返回顶部 */ 41 | .scroll-to-top { 42 | position: fixed; 43 | right: 10px; 44 | bottom: 10px; 45 | width: 60px; 46 | height: 30px; 47 | border-radius: 5px; 48 | background: deepskyblue; 49 | color: #fff; 50 | } 51 | 52 | /* 内容 */ 53 | .timeline-container { 54 | display: flex; 55 | margin-top: 120px; 56 | } 57 | 58 | /* 左侧列表 */ 59 | section { 60 | width: 700px; 61 | background: #fff; 62 | font-size: 14px; 63 | } 64 | .left-list-nav { 65 | display: flex; 66 | justify-content: space-between; 67 | padding: 15.6px 12px; 68 | border-bottom: 1px solid hsla(0,0%,59.2%,.1); 69 | } 70 | .left-list-nav-active { 71 | color: #007fff; 72 | } 73 | .left-list-nav-left a { 74 | display: inline-block; 75 | width: 56px; 76 | text-align: center; 77 | } 78 | .left-list-nav-left-split { 79 | color: hsla(0,0%,59.2%,.2); 80 | } 81 | .left-list-nav-right a { 82 | display: inline-block; 83 | width: 72px; 84 | text-align: center; 85 | } 86 | .left-list-nav-right-split { 87 | color: hsla(0,0%,59.2%,.8); 88 | } 89 | .left-list-item { 90 | display: flex; 91 | justify-content: space-between; 92 | padding: 18px 24px; 93 | border-bottom: 1px solid hsla(0,0%,59.2%,.1); 94 | } 95 | .left-list-item img { 96 | width: 60px; 97 | height: 60px; 98 | } 99 | .left-list-item-split { 100 | display: inline-block; 101 | width: 10px; 102 | text-align: center; 103 | } 104 | .left-list-item-detail { 105 | font-size: 13px; 106 | } 107 | .left-list-item h3 { 108 | font-size: 17px; 109 | font-weight: bold; 110 | margin-top: 8px; 111 | } 112 | .left-list-item-action { 113 | display: flex; 114 | margin-top: 10px; 115 | } 116 | .left-list-item-action-button { 117 | display: flex; 118 | align-items: center; 119 | background: #fff; 120 | color: #b2bac2; 121 | border: 1px solid #edeeef; 122 | padding: 5px 10px; 123 | font-size: 12px; 124 | } 125 | .left-list-item-action .icon { 126 | width: 18px; 127 | height: 18px; 128 | margin-right: 4px; 129 | } 130 | 131 | /* 右侧侧边栏 */ 132 | aside { 133 | width: 240px; 134 | margin-left: 20px; 135 | background: #f4f5f5; 136 | } 137 | .right-recommend-ad img { 138 | width: 240px; 139 | height: 200px; 140 | } 141 | .right-recommend-author { 142 | margin-top: 12px; 143 | background: #fff; 144 | } 145 | .right-recommend-author-title { 146 | padding: 12px 16px; 147 | border-bottom: 1px solid hsla(0,0%,59.2%,.1); 148 | font-size: 14px; 149 | } 150 | .right-recommend-author-detail-item { 151 | box-sizing: border-box; 152 | display: flex; 153 | width: 100%; 154 | height: 80px; 155 | align-items: center; 156 | padding: 12px 16px; 157 | } 158 | .right-recommend-author-detail-item img { 159 | width: 46px; 160 | margin-right: 10px; 161 | } 162 | .right-recommend-author-detail-item-content p { 163 | font-size: 12px; 164 | color: #909090; 165 | margin-bottom: 4px; 166 | white-space: nowrap; 167 | overflow: hidden; 168 | text-overflow: ellipsis; 169 | } 170 | .right-recommend-author-detail-item-content p:first-child { 171 | font-size: 14px; 172 | color: #333; 173 | } 174 | .right-recommend-author-more { 175 | display: block; 176 | box-sizing: border-box; 177 | width: 100%; 178 | text-align: center; 179 | font-size: 14px; 180 | height: 42px; 181 | color: #007fff; 182 | padding: 12px 0; 183 | border-top: 1px solid hsla(0,0%,59.2%,.1); 184 | } 185 | .right-recommend-other { 186 | height: 360px; 187 | background: #fff; 188 | margin-top: 16px; 189 | } 190 | .right-recommend-other-item { 191 | display: flex; 192 | align-items: center; 193 | box-sizing: border-box; 194 | height: 60px; 195 | padding: 12px; 196 | } 197 | .right-recommend-other-item img { 198 | width: 36px; 199 | height: 36px; 200 | margin-right: 10px; 201 | } -------------------------------------------------------------------------------- /JianShu/src/common/header/index.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import { connect } from 'react-redux'; 3 | import { CSSTransition } from 'react-transition-group'; 4 | import './index.css'; 5 | import { actionCreators } from './store'; 6 | 7 | import homeImage from '../../resources/img/header-home.png'; 8 | 9 | class Header extends Component { 10 | render() { 11 | return ( 12 |
    13 |
    14 | 15 | 首页 16 | 17 |
    18 |
    19 |
    20 |
    21 | 22 | 首页 23 |
    24 |
    25 | 26 | 下载App 27 |
    28 |
    29 | 34 | this.props.searchFocus(this.props.list)} 38 | onBlur={this.props.searchBlur} 39 | /> 40 | 41 | 42 |
    47 |
    48 | 热门搜索 49 | this.props.changePage(this.props.page, this.props.totalPage, this.spinIcon)}> 50 | {this.spinIcon = icon}}> 51 | 换一批 52 | 53 |
    54 |
    55 | { 56 | this.props.list.map((item, index) => { 57 | if(index >= (this.props.page - 1) * 10 && index < this.props.page * 10) { 58 | return {item} 59 | } else { 60 | return ''; 61 | } 62 | }) 63 | } 64 |
    65 |
    66 |
    67 |
    68 |
    69 |
    70 | Aa 71 |
    72 |
    73 | 登录 74 |
    75 |
    76 |
    77 |
    78 | 注册 79 | 80 | 81 | 写文章 82 | 83 |
    84 |
    85 | ) 86 | } 87 | } 88 | 89 | const mapStateToProps = (state) => { 90 | return { 91 | inputFocus: state.get('header').get('inputFocus'), 92 | list: state.get('header').get('list'), 93 | mouseInHot: state.get('header').get('mouseInHot'), 94 | page: state.get('header').get('page'), 95 | totalPage: state.get('header').get('totalPage'), 96 | } 97 | } 98 | 99 | const mapDispathToProps = (dispatch) => { 100 | return { 101 | searchFocus(list) { 102 | if(list.size === 0) { 103 | dispatch(actionCreators.getList()); 104 | } 105 | dispatch(actionCreators.searchFocus()); 106 | }, 107 | searchBlur() { 108 | dispatch(actionCreators.searchBlur()); 109 | }, 110 | onMouseEnterHot() { 111 | dispatch(actionCreators.onMouseEnterHot()); 112 | }, 113 | onMouseLeaveHot() { 114 | dispatch(actionCreators.onMouseLeaveHot()); 115 | }, 116 | changePage(page, totalPage, spinIcon) { 117 | if(spinIcon.style.transform === 'rotate(360deg)') { 118 | spinIcon.style.transform = 'rotate(0deg)'; 119 | } else { 120 | spinIcon.style.transform = 'rotate(360deg)'; 121 | } 122 | if(page === totalPage) { 123 | page = 1; 124 | dispatch(actionCreators.changePage(page)); 125 | } else { 126 | dispatch(actionCreators.changePage(page)); 127 | } 128 | } 129 | } 130 | } 131 | 132 | export default connect(mapStateToProps, mapDispathToProps)(Header); 133 | -------------------------------------------------------------------------------- /JianShu/public/api/rightRecommendAuthor.json: -------------------------------------------------------------------------------- 1 | { 2 | "code": 0, 3 | "data": { 4 | "recommendationCard": [ 5 | { 6 | "id": "5cb4c972ef23ab50556443ac", 7 | "description": "前端领域贡献者", 8 | "author": { 9 | "id": "5ba9ea3c5188255c8b6ef168", 10 | "username": "陈煜仑", 11 | "avatarHd": "", 12 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/9/25/1660fbc60104ac18?w=1080&h=1080&f=jpeg&s=56301", 13 | "company": "智慧城市交通", 14 | "jobTitle": "前端开发@深圳", 15 | "viewerIsFollowing": false, 16 | "selfDescription": "种一棵树最好的时间是十年前,还有现在" 17 | } 18 | }, 19 | { 20 | "id": "5cb4c972ef23ab505564438c", 21 | "description": "前端领域贡献者", 22 | "author": { 23 | "id": "5bdfac11e51d453e2270389d", 24 | "username": "今晚打老虎i2016", 25 | "avatarHd": "https://mirror-gold-cdn.xitu.io/168e095c53c725a34de", 26 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/3/31/169d2354b05600f7?w=564&h=797&f=png&s=689169", 27 | "company": "", 28 | "jobTitle": "", 29 | "viewerIsFollowing": false, 30 | "selfDescription": "" 31 | } 32 | }, 33 | { 34 | "id": "5cb4c972ef23ab5055644388", 35 | "description": "前端领域贡献者", 36 | "author": { 37 | "id": "5783c481c4c9710066edc0a0", 38 | "username": "jannesand", 39 | "avatarHd": "", 40 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/2/20/1690a2f2fd5e2742?w=276&h=276&f=jpeg&s=20447", 41 | "company": "唯品会", 42 | "jobTitle": "h5前端开发", 43 | "viewerIsFollowing": false, 44 | "selfDescription": "越努力,越幸运!" 45 | } 46 | }, 47 | { 48 | "id": "5cb4c972ef23ab505564436c", 49 | "description": "前端领域贡献者", 50 | "author": { 51 | "id": "56d08dcfdf0eea79dc943244", 52 | "username": "子曰五溪", 53 | "avatarHd": "https://dn-mhke0kuv.qbox.me/P0rKrhMDIQBY8PazlqNfKFA", 54 | "avatarLarge": "https://lc-gold-cdn.xitu.io/u3UiRbBpJ6MtyCtZZRwZFwB", 55 | "company": "", 56 | "jobTitle": "厨子/摩旅/编程 | front end developer", 57 | "viewerIsFollowing": false, 58 | "selfDescription": "" 59 | } 60 | }, 61 | { 62 | "id": "5cb4c972ef23ab505564439a", 63 | "description": "前端领域贡献者", 64 | "author": { 65 | "id": "5aaf50216fb9a028bb18cae5", 66 | "username": "纳兰不是容若", 67 | "avatarHd": "", 68 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/9/28/1661ee2d90741789?w=2048&h=1409&f=jpeg&s=525782", 69 | "company": "", 70 | "jobTitle": "前端开发", 71 | "viewerIsFollowing": false, 72 | "selfDescription": "" 73 | } 74 | }, 75 | { 76 | "id": "5cb4c972ef23ab50556443a2", 77 | "description": "前端领域贡献者", 78 | "author": { 79 | "id": "59fac8c7f265da431d3c047c", 80 | "username": "前端小然子", 81 | "avatarHd": "https://mirror-gold-cdn.xitu.io/168e08af8d0e0d2b803", 82 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e08af8d0e0d2b803", 83 | "company": "中国法院网", 84 | "jobTitle": "前端研发工程师", 85 | "viewerIsFollowing": false, 86 | "selfDescription": "技术分享爱好者" 87 | } 88 | }, 89 | { 90 | "id": "5cb4c972ef23ab505564438e", 91 | "description": "前端、掘金翻译计划领域贡献者", 92 | "author": { 93 | "id": "5765fe732e958a0058225427", 94 | "username": "磊仔", 95 | "avatarHd": "https://user-gold-cdn.xitu.io/2016/11/29/27ab41dc29e2d2338de2584bc73c5d71", 96 | "avatarLarge": "https://lc-gold-cdn.xitu.io/ada965bd605a3b55371b.jpg?imageView/2/w/100/h/100/q/80/format/png", 97 | "company": "suncafe", 98 | "jobTitle": "前端开发", 99 | "viewerIsFollowing": false, 100 | "selfDescription": "前端开发工程师" 101 | } 102 | }, 103 | { 104 | "id": "5cb4c972ef23ab505564436b", 105 | "description": "前端、Vue.js 领域贡献者", 106 | "author": { 107 | "id": "5971a626f265da6c50303ae2", 108 | "username": "利维亚的杰洛特", 109 | "avatarHd": "https://mirror-gold-cdn.xitu.io/168e0869c9ae31dcc26", 110 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e0869c9ae31dcc26", 111 | "company": "好未来", 112 | "jobTitle": "前端", 113 | "viewerIsFollowing": false, 114 | "selfDescription": "2019 30th" 115 | } 116 | }, 117 | { 118 | "id": "5cb4c972ef23ab5055644369", 119 | "description": "前端、three.js 领域贡献者", 120 | "author": { 121 | "id": "578f6263128fe10063d40926", 122 | "username": "莫夭", 123 | "avatarHd": "https://mirror-gold-cdn.xitu.io/168e082da9edbdfc974", 124 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e082da9edbdfc974", 125 | "company": "Alibaba", 126 | "jobTitle": "前端", 127 | "viewerIsFollowing": false, 128 | "selfDescription": "vue/react/WebGL" 129 | } 130 | }, 131 | { 132 | "id": "5cb4c972ef23ab5055644362", 133 | "description": "前端领域贡献者", 134 | "author": { 135 | "id": "5bddafbc6fb9a049f91202dc", 136 | "username": "AppleGuard", 137 | "avatarHd": "https://mirror-gold-cdn.xitu.io/168e095bff9fc7ab3a6", 138 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e095bff9fc7ab3a6", 139 | "company": "", 140 | "jobTitle": "前端工程师 + python爱好者", 141 | "viewerIsFollowing": false, 142 | "selfDescription": "心有猛虎, 细嗅蔷薇" 143 | } 144 | } 145 | ] 146 | } 147 | } -------------------------------------------------------------------------------- /JueJin/src/pages/TimeLine/components/leftList.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from "react"; 2 | import { NavLink, Link } from 'react-router-dom'; 3 | 4 | class LeftList extends Component { 5 | render() { 6 | return ( 7 |
    8 |
    9 |
    10 | 热门 11 | | 12 | 最新 13 | | 14 | 评论 15 |
    16 |
    17 | 本周最热 18 | · 19 | 本月最热 20 | · 21 | 历史最热 22 |
    23 |
    24 |
    25 |
    26 |
    27 | 28 |
    29 | 30 | · 31 | 专栏 32 | · 33 | 郭东东 34 | · 35 | 2月前 36 | · 37 | 面试 38 |
    39 |

    中高级前端大厂面试秘籍,为你保驾护航金三银四,直通大厂(上)

    40 | 41 |
    42 | 46 | 50 |
    51 |
    52 | 缩略图 53 |
    54 |
    55 |
    56 | 57 |
    58 | 59 | · 60 | 专栏 61 | · 62 | 郭东东 63 | · 64 | 2月前 65 | · 66 | 面试 67 |
    68 |

    中高级前端大厂面试秘籍,为你保驾护航金三银四,直通大厂(上)

    69 | 70 |
    71 | 75 | 79 |
    80 |
    81 | 缩略图 82 |
    83 |
    84 |
    85 | 86 |
    87 | 88 | · 89 | 专栏 90 | · 91 | 郭东东 92 | · 93 | 2月前 94 | · 95 | 面试 96 |
    97 |

    中高级前端大厂面试秘籍,为你保驾护航金三银四,直通大厂(上)

    98 | 99 |
    100 | 104 | 108 |
    109 |
    110 | 缩略图 111 |
    112 |
    113 |
    114 | ) 115 | } 116 | } 117 | 118 | export default LeftList; -------------------------------------------------------------------------------- /JueJin/src/assets/img/logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Slice 16 5 | Created with Sketch. 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /JianShu/public/api/leftList.json: -------------------------------------------------------------------------------- 1 | { 2 | "code": 0, 3 | "data": { 4 | "articleFeed": [ 5 | { 6 | "id": "5cb3cfa06fb9a068a54c95af", 7 | "commentsCount": 5, 8 | "hot": false, 9 | "hotIndex": 9807.2865, 10 | "original": true, 11 | "originalUrl": "https://juejin.im/post/5cb3376bf265da039c0543da", 12 | "rankIndex": 28.547673167633, 13 | "screenshot": "", 14 | "content": "半月刊第四期来啦,这段时间 Daily-Interview-Question 新增了 14 道高频面试题,今天就把最近半月汇总的面试题和部分答案发给大家,帮助大家查漏补缺,欢迎 加群 互相学习。 更多更全的面试题和答案汇总在下面的项目中,点击查看。 如果修改了,Vue 是如何监…", 15 | "summaryInfo": null, 16 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 17 | "tags": [ 18 | { "id": "55964d83e4b08a686cc6b353", "title": "JavaScript" }, 19 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 20 | ], 21 | "title": "【半月刊 4】前端高频面试题及答案汇总", 22 | "type": "post", 23 | "user": { 24 | "id": "56dea4aa7664bf00559f002d", 25 | "role": "editor", 26 | "avatarHd": null, 27 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/10/19/16689e2bb057f60d?w=400&h=400&f=jpeg&s=16335", 28 | "username": "木易杨说" 29 | }, 30 | "lastCommentTime": "2019-04-15T18:01:04.078Z", 31 | "likeCount": 207, 32 | "eventInfo": null, 33 | "viewerHasLiked": false, 34 | "createdAt": "2019-04-15T00:26:08.968Z", 35 | "updatedAt": "2019-04-16T00:07:18.352Z" 36 | }, 37 | { 38 | "id": "5cb3e4e66fb9a068ae265857", 39 | "commentsCount": 57, 40 | "hot": false, 41 | "hotIndex": 6278.71, 42 | "original": true, 43 | "originalUrl": "https://juejin.im/post/5cb1d5a3f265da03587bed99", 44 | "rankIndex": 20.390697440336, 45 | "screenshot": "", 46 | "content": "其实原因很简单,那就是 forEach 只支持同步代码。 从上述代码中我们可以发现,forEach 只是简单的执行了下回调函数而已,并不会去处理异步的情况。并且你在 callback 中即使使用 break 也并不能结束遍历。 一般来说解决的办法有两种。 这样可以生效的原因是 …", 47 | "summaryInfo": null, 48 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 49 | "tags": [ 50 | { "id": "55964d83e4b08a686cc6b353", "title": "JavaScript" }, 51 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 52 | ], 53 | "title": "重学 JS:为啥 await 在 forEach 中不生效", 54 | "type": "post", 55 | "user": { 56 | "id": "574f8d8d2e958a005fd4edac", 57 | "role": "editor", 58 | "avatarHd": null, 59 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/10/30/166c3fd3666b5d05?w=200&h=200&f=jpeg&s=8287", 60 | "username": "yck" 61 | }, 62 | "lastCommentTime": "2019-04-16T00:24:39.549Z", 63 | "likeCount": 108, 64 | "eventInfo": null, 65 | "viewerHasLiked": false, 66 | "createdAt": "2019-04-15T01:56:54.397Z", 67 | "updatedAt": "2019-04-16T00:07:16.727Z" 68 | }, 69 | { 70 | "id": "5cb4a0bc6fb9a068a41183b4", 71 | "commentsCount": 1, 72 | "hot": false, 73 | "hotIndex": 894.8517, 74 | "original": true, 75 | "originalUrl": "https://juejin.im/post/5cb4a078f265da0354030026", 76 | "rankIndex": 12.403360242055, 77 | "screenshot": "https://user-gold-cdn.xitu.io/2019/4/15/16a21937cb242c2c?w=1200&h=500&f=png&s=106505", 78 | "content": "从官网的介绍中我们可以看到,首先 Prettier 的定位是一个代码格式化工具,并且比较任性(opinionated)。它移除了**几乎所有[1]**原始格式,来确保所有输出的代码符合一致。 等... 不过作为一款代码格式化工具,Prettier 通过开放了插件(Beta)的能…", 79 | "summaryInfo": null, 80 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 81 | "tags": [ 82 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }, 83 | { "id": "58c63ae4570c3500583c1b27", "title": "ESLint" } 84 | ], 85 | "title": "Prettier your project", 86 | "type": "post", 87 | "user": { 88 | "id": "5a7c03256fb9a06342148fb6", 89 | "role": "editor", 90 | "avatarHd": null, 91 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/2/8/16174c8d7e38e18c?w=98&h=98&f=png&s=21331", 92 | "username": "大搜车无线开发中心" 93 | }, 94 | "lastCommentTime": "2019-04-16T00:19:47.154Z", 95 | "likeCount": 11, 96 | "eventInfo": null, 97 | "viewerHasLiked": false, 98 | "createdAt": "2019-04-15T15:18:20.984Z", 99 | "updatedAt": "2019-04-16T00:07:19.919Z" 100 | }, 101 | { 102 | "id": "5cb36c795188251b090acd56", 103 | "commentsCount": 5, 104 | "hot": false, 105 | "hotIndex": 3265.6169, 106 | "original": true, 107 | "originalUrl": "https://juejin.im/post/5cb36a3ef265da03a1581d6d", 108 | "rankIndex": 11.876811564182, 109 | "screenshot": "", 110 | "content": "1. 1 什么是WebPack webpack 是一个现代 JavaScript 应用程序的静态模块打包工具:它做的事情是,分析你的项目结构,找到JavaScript模块以及其它的一些浏览器不能直接运行的拓展语言(Scss,TypeScript等),并生成一个或多个 bundl…", 111 | "summaryInfo": null, 112 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 113 | "tags": [ 114 | { "id": "55e325a100b0ded317d2f846", "title": "Webpack" }, 115 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 116 | ], 117 | "title": "从基础到实战 手摸手带你掌握新版Webpack4.0详解", 118 | "type": "post", 119 | "user": { 120 | "id": "5cadb8075188251aee3a58d1", 121 | "role": "guest", 122 | "avatarHd": null, 123 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/4/10/16a06a45ae6dcb23?w=161&h=240&f=jpeg&s=6265", 124 | "username": "无敌UFO" 125 | }, 126 | "lastCommentTime": "2019-04-15T17:57:05.578Z", 127 | "likeCount": 83, 128 | "eventInfo": null, 129 | "viewerHasLiked": false, 130 | "createdAt": "2019-04-15T03:25:17.324Z", 131 | "updatedAt": "2019-04-16T00:07:18.684Z" 132 | }, 133 | { 134 | "id": "5cb079865188251acc539127", 135 | "commentsCount": 22, 136 | "hot": false, 137 | "hotIndex": 9228.6081, 138 | "original": true, 139 | "originalUrl": "https://juejin.im/post/5cb078f05188251ace1fedb4", 140 | "rankIndex": 5.4156736956501, 141 | "screenshot": "https://user-gold-cdn.xitu.io/2019/4/12/16a115927295f1f3?w=750&h=750&f=jpeg&s=32900", 142 | "content": "最近在研究关于布局的设计方案,通过学习理解阿里的fusion.design的设计思想并结合手机淘宝H5版的px布局问题。逐渐有了一些想法,这里进行综合整理,也算是抛砖引玉吧。 rem和vw都是为了解决移动端适配问题。rem方案中最成功的就是淘宝的lib-flexible了,它是…", 143 | "summaryInfo": null, 144 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 145 | "tags": [ 146 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }, 147 | { "id": "555eadc1e4b00c57d9962402", "title": "CSS" } 148 | ], 149 | "title": "第三代移动端布局方案", 150 | "type": "post", 151 | "user": { 152 | "id": "5bbd67656fb9a05d3634f949", 153 | "role": "guest", 154 | "avatarHd": null, 155 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e09514836d8fceef", 156 | "username": "YataoZhang" 157 | }, 158 | "lastCommentTime": "2019-04-15T18:40:43.862Z", 159 | "likeCount": 281, 160 | "eventInfo": null, 161 | "viewerHasLiked": false, 162 | "createdAt": "2019-04-13T11:39:52.662Z", 163 | "updatedAt": "2019-04-16T00:03:22.624Z" 164 | }, 165 | { 166 | "id": "5cb448d85188251ad1351c77", 167 | "commentsCount": 4, 168 | "hot": false, 169 | "hotIndex": 606.1286, 170 | "original": true, 171 | "originalUrl": "https://juejin.im/post/5cb444605188251ada7e320d", 172 | "rankIndex": 4.6515234363263, 173 | "screenshot": "", 174 | "content": "1. 动态属性名:可使用表达式来设置动态属性名或方法名: 2. computed/methods/watch computed可缓存,但不可传参,会根据data中的属性变化而变化,即是根据响应式依赖来变化,而Date不是响应式依赖,即不会变化;method则每次都会进行计算,但…", 175 | "summaryInfo": null, 176 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 177 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 178 | "title": "理理Vue细节", 179 | "type": "post", 180 | "user": { 181 | "id": "5ba9ea3c5188255c8b6ef168", 182 | "role": "guest", 183 | "avatarHd": null, 184 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/9/25/1660fbc60104ac18?w=1080&h=1080&f=jpeg&s=56301", 185 | "username": "陈煜仑" 186 | }, 187 | "lastCommentTime": "2019-04-16T07:53:23.989Z", 188 | "likeCount": 21, 189 | "eventInfo": null, 190 | "viewerHasLiked": false, 191 | "createdAt": "2019-04-15T11:07:31.029Z", 192 | "updatedAt": "2019-04-16T00:05:24.172Z" 193 | }, 194 | { 195 | "id": "5cb402b5e51d456e651b646b", 196 | "commentsCount": 4, 197 | "hot": false, 198 | "hotIndex": 1195.3241, 199 | "original": false, 200 | "originalUrl": "https://css-tricks.com/edge-goes-chromium-what-does-it-mean-for-front-end-developers/", 201 | "rankIndex": 4.5774456669739, 202 | "screenshot": "", 203 | "content": "合久必分,分久必合\n微软拥抱开源正道,背后提高开发效率的同时,又有哪些意义?", 204 | "summaryInfo": null, 205 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 206 | "tags": [ 207 | { "id": "5cac088a6fb9a0573040d8a6", "title": "Microsoft Edge" }, 208 | { "id": "555e9ae0e4b00c57d99562ee", "title": "Chrome" }, 209 | { "id": "57089cf279bc44004c6266dc", "title": "浏览器" }, 210 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 211 | ], 212 | "title": "Microsoft 选择了 Chromium,这对前端开发来讲有什么意义?", 213 | "type": "article", 214 | "user": { 215 | "id": "551d677ee4b0cd5b623f49cb", 216 | "role": "admin", 217 | "avatarHd": null, 218 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/3/22/169a1107d352a82b?w=1122&h=1125&f=png&s=1034504", 219 | "username": "阴明" 220 | }, 221 | "lastCommentTime": "2019-04-15T13:51:01.355Z", 222 | "likeCount": 6, 223 | "eventInfo": null, 224 | "viewerHasLiked": false, 225 | "createdAt": "2019-04-15T04:04:05.761Z", 226 | "updatedAt": "2019-04-16T00:07:19.375Z" 227 | }, 228 | { 229 | "id": "5cb417ed51882554356afed6", 230 | "commentsCount": 3, 231 | "hot": false, 232 | "hotIndex": 607.6746, 233 | "original": true, 234 | "originalUrl": "https://juejin.im/post/5cb3eedcf265da038f7734c4", 235 | "rankIndex": 4.2026176707002, 236 | "screenshot": "", 237 | "content": "最近写的项目,应用里所有的ajax请求都发送了2遍。由于新项目,基础模块是新搭的,所以出现一些奇葩问题也是意料之中,啊终于第一次在chrome的devTools遇见了活的options请求。 服务器基于从预检请求头部获得的信息来判断,是否接受接下来的实际请求。 此次OPTION…", 238 | "summaryInfo": null, 239 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 240 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 241 | "title": "什么时候会发送options请求", 242 | "type": "post", 243 | "user": { 244 | "id": "58f6c9178d6d8100649aaab3", 245 | "role": "guest", 246 | "avatarHd": null, 247 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/9/6/165acae9509655c0?w=3024&h=3024&f=jpeg&s=1371970", 248 | "username": "熊也抱抱" 249 | }, 250 | "lastCommentTime": "2019-04-15T23:49:32.304Z", 251 | "likeCount": 12, 252 | "eventInfo": null, 253 | "viewerHasLiked": false, 254 | "createdAt": "2019-04-15T10:14:12.865Z", 255 | "updatedAt": "2019-04-16T00:06:27.691Z" 256 | }, 257 | { 258 | "id": "5cb337a1f265da038733928c", 259 | "commentsCount": 7, 260 | "hot": false, 261 | "hotIndex": 2660.8221, 262 | "original": true, 263 | "originalUrl": "https://juejin.im/post/5cb298625188251aeb3ec94c", 264 | "rankIndex": 4.1125091536156, 265 | "screenshot": "", 266 | "content": "PWA确实是当下很热门的技术,因为它提升了web应用的体验,甚至达到可以和原生app体验相提并论,但是它的问题就是兼容性问题,相信如果兼容性问题得到解决,这种技术一定会被大面积推广到实际应用,希望通过这篇文章能对大家了解这门技术有一定的帮助。如果有错误或不严谨的地方,欢迎批评指…", 267 | "summaryInfo": null, 268 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 269 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 270 | "title": "初探PWA", 271 | "type": "post", 272 | "user": { 273 | "id": "5927f0e10ce46300575ec67b", 274 | "role": "guest", 275 | "avatarHd": null, 276 | "avatarLarge": "https://user-gold-cdn.xitu.io/2017/9/10/b6f2ba4ff67d3b6af7842daa075b02dc", 277 | "username": "william_li" 278 | }, 279 | "lastCommentTime": "2019-04-15T18:13:28.617Z", 280 | "likeCount": 89, 281 | "eventInfo": null, 282 | "viewerHasLiked": false, 283 | "createdAt": "2019-04-14T13:38:13.031Z", 284 | "updatedAt": "2019-04-16T00:03:21.839Z" 285 | }, 286 | { 287 | "id": "5cb1a8456fb9a0688c0392ee", 288 | "commentsCount": 24, 289 | "hot": false, 290 | "hotIndex": 6511.4264, 291 | "original": true, 292 | "originalUrl": "https://juejin.im/post/5cb1a7af5188251b0c653736", 293 | "rankIndex": 3.7781750424097, 294 | "screenshot": "", 295 | "content": "我们喜欢(使用)
    标签。它们已经存在了几十年,这几十年来,当需要将一些内容包裹起来达到(添加)样式或者布局目的的时候,它们成为首选元素。查看线上站点时,看到像下面这些内容的情况依旧很常见: Hoo,那有很多的div标签。但是,它有效。我的意思主要是,它具有你需要的结构。…", 296 | "summaryInfo": null, 297 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 298 | "tags": [ 299 | { "id": "555eadbbe4b00c57d99623cc", "title": "HTML" }, 300 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 301 | ], 302 | "title": "【译】停止滥用div! HTML语义化介绍", 303 | "type": "post", 304 | "user": { 305 | "id": "5a00493f5188252c224d6475", 306 | "role": "guest", 307 | "avatarHd": null, 308 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/3/3/161ebfb7e76dd7db?w=959&h=959&f=jpeg&s=52129", 309 | "username": "call_me_R" 310 | }, 311 | "lastCommentTime": "2019-04-15T22:14:44.434Z", 312 | "likeCount": 136, 313 | "eventInfo": null, 314 | "viewerHasLiked": false, 315 | "createdAt": "2019-04-13T11:16:19.895Z", 316 | "updatedAt": "2019-04-16T00:07:19.476Z" 317 | }, 318 | { 319 | "id": "5cb3e07fe51d456e5f76c45e", 320 | "commentsCount": 1, 321 | "hot": false, 322 | "hotIndex": 1039.0156, 323 | "original": true, 324 | "originalUrl": "https://juejin.im/post/5cb3e044e51d456e51614a78", 325 | "rankIndex": 3.5512569561442, 326 | "screenshot": "", 327 | "content": "假设集合A有n个子集,每个子集有m个元素,元素都为正负数。找出任意相加为0的元素,将他们消掉,要求每次消掉的都是最大正数,且尽可能多的负元素。 穷举行不通,因为穷举的时间复杂度将达到,不可能跑完。而贪心算法可以简化问题,但不具备完整的说服力,不过可借鉴它的思想。所以,最终可选择…", 328 | "summaryInfo": null, 329 | "category": { "name": "后端", "id": "5562b419e4b00c57d9b94ae2" }, 330 | "tags": [ 331 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }, 332 | { "id": "55cd843d60b203b0519307a9", "title": "算法" } 333 | ], 334 | "title": "一道算法题(回溯+剪枝)", 335 | "type": "post", 336 | "user": { 337 | "id": "57c3970f79bc440063e58518", 338 | "role": "editor", 339 | "avatarHd": null, 340 | "avatarLarge": "https://user-gold-cdn.xitu.io/2016/11/29/c5bf3730900a3ab19fd65c7d666a19ce", 341 | "username": "超人汪小建" 342 | }, 343 | "lastCommentTime": "2019-04-15T09:51:54.482Z", 344 | "likeCount": 16, 345 | "eventInfo": null, 346 | "viewerHasLiked": false, 347 | "createdAt": "2019-04-15T01:38:07.685Z", 348 | "updatedAt": "2019-04-15T23:59:20.084Z" 349 | }, 350 | { 351 | "id": "5cb3e54d6fb9a068616b329b", 352 | "commentsCount": 2, 353 | "hot": false, 354 | "hotIndex": 852.5278, 355 | "original": true, 356 | "originalUrl": "https://juejin.im/post/5cafeb515188251aeb3ec6a2", 357 | "rankIndex": 3.1929009139221, 358 | "screenshot": "", 359 | "content": "对于根实例会走false的逻辑,进入mergeOptions函数,合并Vue的各个配置项options,比如mixins,props,methods,watch,computed,生命周期钩子等等,这是整个项目中第一次的合并配置。Vue会将所有的合并策略都保存在一个strats…", 360 | "summaryInfo": null, 361 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 362 | "tags": [ 363 | { "id": "555e9a98e4b00c57d9955f68", "title": "Vue.js" }, 364 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 365 | ], 366 | "title": "[Vue.js进阶]从源码角度剖析Vue的生命周期", 367 | "type": "post", 368 | "user": { 369 | "id": "5ba9f38ce51d450e8477bd7a", 370 | "role": "guest", 371 | "avatarHd": null, 372 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e094945d95739467", 373 | "username": "yeyan1996" 374 | }, 375 | "lastCommentTime": "2019-04-15T16:02:24.524Z", 376 | "likeCount": 15, 377 | "eventInfo": null, 378 | "viewerHasLiked": false, 379 | "createdAt": "2019-04-15T02:47:57.953Z", 380 | "updatedAt": "2019-04-15T23:39:21.593Z" 381 | }, 382 | { 383 | "id": "5cb46fd05188257aaa66ec2f", 384 | "commentsCount": 1, 385 | "hot": false, 386 | "hotIndex": 200.6516, 387 | "original": true, 388 | "originalUrl": "https://juejin.im/post/5cb46f785188251ad443c7bc", 389 | "rankIndex": 2.859708384407, 390 | "screenshot": "", 391 | "content": "自从 Web 开始迅猛发展,对程序员来说开发 API 是一项很艰巨的任务。我们开发 API 的方式必须随着时间的推移而发展,以便我们始终可以开发良好、直观且设计良好的API。 在过去几年中,GraphQL 在越来越受到开发者的欢迎。许多公司已经开始采用这种技术来构建他们的API…", 392 | "summaryInfo": null, 393 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 394 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 395 | "title": "为什么 GraphQL 是 API 的未来", 396 | "type": "post", 397 | "user": { 398 | "id": "5bcee48e518825102423e40d", 399 | "role": "guest", 400 | "avatarHd": null, 401 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/2/21/1690fd0c3f7514f2?w=626&h=626&f=jpeg&s=58154", 402 | "username": "前端先锋" 403 | }, 404 | "lastCommentTime": "2019-04-15T23:40:02.253Z", 405 | "likeCount": 7, 406 | "eventInfo": null, 407 | "viewerHasLiked": false, 408 | "createdAt": "2019-04-15T15:29:34.865Z", 409 | "updatedAt": "2019-04-16T00:03:16.693Z" 410 | }, 411 | { 412 | "id": "5cb344b25188257ab826a42b", 413 | "commentsCount": 3, 414 | "hot": false, 415 | "hotIndex": 1714.4794, 416 | "original": true, 417 | "originalUrl": "https://juejin.im/post/5cb34404f265da0384127fcd", 418 | "rankIndex": 2.7740427959677, 419 | "screenshot": "", 420 | "content": "近期和一些朋友聊到了 React-Native 的官方重构状态,而刚好近期发布的 0.59.x 系列版本中,上层设计出现了比较大的调整,结合体验之后的状态,就想聊聊 React-Native 的现状、新版本的升级体验、还有新支持的 React Hook 等特性。 本篇并不是源码…", 421 | "summaryInfo": null, 422 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 423 | "tags": [ 424 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }, 425 | { "id": "55e7cc62ddb2dd0023accd0d", "title": "React Native" } 426 | ], 427 | "title": "React Native 的未来与React Hooks", 428 | "type": "post", 429 | "user": { 430 | "id": "582aca2ba22b9d006b59ae68", 431 | "role": "editor", 432 | "avatarHd": null, 433 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/4/2/169ddef077c60a3a?w=780&h=718&f=png&s=299184", 434 | "username": "恋猫de小郭" 435 | }, 436 | "lastCommentTime": "2019-04-15T19:15:16.054Z", 437 | "likeCount": 39, 438 | "eventInfo": null, 439 | "viewerHasLiked": false, 440 | "createdAt": "2019-04-14T14:33:22.687Z", 441 | "updatedAt": "2019-04-16T00:06:20.527Z" 442 | }, 443 | { 444 | "id": "5cb42789e51d456e8b07dd3c", 445 | "commentsCount": 2, 446 | "hot": false, 447 | "hotIndex": 319.5351, 448 | "original": true, 449 | "originalUrl": "https://juejin.im/post/5cb4272d5188251b1d37a16e", 450 | "rankIndex": 2.4628421955487, 451 | "screenshot": "", 452 | "content": "作为一个总是去设计领域闲逛的开发,或许可以更好得把自己对设计的领悟给开发们讲清楚,这也是我输出的第一篇更加偏向于设计领域的文章,毕竟职业还是开发,只能算一个不入流的旁门左道的设计师,对设计的一些术语表述有误还请设计大佬谅解。 本文旨在给开发者一个基本的色彩的认识,把一些设计知识…", 453 | "summaryInfo": null, 454 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 455 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 456 | "title": "写给开发们的色彩理论", 457 | "type": "post", 458 | "user": { 459 | "id": "5b10faeb6fb9a01e273105d5", 460 | "role": "guest", 461 | "avatarHd": null, 462 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/4/15/16a2175908d6f85f?w=748&h=728&f=png&s=228660", 463 | "username": "白小寒" 464 | }, 465 | "lastCommentTime": "2019-04-15T23:35:56.843Z", 466 | "likeCount": 12, 467 | "eventInfo": null, 468 | "viewerHasLiked": false, 469 | "createdAt": "2019-04-15T11:10:22.176Z", 470 | "updatedAt": "2019-04-16T00:00:21.550Z" 471 | }, 472 | { 473 | "id": "5cb1de5df265da03555c7047", 474 | "commentsCount": 7, 475 | "hot": false, 476 | "hotIndex": 1216.0861, 477 | "original": true, 478 | "originalUrl": "https://juejin.im/post/5cb1da3ce51d456e4c4bfff8", 479 | "rankIndex": 2.2293705049941, 480 | "screenshot": "https://user-gold-cdn.xitu.io/2019/4/13/16a16cb567fe57a1?w=3812&h=1787&f=png&s=2945195", 481 | "content": "###. 跨域", 482 | "summaryInfo": null, 483 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 484 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 485 | "title": "c站(clicli.us)3.0 重构经验分享", 486 | "type": "post", 487 | "user": { 488 | "id": "5b0bb58af265da08f90f5dcf", 489 | "role": "guest", 490 | "avatarHd": null, 491 | "avatarLarge": "https://user-gold-cdn.xitu.io/2018/12/25/167e59b68382adcf?w=720&h=718&f=jpeg&s=112497", 492 | "username": "132" 493 | }, 494 | "lastCommentTime": "2019-04-15T16:02:12.471Z", 495 | "likeCount": 14, 496 | "eventInfo": null, 497 | "viewerHasLiked": false, 498 | "createdAt": "2019-04-14T15:56:36.325Z", 499 | "updatedAt": "2019-04-15T23:57:28.152Z" 500 | }, 501 | { 502 | "id": "5cb00e3b6fb9a0687177ac9f", 503 | "commentsCount": 14, 504 | "hot": false, 505 | "hotIndex": 7388.5518, 506 | "original": true, 507 | "originalUrl": "https://juejin.im/post/5cb00b1c6fb9a068a256b37c", 508 | "rankIndex": 2.0827618402423, 509 | "screenshot": "", 510 | "content": "软件系统变得复杂的三个成因是规模、结构与变化。 『按文件类型组织』,这也是前端项目中最普遍的组织方式。例如: 『按功能特性组织』。例如: 两种文件组织方式都是在做『关注点分离』,不同的是对『关注点』的理解。 File-Type First 的 『关注点』是技术和手段。 Feat…", 511 | "summaryInfo": null, 512 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 513 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 514 | "title": "用 Feature First 的方式管理前端项目复杂度", 515 | "type": "post", 516 | "user": { 517 | "id": "5c78cf4d6fb9a049af6df72b", 518 | "role": "guest", 519 | "avatarHd": null, 520 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/3/1/16937eaf5a5f02f1?w=1360&h=1360&f=png&s=80344", 521 | "username": "BDEEFE" 522 | }, 523 | "lastCommentTime": "2019-04-13T21:46:30.140Z", 524 | "likeCount": 211, 525 | "eventInfo": null, 526 | "viewerHasLiked": false, 527 | "createdAt": "2019-04-12T04:17:03.730Z", 528 | "updatedAt": "2019-04-16T00:07:18.618Z" 529 | }, 530 | { 531 | "id": "5cabe3f6e51d456e6e3891e1", 532 | "commentsCount": 54, 533 | "hot": false, 534 | "hotIndex": 21754.4762, 535 | "original": true, 536 | "originalUrl": "https://juejin.im/post/5caa0c2d51882543fa41e478", 537 | "rankIndex": 2.1060663226157, 538 | "screenshot": "", 539 | "content": "这篇文章是三天前写就的,有大佬给我提了一些修改意见,我觉得这个意见确实中肯。所以就有了这个升级的修改版本。代码同步更新到 GitHub 了。 我入职第二家公司接到的第一个需求就是修复之前外包做的滚动吸顶效果。我当时很纳闷为何一个滚动吸顶会有 bug,后来我查看代码才发现直接用的…", 540 | "summaryInfo": null, 541 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 542 | "tags": [ 543 | { "id": "55964d83e4b08a686cc6b353", "title": "JavaScript" }, 544 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" } 545 | ], 546 | "title": "【前端词典】5 种滚动吸顶实现方式的比较[性能升级版]", 547 | "type": "post", 548 | "user": { 549 | "id": "5b6d656ef265da0f7c4ff4fd", 550 | "role": "editor", 551 | "avatarHd": null, 552 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/1/14/1684b8cf1ed7df86?w=523&h=522&f=jpeg&s=32607", 553 | "username": "小生方勤" 554 | }, 555 | "lastCommentTime": "2019-04-13T11:24:05.749Z", 556 | "likeCount": 728, 557 | "eventInfo": null, 558 | "viewerHasLiked": false, 559 | "createdAt": "2019-04-09T00:14:46.743Z", 560 | "updatedAt": "2019-04-16T00:05:58.530Z" 561 | }, 562 | { 563 | "id": "5ca2f441e51d457b0d00ffc8", 564 | "commentsCount": 87, 565 | "hot": false, 566 | "hotIndex": 70889.5743, 567 | "original": true, 568 | "originalUrl": "https://juejin.im/post/5ca2e1935188254416288eb2", 569 | "rankIndex": 2.0804775905762, 570 | "screenshot": "", 571 | "content": "ECMA规范最终由TC39敲定。TC39由包括浏览器厂商在内的各方组成,他们开会推动JavaScript提案沿着一条严格的发展道路前进。 Stage 0: strawman——最初想法的提交。 Stage 1: proposal(提案)——由TC39至少一名成员倡导的正式提案文…", 572 | "summaryInfo": null, 573 | "category": { "name": "前端", "id": "5562b415e4b00c57d9b94ac8" }, 574 | "tags": [{ "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }], 575 | "title": "ES6、ES7、ES8、ES9、ES10新特性一览", 576 | "type": "post", 577 | "user": { 578 | "id": "59ee29a36fb9a0451c3990e5", 579 | "role": "guest", 580 | "avatarHd": null, 581 | "avatarLarge": "https://user-gold-cdn.xitu.io/2019/4/8/169fbe471e6bb14e?w=860&h=816&f=png&s=346726", 582 | "username": "上沅兮" 583 | }, 584 | "lastCommentTime": "2019-04-15T14:53:57.644Z", 585 | "likeCount": 1676, 586 | "eventInfo": null, 587 | "viewerHasLiked": false, 588 | "createdAt": "2019-04-02T08:27:27.280Z", 589 | "updatedAt": "2019-04-16T00:06:22.640Z" 590 | }, 591 | { 592 | "id": "5cad9746e51d456e6154b3dc", 593 | "commentsCount": 90, 594 | "hot": false, 595 | "hotIndex": 11437.62, 596 | "original": true, 597 | "originalUrl": "https://juejin.im/post/5cad966be51d456e7a303b54", 598 | "rankIndex": 1.616149650937, 599 | "screenshot": "", 600 | "content": "Scott 近两年无论是面试还是线下线上的技术分享,遇到许许多多前端同学,由于团队原因,个人原因,职业成长,技术方向,甚至家庭等等原因,在理想国与现实之间,在放弃与坚守之间,摇摆不停,心酸硬扛,大家可以找我聊聊南聊聊北,对工程师的宿命有更多的了解,有更多的看见与听见,Scott…", 601 | "summaryInfo": null, 602 | "category": { 603 | "name": "代码人生", 604 | "id": "5c9c7cca1b117f3c60fee548" 605 | }, 606 | "tags": [ 607 | { "id": "5597a05ae4b08a686ce56f6f", "title": "前端" }, 608 | { "id": "55c1748160b28fd99e49ea68", "title": "程序员" }, 609 | { "id": "5c9dc1a0518825652082e533", "title": "团队管理" } 610 | ], 611 | "title": "如何看待 996.ICU 的创业公司与成长型前端团队", 612 | "type": "post", 613 | "user": { 614 | "id": "5790c76dc4c9710054f0f58b", 615 | "role": "guest", 616 | "avatarHd": null, 617 | "avatarLarge": "https://mirror-gold-cdn.xitu.io/168e082dbe6a4e636d5", 618 | "username": "Scott" 619 | }, 620 | "lastCommentTime": "2019-04-15T19:57:20.990Z", 621 | "likeCount": 151, 622 | "eventInfo": null, 623 | "viewerHasLiked": false, 624 | "createdAt": "2019-04-10T07:25:04.810Z", 625 | "updatedAt": "2019-04-15T23:14:16.687Z" 626 | } 627 | ] 628 | } 629 | } 630 | --------------------------------------------------------------------------------