Authored by 于良

rn 搜索cell review by 草莓

'use strict';
import React from 'react';
import ReactNative from 'react-native';
const {
View,
Image,
Text,
TouchableOpacity,
Dimensions,
StyleSheet,
} = ReactNative;
export default class GPTags extends React.Component {
constructor(props) {
super (props);
}
render() {
let {title, isLimit} = this.props;
let leftWidth = tagMaxWidth;
if (isLimit) {
leftWidth = tagMaxWidth - limitWidth - 2;
}
let textMaxWidth = leftWidth - iconWidth - 5 * 2;
return (
<View style={styles.container}>
<View style={[styles.leftContainer, {width: leftWidth}]}>
<Image
style={styles.icon}
source={require('../../images/tag/globalpurchase_fly_smallicon.png')}
/>
<Text numberOfLines={1} style={[styles.text, {maxWidth: textMaxWidth}]}>{title}</Text>
</View>
{isLimit ? <Image
style={styles.limit}
source={require('../../images/tag/gp_tip_xl_product.png')}
/> : null}
</View>
);
}
}
let {width, height} = Dimensions.get('window');
const DEVICE_WIDTH_RATIO = width / 320;
let tagMaxWidth = Math.ceil(137.5 * DEVICE_WIDTH_RATIO);
let tagHeight = Math.ceil(14 * DEVICE_WIDTH_RATIO);
let iconWidth = Math.ceil(10 * DEVICE_WIDTH_RATIO);
let limitWidth = Math.ceil(30 * DEVICE_WIDTH_RATIO);
let limitHeight = Math.ceil(14 * DEVICE_WIDTH_RATIO);
let styles = StyleSheet.create({
container: {
flexDirection: 'row',
alignItems: 'center',
width: width,
height: tagHeight,
},
leftContainer: {
flexDirection: 'row',
alignItems: 'center',
backgroundColor: '#462e3d',
height: tagHeight,
},
icon: {
marginLeft: 5,
width: iconWidth,
height: iconWidth,
resizeMode: 'contain',
},
text: {
marginLeft: 5,
marginRight: 5,
color: 'white',
fontSize: 10,
fontFamily: 'STHeitiSC-Light',
},
limit: {
marginLeft: 2,
width: limitWidth,
height: limitHeight,
resizeMode: 'contain',
},
});
... ...
... ... @@ -13,6 +13,7 @@ import ReactNative, {
import SlicedImage from '../../../common/components/SlicedImage';
import Tags from './Tags';
import GPTags from './GPTags';
export default class Search extends Component {
... ... @@ -20,33 +21,125 @@ export default class Search extends Component {
constructor(props) {
super(props);
this._renderTags = this._renderTags.bind(this);
this._renderImages = this._renderImages.bind(this);
this._renderPrice = this._renderPrice.bind(this);
}
render() {
let {rowID, data, style} = this.props;
let url = data.get('default_images').replace('{width}', rowWidth).replace('{height}', imageHeight);
_renderTags() {
let {data, sourceType} = this.props;
let isGlobalProduct = data.get('is_global') && data.get('is_global') == 'Y'; // 是否全球购商品
let tags = data.get('tags'); // 商品标签
// 数据源是全球购
if (sourceType == 1) {
if (isGlobalProduct) {
} else {
tags = ['is_in_stock', ...tags];
}
}
let countryName = isGlobalProduct && data.get('country_name'); // 全球购国家名称
if (isGlobalProduct) {
return <GPTags title={countryName} limit={showGPLimitTag}/>;
} else {
return <Tags items={tags}/>;
}
}
_renderImages() {
let {data, sourceType} = this.props;
let url = data.get('default_images').replace('{width}', rowWidth).replace('{height}', imageHeight); // 商品缩略图
url = SlicedImage.getSlicedUrl(data.get('default_images'), 290, 386, 2);
let isGlobalProduct = data.get('is_global') && data.get('is_global') == 'Y'; // 是否全球购商品
let showGPLimitTag = isGlobalProduct && data.get('is_limited') && data.get('is_limited') == 'Y'; // 全球购限量商品
let showGPSoldOut = isGlobalProduct && data.get('is_stock') && data.get('is_stock') == 'Y'; // 全球购售罄
let showAlmostSoldOut = !isGlobalProduct && data.get('is_soon_sold_out') && data.get('is_soon_sold_out') == 'Y'; // 非全球购的即将售罄
let showSoldOut = sourceType == 2 && data.get('storage_num') && data.get('storage_num') == 0; // 数据源是奥莱才显示
return (
<View style={[styles.container, style]}>
<Tags/>
<View style={styles.imageContainer}>
<Image style={styles.image} source={{uri: url}}>
<Image style={styles.almostSoldOutImage} source={require('../../images/tag/tip_jjsq.png')}/>
<Image style={styles.soldOutImage} source={require('../../images/tag/outlet_sellout_bg.png')}/>
</Image>
</View>
<View style={styles.nameContainer}>
<Text style={styles.name} numberOfLines={2}>{data.get('product_name')}</Text>
</View>
<View style={styles.imageContainer}>
<Image style={styles.image} source={{uri: url}}>
{showAlmostSoldOut ? <Image style={styles.almostSoldOutImage} source={require('../../images/tag/tip_jjsq.png')}/> : null}
{showSoldOut ? <Image style={styles.soldOutImage} source={require('../../images/tag/outlet_sellout_bg.png')}/> : null}
{showGPSoldOut ? <Image style={styles.gpSoldOutImage} source={require('../../images/tag/gp_tip_SQ.png')}/> : null}
</Image>
</View>
);
}
_renderPrice() {
let {data, sourceType} = this.props;
let isGlobalProduct = data.get('is_global') && data.get('is_global') == 'Y'; // 是否全球购商品
let salePrice = 0; // 售卖价
let originPrice = 0; // 原价
let salePriceStr = ''; // 拼接的售卖价
let originPriceStr = ''; // 拼接的原价
let showOriginPrice = true; // 是否显示原价
let salePriceColor = '#d0021b'; // 不显示原价时,售卖价颜色
if (isGlobalProduct) {
salePrice = parseFloat(data.get('final_price'));
originPrice = parseFloat(data.get('orign_price'));
salePriceStr = data.get('formart_final_price');
originPriceStr = data.get('formart_orign_price');
} else {
salePrice = parseFloat(data.get('sales_price'));
originPrice = parseFloat(data.get('market_price'));
salePriceStr = '¥' + salePrice.toFixed(2);
originPriceStr = '¥' + originPrice.toFixed(2);
}
if (!originPrice || (salePrice == originPrice)) {
showOriginPrice = false;
salePriceColor = '#444444';
}
if (showOriginPrice) {
return (
<View style={styles.priceContainer}>
<Text style={styles.nowPrice} numberOfLines={1}>{'¥' + data.get('sales_price')}</Text>
<Text style={[styles.nowPrice, {color: salePriceColor}]} numberOfLines={1}>{salePriceStr}</Text>
<View style={styles.oldPriceContainer}>
<Text style={styles.oldPrice} numberOfLines={1}>{'¥' + data.get('market_price')}</Text>
<Text style={styles.oldPrice} numberOfLines={1}>{originPriceStr}</Text>
<View style={styles.deleteLine}/>
</View>
</View>
);
} else {
return (
<View style={styles.priceContainer}>
<Text style={[styles.nowPrice, {color: salePriceColor}]} numberOfLines={1}>{salePriceStr}</Text>
</View>
);
}
}
render() {
let {data, sourceType, style} = this.props;
let name = data.get('product_name') ? data.get('product_name') : '';
return (
<View style={[styles.container, style]}>
{this._renderTags()}
{this._renderImages()}
<View style={styles.nameContainer}>
<Text style={styles.name} numberOfLines={2}>{name}</Text>
</View>
{this._renderPrice()}
</View>
);
}
... ... @@ -71,9 +164,10 @@ let almostSoldOutImageTop = imageHeight - almostSoldOutImageHeight;
let nameMarginTop = Math.ceil(7 * DEVICE_WIDTH_RATIO);
let nameHeight = Math.ceil(36 * DEVICE_WIDTH_RATIO);
let gpSoldOutImageHeight = Math.ceil(25 * DEVICE_WIDTH_RATIO);
let styles = StyleSheet.create({
container: {
// backgroundColor: 'gray',
width: rowWidth,
height: rowHeight,
marginTop: rowMarginTop,
... ... @@ -89,7 +183,6 @@ let styles = StyleSheet.create({
backgroundColor: '#f0f0f0',
},
image: {
// top: imageTop,
width: rowWidth,
height: imageHeight,
backgroundColor: '#f0f0f0',
... ... @@ -112,7 +205,6 @@ let styles = StyleSheet.create({
marginTop: nameMarginTop,
width: rowWidth,
height: nameHeight,
// backgroundColor: 'red',
},
name: {
fontFamily: 'STHeitiSC-Light',
... ... @@ -127,10 +219,8 @@ let styles = StyleSheet.create({
color: '#d0021b',
},
oldPriceContainer: {
// flex: 1,
flexDirection: 'row',
marginLeft: 5,
// backgroundColor: 'red',
},
oldPrice: {
fontSize: 12,
... ... @@ -139,14 +229,17 @@ let styles = StyleSheet.create({
},
deleteLine: {
position: 'absolute',
// flex: 1,
top: (16 / 2) - 0.5,
left: 0,
right: 0,
// marginLeft: 0,
// marginRight: 0,
// width: 50,
height: 1,
backgroundColor: '#b0b0b0',
},
gpSoldOutImage: {
position: 'absolute',
top: 5,
right: 5,
width: gpSoldOutImageHeight,
height: gpSoldOutImageHeight,
},
});
... ...
... ... @@ -84,8 +84,8 @@ export default class Tags extends React.Component {
render() {
let {style} = this.props;
let tags = ['is_discount', 'resale', ];
let {style, items} = this.props;
// let tags = ['is_discount', 'resale', ];
return (
<View style={[styles.container]}>
... ... @@ -93,7 +93,7 @@ export default class Tags extends React.Component {
style={[styles.container]}
contentContainerStyle={[styles.contentContainer]}
enableEmptySections={true}
dataSource={this.dataSource.cloneWithRows(tags)}
dataSource={this.dataSource.cloneWithRows(items.toArray())}
renderRow={this._renderRow}
scrollEnabled={false}
scrollsToTop={false}
... ...
... ... @@ -129,7 +129,7 @@ export function searchProductList(keyword, reload=false) {
let payload = parseProductList(json);
payload.endReached = payload.currentPage == payload.pageCount;
if (productList.currentPage > 1) {
if (payload.currentPage > 1) {
let oldList = productList.list.toJS();
let list = [...oldList, ...payload.list];
payload.list = list;
... ...
... ... @@ -35,6 +35,7 @@ let InitialState = Record({
pageSize: 6,//60,
total: 0,
endReached: false,
sourceType: 0, // 0 - 默认,1 - 全球购,2 - 奥莱
})),
});
... ...