Showing
5 changed files
with
344 additions
and
121 deletions
@@ -6,7 +6,97 @@ | @@ -6,7 +6,97 @@ | ||
6 | 6 | ||
7 | var $ = require('yoho.zepto'), | 7 | var $ = require('yoho.zepto'), |
8 | ellipsis = require('mlellipsis'), | 8 | ellipsis = require('mlellipsis'), |
9 | - lazyLoad = require('yoho.lazyload'); | 9 | + lazyLoad = require('yoho.lazyload'), |
10 | + IScroll = require('iscroll/iscroll-probe'); | ||
11 | + | ||
12 | +var $authorIntro = $('.author .intro'); | ||
13 | + | ||
14 | +var isIphone = navigator.userAgent.indexOf('iPhone') > 0 ? true : false; | ||
15 | + | ||
16 | +var hasCollocationBlock = $('.collocation-block').length > 0 ? true : false; | ||
17 | + | ||
18 | +//collocation block variable | ||
19 | +var thumbWidth = 0, | ||
20 | + $fixedThumbContainer = $(''), | ||
21 | + $coBlock, $thumbContainer, $thumbs, $prods, | ||
22 | + scrollToEl; | ||
23 | + | ||
24 | +var scrollToEl = document.querySelector('#wrapper .collocation-block'); | ||
25 | + | ||
26 | +var winW = $(window).width(); | ||
27 | + | ||
28 | +var myScroll; | ||
29 | + | ||
30 | +/** | ||
31 | + * 计算搭配的箭头的位置 | ||
32 | + * @param $curPos 当前focus的搭配项 | ||
33 | + */ | ||
34 | +function posCollocationArrow($curCo) { | ||
35 | + var left = $curCo.offset().left, | ||
36 | + bgPos = -winW + left + (thumbWidth / 2) + 'px'; | ||
37 | + | ||
38 | + $thumbContainer.css({ | ||
39 | + backgroundPosition: bgPos + ' bottom' | ||
40 | + }); | ||
41 | + | ||
42 | + if (isIphone) { | ||
43 | + $fixedThumbContainer.css({ | ||
44 | + backgroundPosition: bgPos + ' bottom' | ||
45 | + }); | ||
46 | + } | ||
47 | +} | ||
48 | + | ||
49 | +//搭配thumb的touch事件句柄 | ||
50 | +function thumbTouchEvt(e) { | ||
51 | + var $curCo = $(e.currentTarget), | ||
52 | + index = $curCo.index(), | ||
53 | + $brother, $brotherCo, | ||
54 | + $curProds; | ||
55 | + | ||
56 | + if ($curCo.hasClass('focus')) { | ||
57 | + return; | ||
58 | + } | ||
59 | + | ||
60 | + $thumbs.filter('.focus').removeClass('focus'); | ||
61 | + | ||
62 | + if (isIphone) { | ||
63 | + if ($curCo.closest('.fixed-thumb-container').length > 0) { | ||
64 | + $brother = $thumbContainer; | ||
65 | + } else { | ||
66 | + $brother = $fixedThumbContainer; | ||
67 | + } | ||
68 | + | ||
69 | + $brotherCo = $brother.find('.thumb').eq(index); | ||
70 | + $fixedThumbContainer.find('.thumb.focus').removeClass('focus'); | ||
71 | + $brotherCo.addClass('focus'); | ||
72 | + } | ||
73 | + | ||
74 | + $curCo.addClass('focus'); | ||
75 | + | ||
76 | + //定位arrow | ||
77 | + posCollocationArrow($curCo); | ||
78 | + | ||
79 | + $prods.not('.hide').addClass('hide'); | ||
80 | + $curProds = $prods.eq(index); | ||
81 | + $curProds.removeClass('hide'); | ||
82 | + | ||
83 | + // | ||
84 | + lazyLoad($curProds.find('.lazy')); | ||
85 | + | ||
86 | + if (isIphone) { | ||
87 | + if (myScroll) { | ||
88 | + myScroll.scrollToElement(scrollToEl, 400); | ||
89 | + } | ||
90 | + } else { | ||
91 | + $('body').animate({ | ||
92 | + scrollTop: $coBlock.offset().top | ||
93 | + }, 400); | ||
94 | + } | ||
95 | +} | ||
96 | + | ||
97 | +if (isIphone) { | ||
98 | + $('#wrapper').addClass('ios'); | ||
99 | +} | ||
10 | 100 | ||
11 | ellipsis.init(); | 101 | ellipsis.init(); |
12 | 102 | ||
@@ -15,4 +105,114 @@ lazyLoad($('.lazy')); | @@ -15,4 +105,114 @@ lazyLoad($('.lazy')); | ||
15 | //title mlellipsis | 105 | //title mlellipsis |
16 | $('.info-list .title, .one-good .reco-name').each(function() { | 106 | $('.info-list .title, .one-good .reco-name').each(function() { |
17 | this.mlellipsis(2); | 107 | this.mlellipsis(2); |
18 | -}); | ||
108 | +}); | ||
109 | + | ||
110 | +//offset.left约等于marginLeft的值则表示介绍被换行,则清除intro的paddingTop让其更靠近头像和作者名 | ||
111 | +if (parseInt($authorIntro.offset().left, 10) === parseInt($authorIntro.css('margin-left'), 10)) { | ||
112 | + $authorIntro.css('padding-top', 0); | ||
113 | +} | ||
114 | + | ||
115 | +//有搭配模块,iphone使用iscroll初始化滚动并有固定的搭配栏,其他的没有 | ||
116 | +if (hasCollocationBlock) { | ||
117 | + $coBlock = $('.collocation-block'); | ||
118 | + $thumbContainer = $coBlock.children('.thumb-container'); | ||
119 | + $thumbs = $thumbContainer.find('li'); | ||
120 | + $prods = $coBlock.find('.prod'); | ||
121 | + | ||
122 | + thumbWidth = $thumbs.width(); | ||
123 | + | ||
124 | + if (isIphone) { | ||
125 | + $fixedThumbContainer = $('#wrapper') | ||
126 | + .after($thumbContainer.clone().addClass('fixed-thumb-container fixed-bottom')) | ||
127 | + .next('.thumb-container'); | ||
128 | + | ||
129 | + //load img of fixed thumb container | ||
130 | + lazyLoad($fixedThumbContainer.find('.lazy'), { | ||
131 | + event: 'sporty' | ||
132 | + }); | ||
133 | + } | ||
134 | + | ||
135 | + //Init Arrow Position | ||
136 | + posCollocationArrow($thumbs.filter('.focus')); | ||
137 | + | ||
138 | + $thumbContainer.delegate('.thumb', 'touchend', thumbTouchEvt); | ||
139 | + | ||
140 | + if (isIphone) { | ||
141 | + $fixedThumbContainer.delegate('.thumb', 'touchend', thumbTouchEvt); | ||
142 | + } | ||
143 | +} | ||
144 | + | ||
145 | +// 初始化iscroll | ||
146 | +window.onload = function() { | ||
147 | + var $scroller = $('#scroller'); | ||
148 | + | ||
149 | + var winH, tcH, cbH, cbTop, fixedThumbDom; | ||
150 | + | ||
151 | + if (!isIphone) { | ||
152 | + return; | ||
153 | + } | ||
154 | + | ||
155 | + myScroll = new IScroll('#wrapper', { | ||
156 | + probeType: 3, | ||
157 | + mouseWheel: true, | ||
158 | + click: true | ||
159 | + }); | ||
160 | + | ||
161 | + document.addEventListener('touchmove', function (e) { | ||
162 | + e.preventDefault(); | ||
163 | + }, false); | ||
164 | + | ||
165 | + if (!hasCollocationBlock) { | ||
166 | + myScroll.on('scroll', function() { | ||
167 | + $scroller.trigger('scroll'); | ||
168 | + }); | ||
169 | + return; | ||
170 | + } | ||
171 | + | ||
172 | + winH = $(window).height(); | ||
173 | + fixedThumbDom = $fixedThumbContainer[0]; | ||
174 | + | ||
175 | + tcH = $thumbContainer.height(); | ||
176 | + cbH = $coBlock.height(); | ||
177 | + cbTop = $coBlock.offset().top; | ||
178 | + | ||
179 | + myScroll.on('scroll', function() { | ||
180 | + var sTop = -this.y; | ||
181 | + var classList = fixedThumbDom.className; | ||
182 | + | ||
183 | + if (sTop <= cbTop - winH + tcH) { | ||
184 | + if (classList.indexOf('fixed-bottom') === -1) { | ||
185 | + $fixedThumbContainer | ||
186 | + .addClass('fixed-bottom') | ||
187 | + .removeClass('hide'); | ||
188 | + } | ||
189 | + } else if (sTop <= cbTop) { | ||
190 | + if (classList.indexOf('hide') === -1) { | ||
191 | + $fixedThumbContainer | ||
192 | + .addClass('hide') | ||
193 | + .removeClass('fixed-bottom fixed-top'); | ||
194 | + } | ||
195 | + } else if (sTop <= cbTop + cbH - tcH) { | ||
196 | + if (classList.indexOf('fixed-top') === -1) { | ||
197 | + $fixedThumbContainer | ||
198 | + .addClass('fixed-top') | ||
199 | + .removeClass('hide absolute') | ||
200 | + .css('top', ''); | ||
201 | + } | ||
202 | + } else if (sTop <= cbTop + cbH) { | ||
203 | + if (classList.indexOf('absolute') === -1) { | ||
204 | + $fixedThumbContainer | ||
205 | + .addClass('absolute') | ||
206 | + .removeClass('fixed-top hide'); | ||
207 | + } | ||
208 | + fixedThumbDom.style.top = cbTop + cbH - tcH - sTop + 'px'; | ||
209 | + } else if (sTop > cbTop + cbH) { | ||
210 | + if (classList.indexOf('hide') === -1) { | ||
211 | + $fixedThumbContainer | ||
212 | + .addClass('hide') | ||
213 | + .removeClass('absolute'); | ||
214 | + } | ||
215 | + } | ||
216 | + $scroller.trigger('scroll'); | ||
217 | + }); | ||
218 | +}; |
@@ -20,7 +20,8 @@ | @@ -20,7 +20,8 @@ | ||
20 | "yoho.jquery": "1.8.3", | 20 | "yoho.jquery": "1.8.3", |
21 | "yoho.lazyload": "1.1.0", | 21 | "yoho.lazyload": "1.1.0", |
22 | "mlellipsis": "0.0.6", | 22 | "mlellipsis": "0.0.6", |
23 | - "yoho.iswiper": "3.0.1" | 23 | + "yoho.iswiper": "3.0.1", |
24 | + "iscroll": "5.1.2" | ||
24 | }, | 25 | }, |
25 | "devDependencies": { | 26 | "devDependencies": { |
26 | "expect.js": "0.3.1" | 27 | "expect.js": "0.3.1" |
@@ -55,16 +55,16 @@ $clothes: sprite-map("guang/clothes/*.png"); | @@ -55,16 +55,16 @@ $clothes: sprite-map("guang/clothes/*.png"); | ||
55 | float: left; | 55 | float: left; |
56 | font-size: 28rem / $pxConvertRem; | 56 | font-size: 28rem / $pxConvertRem; |
57 | color: #000; | 57 | color: #000; |
58 | - padding: 30rem / $pxConvertRem; | ||
59 | - margin-left: 30rem / $pxConvertRem 0; | 58 | + padding: 30rem / $pxConvertRem 0; |
59 | + margin-left: 30rem / $pxConvertRem; | ||
60 | } | 60 | } |
61 | 61 | ||
62 | .intro { | 62 | .intro { |
63 | float: left; | 63 | float: left; |
64 | font-size: 28rem / $pxConvertRem; | 64 | font-size: 28rem / $pxConvertRem; |
65 | color: #b0b0b0; | 65 | color: #b0b0b0; |
66 | - padding: 30rem / $pxConvertRem; | ||
67 | - margin-left: 30rem / $pxConvertRem 0; | 66 | + padding: 30rem / $pxConvertRem 0; |
67 | + margin-left: 30rem / $pxConvertRem; | ||
68 | } | 68 | } |
69 | } | 69 | } |
70 | 70 | ||
@@ -116,131 +116,135 @@ $clothes: sprite-map("guang/clothes/*.png"); | @@ -116,131 +116,135 @@ $clothes: sprite-map("guang/clothes/*.png"); | ||
116 | .collocation-block { | 116 | .collocation-block { |
117 | background: #fff; | 117 | background: #fff; |
118 | 118 | ||
119 | - .thumb-container { | ||
120 | - padding-top: 30rem / $pxConvertRem; | ||
121 | - padding-left: 30rem / $pxConvertRem; | ||
122 | - background: transparent image-url('guang/thumb-container-bg.png') no-repeat; | ||
123 | - background-size: 100% 100%; | ||
124 | - | ||
125 | - &.fixed-top { | ||
126 | - position: fixed; | ||
127 | - left: 0; | ||
128 | - right: 0; | ||
129 | - top: 0; | ||
130 | - } | ||
131 | - | ||
132 | - &.fixed-bottom { | ||
133 | - position: fixed; | ||
134 | - left: 0; | ||
135 | - right: 0; | ||
136 | - bottom: 0; | ||
137 | - background: rgba(255,255,255,0.9); | ||
138 | - } | ||
139 | - | ||
140 | - &.absolute { | ||
141 | - position: absolute; | ||
142 | - left: 0; | ||
143 | - right: 0; | ||
144 | - } | 119 | + .good-list { |
120 | + padding-left:15rem / $pxConvertRem; | ||
121 | + } | ||
122 | + } | ||
145 | 123 | ||
146 | - &.static { | ||
147 | - position: static; | ||
148 | - } | 124 | + .thumb-container { |
125 | + padding-top: 30rem / $pxConvertRem; | ||
126 | + padding-left: 30rem / $pxConvertRem; | ||
127 | + background: transparent image-url('guang/thumb-container-bg.png') no-repeat; | ||
128 | + background-size: 200% 100%; | ||
129 | + | ||
130 | + &.fixed-top { | ||
131 | + position: fixed; | ||
132 | + left: 0; | ||
133 | + right: 0; | ||
134 | + top: 0; | ||
149 | } | 135 | } |
150 | 136 | ||
151 | - .thumb { | ||
152 | - display: inline-block; | ||
153 | - position: relative; | ||
154 | - margin-right: 22rem / $pxConvertRem; | ||
155 | - padding-bottom: 30rem / $pxConvertRem; | 137 | + &.fixed-bottom { |
138 | + position: fixed; | ||
139 | + left: 0; | ||
140 | + right: 0; | ||
141 | + bottom: 0; | ||
142 | + background: rgba(255,255,255,0.9); | ||
143 | + } | ||
156 | 144 | ||
157 | - &:last-child { | ||
158 | - margin-right: 0; | ||
159 | - } | 145 | + &.absolute { |
146 | + position: absolute; | ||
147 | + left: 0; | ||
148 | + right: 0; | ||
149 | + } | ||
160 | 150 | ||
161 | - &.focus .thumb-img { | ||
162 | - border-color: #000; | ||
163 | - } | 151 | + &.static { |
152 | + position: static; | ||
164 | } | 153 | } |
165 | 154 | ||
166 | - .thumb-img { | ||
167 | - height: 134rem / $pxConvertRem; | ||
168 | - width: 96rem / $pxConvertRem; | ||
169 | - border: 1px solid transparent; | 155 | + &.hide { |
156 | + display: none; | ||
170 | } | 157 | } |
158 | + } | ||
171 | 159 | ||
172 | - .good-list { | ||
173 | - padding-left:15rem / $pxConvertRem; | 160 | + .clothe-type { |
161 | + position: absolute; | ||
162 | + right: 6rem / $pxConvertRem; | ||
163 | + bottom: 34rem / $pxConvertRem; | ||
164 | + width: 20px; | ||
165 | + height: 20px; | ||
166 | + @include border-radius(50%); | ||
167 | + | ||
168 | + &.bag { | ||
169 | + @include retina-sprite ($clothes, bag, 80/20); | ||
170 | + background-color: #fff; | ||
171 | + background-size: 100%; | ||
174 | } | 172 | } |
175 | 173 | ||
176 | - .clothe-type { | ||
177 | - position: absolute; | ||
178 | - right: 6rem / $pxConvertRem; | ||
179 | - bottom: 34rem / $pxConvertRem; | ||
180 | - width: 20px; | ||
181 | - height: 20px; | ||
182 | - @include border-radius(50%); | ||
183 | - | ||
184 | - &.bag { | ||
185 | - @include retina-sprite ($clothes, bag, 80/20); | ||
186 | - background-color: #fff; | ||
187 | - background-size: 100%; | ||
188 | - } | ||
189 | - | ||
190 | - &.cloth { | ||
191 | - @include retina-sprite ($clothes, cloth, 80/20); | ||
192 | - background-color: #fff; | ||
193 | - background-size: 100%; | ||
194 | - } | ||
195 | - | ||
196 | - &.dress { | ||
197 | - @include retina-sprite ($clothes, dress, 80/20); | ||
198 | - background-color: #fff; | ||
199 | - background-size: 100%; | ||
200 | - } | ||
201 | - | ||
202 | - &.headset { | ||
203 | - @include retina-sprite ($clothes, headset, 80/20); | ||
204 | - background-color: #fff; | ||
205 | - background-size: 100%; | ||
206 | - } | ||
207 | - | ||
208 | - &.lamp { | ||
209 | - @include retina-sprite ($clothes, lamp, 80/20); | ||
210 | - background-color: #fff; | ||
211 | - background-size: 100%; | ||
212 | - } | ||
213 | - | ||
214 | - &.pants { | ||
215 | - @include retina-sprite ($clothes, pants, 80/20); | ||
216 | - background-color: #fff; | ||
217 | - background-size: 100%; | ||
218 | - } | ||
219 | - | ||
220 | - &.shoe { | ||
221 | - @include retina-sprite ($clothes, shoe, 80/20); | ||
222 | - background-color: #fff; | ||
223 | - background-size: 100%; | ||
224 | - } | ||
225 | - | ||
226 | - &.swim-suit { | ||
227 | - @include retina-sprite ($clothes, swim-suit, 80/20); | ||
228 | - background-color: #fff; | ||
229 | - background-size: 100%; | ||
230 | - } | ||
231 | - | ||
232 | - &.under { | ||
233 | - @include retina-sprite ($clothes, under, 80/20); | ||
234 | - background-color: #fff; | ||
235 | - background-size: 100%; | ||
236 | - } | ||
237 | - | ||
238 | - &.watch { | ||
239 | - @include retina-sprite ($clothes, watch, 80/20); | ||
240 | - background-color: #fff; | ||
241 | - background-size: 100%; | ||
242 | - } | 174 | + &.cloth { |
175 | + @include retina-sprite ($clothes, cloth, 80/20); | ||
176 | + background-color: #fff; | ||
177 | + background-size: 100%; | ||
178 | + } | ||
179 | + | ||
180 | + &.dress { | ||
181 | + @include retina-sprite ($clothes, dress, 80/20); | ||
182 | + background-color: #fff; | ||
183 | + background-size: 100%; | ||
184 | + } | ||
185 | + | ||
186 | + &.headset { | ||
187 | + @include retina-sprite ($clothes, headset, 80/20); | ||
188 | + background-color: #fff; | ||
189 | + background-size: 100%; | ||
190 | + } | ||
191 | + | ||
192 | + &.lamp { | ||
193 | + @include retina-sprite ($clothes, lamp, 80/20); | ||
194 | + background-color: #fff; | ||
195 | + background-size: 100%; | ||
196 | + } | ||
197 | + | ||
198 | + &.pants { | ||
199 | + @include retina-sprite ($clothes, pants, 80/20); | ||
200 | + background-color: #fff; | ||
201 | + background-size: 100%; | ||
243 | } | 202 | } |
203 | + | ||
204 | + &.shoe { | ||
205 | + @include retina-sprite ($clothes, shoe, 80/20); | ||
206 | + background-color: #fff; | ||
207 | + background-size: 100%; | ||
208 | + } | ||
209 | + | ||
210 | + &.swim-suit { | ||
211 | + @include retina-sprite ($clothes, swim-suit, 80/20); | ||
212 | + background-color: #fff; | ||
213 | + background-size: 100%; | ||
214 | + } | ||
215 | + | ||
216 | + &.under { | ||
217 | + @include retina-sprite ($clothes, under, 80/20); | ||
218 | + background-color: #fff; | ||
219 | + background-size: 100%; | ||
220 | + } | ||
221 | + | ||
222 | + &.watch { | ||
223 | + @include retina-sprite ($clothes, watch, 80/20); | ||
224 | + background-color: #fff; | ||
225 | + background-size: 100%; | ||
226 | + } | ||
227 | + } | ||
228 | + | ||
229 | + .thumb { | ||
230 | + display: inline-block; | ||
231 | + position: relative; | ||
232 | + margin-right: 22rem / $pxConvertRem; | ||
233 | + padding-bottom: 30rem / $pxConvertRem; | ||
234 | + | ||
235 | + &:last-child { | ||
236 | + margin-right: 0; | ||
237 | + } | ||
238 | + | ||
239 | + &.focus .thumb-img { | ||
240 | + border-color: #000; | ||
241 | + } | ||
242 | + } | ||
243 | + | ||
244 | + .thumb-img { | ||
245 | + height: 134rem / $pxConvertRem; | ||
246 | + width: 96rem / $pxConvertRem; | ||
247 | + border: 1px solid transparent; | ||
244 | } | 248 | } |
245 | 249 | ||
246 | .related-reco-block { | 250 | .related-reco-block { |
@@ -137,7 +137,7 @@ | @@ -137,7 +137,7 @@ | ||
137 | <ul class="info-list"> | 137 | <ul class="info-list"> |
138 | {{# relatedInfo}} | 138 | {{# relatedInfo}} |
139 | <li> | 139 | <li> |
140 | - <a href={{url}}> | 140 | + <a class="clearfix" href={{url}}> |
141 | <img class="lazy {{#if squareThumb}}square{{/if}}" data-original={{thumb}}> | 141 | <img class="lazy {{#if squareThumb}}square{{/if}}" data-original={{thumb}}> |
142 | <span class="title">{{title}}</span> | 142 | <span class="title">{{title}}</span> |
143 | <span class="publish-time"> | 143 | <span class="publish-time"> |
@@ -56,6 +56,24 @@ class DetailController extends AbstractAction | @@ -56,6 +56,24 @@ class DetailController extends AbstractAction | ||
56 | 'isFew' => true, | 56 | 'isFew' => true, |
57 | 'url' => '' | 57 | 'url' => '' |
58 | ) | 58 | ) |
59 | + ), | ||
60 | + array( | ||
61 | + 'thumb' => 'http://7xidk0.com1.z0.glb.clouddn.com/clothe.png', | ||
62 | + 'type' => 'cloth', | ||
63 | + 'goods' => array( | ||
64 | + 'id' => 1, | ||
65 | + 'thumb' => 'http://img11.static.yhbimg.com/goodsimg/2015/03/02/07/01ebfb219e22770ffb0c2c3a2cbb2b4bef.jpg?imageMogr2/thumbnail/235x314/extent/235x314/background/d2hpdGU=/position/center/quality/90', | ||
66 | + 'name' => 'GAWS DIGI 丛林数码印花拼接卫衣', | ||
67 | + 'price' => 1268, | ||
68 | + 'salePrice' => 589, | ||
69 | + 'tags' => array( | ||
70 | + array( | ||
71 | + 'isNew' => true | ||
72 | + ) | ||
73 | + ), | ||
74 | + 'isFew' => true, | ||
75 | + 'url' => '' | ||
76 | + ) | ||
59 | ) | 77 | ) |
60 | ) | 78 | ) |
61 | ) | 79 | ) |
-
Please register or login to post a comment