8000 add shopping · onesimplecoder/vue-book@62c39f2 · GitHub
[go: up one dir, main page]

Skip to content

Commit 62c39f2

Browse files
committed
add shopping
1 parent d0da8b5 commit 62c39f2

File tree

15 files changed

+1037
-0
lines changed

15 files changed

+1037
-0
lines changed

shopping/.babelrc

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"presets": ["es2015"],
3+
"plugins": ["transform-runtime"],
4+
"comments": false
5+
}

shopping/app.vue

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<template>
2+
<div>
3+
<div class="header">
4+
<router-link to="/list" class="header-title">电商网站示例</router-link>
5+
<div class="header-menu">
6+
<router-link to="/cart" class="header-menu-cart">
7+
购物车
8+
<span v-if="cartList.length">{{ cartList.length }}</span>
9+
</router-link>
10+
</div>
11+
</div>
12+
<router-view></router-view>
13+
</div>
14+
</template>
15+
<script>
16+
export default {
17+
computed: {
18+
cartList () {
19+
return this.$store.state.cartList;
20+
}
21+
}
22+
}
23+
</script>

shopping/components/product.vue

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,89 @@
1+
<template>
2+
<div class="product">
3+
<router-link :to="'/product/' + info.id" class="product-main">
4+
<img :src="info.image">
5+
<h4>{{ info.name }}</h4>
6+
<div class="product-color" :style="{ background: colors[info.color]}"></div>
7+
<div class="product-cost">¥ {{ info.cost }}</div>
8+
<div class="product-add-cart" @click.prevent="handleCart">加入购物车</div>
9+
</router-link>
10+
</div>
11+
</template>
12+
<script>
13+
export default {
14+
props: {
15+
info: Object
16+
},
17+
data () {
18+
return {
19+
colors: {
20+
'白色': '#ffffff',
21+
'金色': '#dac272',
22+
'蓝色': '#233472',
23+
'红色': '#f2352e'
24+
}
25+
}
26+
},
27+
methods: {
28+
handleCart () {
29+
this.$store.commit('addCart', this.info.id);
30+
}
31+
}
32+
};
33+
</script>
34+
<style scoped>
35+
.product{
36+
width: 25%;
37+
float: left;
38+
}
39+
.product-main{
40+
display: block;
41+
margin: 16px;
42+
padding: 16px;
43+
border: 1px solid #dddee1;
44+
border-radius: 6px;
45+
overflow: hidden;
46+
background: #fff;
47+
text-align: center;
48+
position: relative;
49+
}
50+
.product-main img{
51+
width: 100%;
52+
}
53+
h4{
54+
color: #222;
55+
overflow: hidden;
56+
text-overflow: ellipsis;
57+
white-space: nowrap;
58+
}
59+
.product-main:hover h4{
60+
color: #0070c9;
61+
}
62+
.product-color{
63+
display: block;
64+
width: 16px;
65+
height: 16px;
66+
border: 1px solid #dddee1;
67+
border-radius: 50%;
68+
margin: 6px auto;
69+
}
70+
.product-cost{
71+
color: #de4037;
72+
margin-top: 6px;
73+
}
74+
.product-add-cart{
75+
display: none;
76+
padding: 4px 8px;
77+
background: #2d8cf0;
78+
color: #fff;
79+
font-size: 12px;
80+
border-radius: 3px;
81+
cursor: pointer;
82+
position: absolute;
83+
top: 5px;
84+
right: 5px;
85+
}
86+
.product-main:hover .product-add-cart{
87+
display: inline-block;
88+
}
89+
</style>

shopping/index.ejs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
<!DOCTYPE html>
2+
<html lang="zh-CN">
3+
<head>
4+
<meta charset="UTF-8">
5+
<title>电商网站示例</title>
6+
<link rel="stylesheet" href="<%= htmlWebpackPlugin.files.css[0] %>">
7+
</head>
8+
<body>
9+
<div id="app"></div>
10+
<script type="text/javascript" src="<%= htmlWebpackPlugin.files.js[0] %>"></script>
11+
</body>
12+
</html>

shopping/index.html

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
<!DOCTYPE html>
2+
<html>
3+
<head>
4+
<meta charset="utf-8">
5+
<title>Webpack App</title>
6+
<link rel="stylesheet" type="text/css" href="/dist/main.css">
7+
</head>
8+
<body>
9+
<div id="app">
10+
11+
</div>
12+
<script type="text/javascript" src="/dist/main.js"></script>
13+
</body>
14+
</html>

shopping/main.js

Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
import Vue from 'vue';
2+
import VueRouter from 'vue-router';
3+
import Routers from './router';
4+
import Vuex from 'vuex';
5+
import App from './app.vue';
6+
import './style.css';
7+
8+
import product_data from './product';
9+
10+
Vue.use(VueRouter);
11+
Vue.use(Vuex);
12+
13+
// 路由配置
14+
const RouterConfig = {
15+
// 使用 HTML5 的 History 路由模式
16+
mode: 'history',
17+
routes: Routers
18+
};
19+
const router = new VueRouter(RouterConfig);
20+
21+
router.beforeEach((to, from, next) => {
22+
window.document.title = to.meta.title;
23+
next();
24+
});
25+
26+
router.afterEach((to, from, next) => {
27+
window.scrollTo(0, 0);
28+
});
29+
30+
// 数组排重
31+
function getFilterArray (array) {
32+
const res = [];
33+
const json = {};
34+
for (let i = 0; i < array.length; i++){
35+
const _self = array[i];
36+
if(!json[_self]){
37+
res.push(_self);
38+
json[_self] = 1;
39+
}
40+
}
41+
return res;
42+
}
43+
44+
const store = new Vuex.Store({
45+
state: {
46+
productList: [],
47+
cartList: []
48+
},
49+
getters: {
50+
brands: state => {
51+
const brands = state.productList.map(item => item.brand);
52+
return getFilterArray(brands);
53+
},
54+
colors: state => {
55+
const colors = state.productList.map(item => item.color);
56+
return getFilterArray(colors);
57+
}
58+
},
59+
mutations: {
60+
// 添加商品列表
61+
setProductList (state, data) {
62+
state.productList = data;
63+
},
64+
// 添加到购物车
65+
addCart (state, id) {
66+
// 先判断购物车是否已有,如果有,数量+1
67+
const isAdded = state.cartList.find(item => item.id === id);
68+
if (isAdded) {
69+
isAdded.count ++;
70+
} else {
71+
state.cartList.push({
72+
id: id,
73+
count: 1
74+
})
75+
}
76+
},
77+
// 修改商品数量
78+
editCartCount (state, payload) {
79+
const product = state.cartList.find(item => item.id === payload.id);
80+
product.count += payload.count;
81+
},
82+
// 删除商品
83+
deleteCart (state, id) {
84+
const index = state.cartList.findIndex(item => item.id === id);
85+
state.cartList.splice(index, 1);
86+
},
87+
// 清空购物车
88+
emptyCart (state) {
89+
state.cartList = [];
90+
}
91+
},
92+
actions: {
93+
// 请求商品列表
94+
getProductList (context) {
95+
// 真实环境通过 ajax 获取,这里用异步模拟
96+
setTimeout(() => {
97+
context.commit('setProductList', product_data);
98+
}, 500);
99+
},
100+
// 购买
101+
buy (context) {
102+
// 真实环境应通过 ajax 提交购买请求后再清空购物列表
103+
return new Promise(resolve=> {
104+
setTimeout(() => {
105+
context.commit('emptyCart');
106+
resolve();
107+
}, 500)
108+
});
109+
}
110+
}
111+
});
112+
113+
new Vue({
114+
el: '#app',
115+
router: router,
116+
store: store,
117+
render: h => {
118+
return h(App)
119+
}
120+
});

shopping/package.json

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
{
2+
"name": "demo",
3+
"version": "1.0.0",
4+
"description": "",
5+
"main": "index.js",
6+
"scripts": {
7+
"test": "echo \"Error: no test specified\" && exit 1",
8+
"dev": "webpack-dev-server --open --history-api-fallback --config webpack.config.js",
9+
"build": "webpack --progress --hide-modules --config webpack.prod.config.js"
10+
},
11+
"author": "",
12+
"license": "ISC",
13+
"devDependencies": {
14+
"babel": "^6.23.0",
15+
"babel-core": "^6.24.0",
16+
"babel-loader": "^6.4.1",
17+
"babel-plugin-transform-runtime": "^6.23.0",
18+
"babel-preset-es2015": "^6.24.0",
19+
"babel-runtime": "^6.23.0",
20+
"css-loader": "^0.27.3",
21+
"extract-text-webpack-plugin": "^2.1.0",
22+
"file-loader": "^0.10.1",
23+
"html-webpack-plugin": "^2.28.0",
24+
"style-loader": "^0.16.1",
25+
"url-loader": "^0.5.8",
26+
"vue-hot-reload-api": "^2.0.11",
27+
"vue-loader": "^11.3.4",
28+
"vue-style-loader": "^2.0.5",
29+
"vue-template-compiler": "^2.2.6",
30+
"webpack": "^2.3.2",
31+
"webpack-dev-server": "^2.4.2",
32+
"webpack-merge": "^4.1.0"
33+
},
34+
"dependencies": {
35+
"vue": "^2.2.6",
36+
"vue-router": "^2.3.1",
37+
"vuex": "^2.2.1"
38+
}
39+
}

0 commit comments

Comments
 (0)
0