Weex 多选,本地动态筛选数据

2019-07-10  本文已影响0人  fordG
image.png
image.png

代码


<template>
    <div>
        <wxc-popup :show="show" @wxcPopupOverlayClicked="popupOverlayBottomClick" 
                    :height="height+touchBarHeight"
                    :overlayCfg="{opacity: 0.3}"
                    popup-color = 'rgba(3,0,0,0)'
                    ref="wxcPopup">
            <div style="align-items: center;">
                <div class="content" :style="{height: 800+touchBarHeight}">
                    <div class="buttonDiv">
                        <text class="button" @click="cancle">取消</text>
                        <text style="font-size: 32px; color: #333333; flex: 1; text-align: center;">{{resultStr()}}</text>
                        <text class="button" @click="cancle">确认</text>
                    </div>
                    <scroller class="filterItem" :style="{height: scrollerHeight}">
                        <div class="filterItem-content">
                            <div class="filterItem-content-item" v-for="(item, index) in Array.from(filterItems)" :key="index" :ref="getRef(index)" @click="deleteItem(item)">
                                <text class="filterItem-content-item-text">{{item.value}}</text>
                            </div>
                        </div>
                    </scroller>
                    <div class="filter-content">
                        <div class="filter-content-top">
                            <div class="filter-content-top-item" @click="directClick">
                                <image class="filter-content-top-item-image" :src="directImage"></image>
                                <text class="filter-content-top-item-text">{{direct.value}}</text>
                            </div>
                            <div class="filter-content-top-item" style="justify-content: flex-end;" @click="shareClick">
                                <image class="filter-content-top-item-image" :src="shareImage"></image>
                                <text class="filter-content-top-item-text">{{share.value}}</text>
                            </div>
                        </div>
                        <div class="scroll-content" >
                            <div class="scroll-content-left">
                                <text v-for="(title, index) in leftItems" :key="title" class="scroll-content-left-text" :style="{color: leftTextColor(index), backgroundColor: leftBackColor(index), borderRightColor: leftBorderRightColor(index), borderBottomColor: leftBoardBottomColor(index)}" @click="leftTextClick(index)">{{title}}</text>
                            </div>
                            <div class="scroll-content-right">
                                <scroller class="content-scroller" v-for="(item, index) in filters" :style="{left: index==leftSelect? 0: 550}" :key="index">
                                    <div v-for="(obj, i) in item" :key="i" class="content-scroller-item" @click="itemFilterClick(item,i)">
                                        <text class="content-scroller-item-text">{{obj.value}}</text>
                                        <image class="content-scroller-item-image" :src="imageStyle(obj.select || false)"></image>
                                    </div>
                                </scroller>
                            </div>
                        </div>
                        <div :style="{height: touchBarHeight}" style="background-color: whi;"></div>
                    </div>
                </div>
            </div>
            <div v-if="showLoading" class="loading">
                <div class="loading-div">
                    <image class="loading-image" src="https://img.alicdn.com/tfs/TB1Ep_9NVXXXXb8XVXXXXXXXXXX-74-74.gif"></image>
                </div>
            </div>
        </wxc-popup>
    </div>
</template>

<script>
    
    import WxcPopup from 'weex-ui/packages/wxc-popup'
    import DateHelper from '../shippingspace/config'
//这个是做一些自己数据处理的类
    import Air from '../../../../components/air.js'
    export default {
        
        props: {
            //组件显示判断
            show: {type: Boolean, default: false},
            //example   time [{value: 00:00-06:00, type: 'time', select: false}]
            //删选条件数组
            filters: {
                default: [[{value: "00:00-06:00", type: 'time', select: false},{value: "06:00-12:00", type: 'time', select: false},{value: "12:00-18:00", type: 'time', select: false},{value: "18:00-00:00", type: 'time', select: false}],[],[],[]]
            },
            //你的原始数据
            flights: {
                default: []
            }
        },

        components:{
            WxcPopup
        },

        computed: {
            //适配iphoneX
            touchBarHeight(){
                return WXEnvironment.touchBarHeight ? WXEnvironment.touchBarHeight : 0
            },
            directImage(){
                return this.imageStyle(this.direct.select)
            },
            shareImage(){
                return this.imageStyle(this.share.select)
            },
            //prpos 属性是只读的
            tmpFlights(){
                return this.flights
            },
            
        },

        data:()=>({
            //左边选择的类目
            leftItems: ['起飞时间', '机场', '机型', '航空公司'],
            //默认选中, 可以自行扩展
            leftSelect: 0,
            //是否直飞, 数据和筛选数组里面的数据格式一致,方便筛选删除增加,改变试图
            direct: {value: '仅看直飞', type: 'zhifei', select: false},
            share: {value: '隐藏共享航班', type: 'gongxiang', select: false},
            //筛选出来的结果
            result: 0,
            //控件整体高度
            height: 600,
            //此筛选是本地的, 可能数据量比较大, 所以做了loading处理
            showLoading: false,
            //记录筛选条件的scroll的高度
            scrollerHeight: 0,
            //筛选的记录集合
            filterItems: null,
        }),

        created(){
            if(this.filters.length != this.leftItems.length) {
                return
            }
            this.filterItems = new Set()
        },

        methods: {
            //当筛选数据的试图高度大于400的时候,滚动到底部
            getRef(index){
                return 'scroller'+index
            },
            //获取结果字符串
            resultStr(){
                var str = "共"+this.result+"结果"
                var flag = false
                if(this.share.select || this.direct.select){
                    return str
                }
                for (var i = 0; i < this.filters.length; i++) {
                    var item = this.filters[i]
                    for (var j = 0; j < item.length; j++) {
                        var obj = item[j]
                        if(obj.select){
                            flag = true
                            break
                        }
                    }
                }
                return !flag? '': str
            },
            
            //ui 样式
            leftBorderRightColor(index){
                return this.leftSelect==index ? '#ffffff': '#DDDDDD'
            },
            leftBackColor(index){
                return this.leftSelect==index ? '#ffffff': '#f7f7f7'
            },
            leftTextColor(index){
                return this.leftSelect==index ? '#00aafb': '#333333'
            },
            leftBoardBottomColor(index){
                return (this.leftItems.length-1)==index? '#ffffff': '#DDDDDD'
            },
            
            imageStyle(flag){
                return flag ? 'bmlocal://assets/makeflight/filter_checked@2x.png' : 'bmlocal://assets/makeflight/filter_unchecked@2x.png'
            },
            //dismiss
            popupOverlayBottomClick(){
                this.$emit('wxcPopupOverlayClicked')
            },
            //dismiss
            cancle(){
                this.$refs.wxcPopup.hide()
                this.$emit('wxcPopupOverlayClicked')
            },
            
            //直飞点击事件
            directClick(){
                this.direct.select = !this.direct.select
                this.changeHeight(this.direct)
                this.filterEmit()
            },
            //是否隐藏共享航班点击事件
            shareClick(){
                this.share.select = !this.share.select
                this.changeHeight(this.share)
                this.filterEmit()
            },
            //类目点击事件
            leftTextClick(index){
                if(this.leftSelect != index) {
                    this.leftSelect = index
                }
            },
            //筛选条件点击事件
            itemFilterClick(item, i){
                var obj = item[i]
                obj.select = !obj.select
                this.changeHeight(obj)
                this.$forceUpdate()
                this.filterEmit()
            },
            //高边高度
            changeHeight(obj){
                //集合里面添加对象, 只会记录改对象的内存地址, 所以添加的对象内部变化了,对集合来说还是一个对象
                //集合里面加入筛选条件
                //筛选的最大高度设置400
                if(obj.select){
                    this.filterItems.add(obj)
                    //改变筛选条件view高度
                    if(this.scrollerHeight < 400){
                        if(this.filterItems.size > 3){
                            if(this.filterItems.size % 3 == 0){
                                this.scrollerHeight = 100 * parseInt(this.filterItems.size/3)
                            }else{
                                this.scrollerHeight = 100 * parseInt(this.filterItems.size/3 + 1)
                            }
                        }else{
                            this.scrollerHeight = 100
                        }
                    }
                    if(this.filterItems.size > 12 ){
                        let ref = this.getRef(this.filterItems.size-1)
                        const dom = weex.requireModule('dom')
                        let self = this
                        setTimeout(e=>{
                            dom.scrollToElement(self.$refs[ref][0])
                        }, 100)
                    }
                }else{
                    //集合删除反选的筛选条件
                    this.filterItems.delete(obj)
                    if(this.filterItems.size < 12 ){
                        if(this.filterItems.size > 3){
                            if(this.filterItems.size % 3 == 0){
                                this.scrollerHeight = 100 * parseInt(this.filterItems.size/3)
                            }else{
                                this.scrollerHeight = 100 * parseInt(this.filterItems.size/3 + 1)
                            }
                        }else{
                            if(this.filterItems.size == 0){
                                console.log('this.filterItems.size', this.filterItems.size)
                                this.scrollerHeight = 0
                            }else{
                                this.scrollerHeight = 100
                            }
                        }
                    }
                }
                this.height = 600 + this.scrollerHeight
            },
            //开始筛选
            filterEmit(){
                console.log('tmpFlights.length', this.tmpFlights.length);
                this.showLoading = true;
                let self = this
                setTimeout(e=>{
                    self.beginFliter()
                }, 10)
            },
            
            beginFliter(){
                let direct = this.direct.select;
                let share = this.share.select;
                let filters = this.filters;
                var tmpArr = [];

                //起飞时间,默认写死了, 不想写死,可以参照下面的筛选条件写法, 用数组代替判断
                //此处筛选可以更具自己的具体数据类型来判断, 我使用的自己数据的字段
                let timeArr = this.filters[0];
                let currentDateStr = DateHelper.currentDateStr(new Date());
                const timeSet = new Set();
                var timeFlag0 = false; //默认没有选择
                var timeFlag1 = false; //默认没有选择
                var timeFlag2 = false; //默认没有选择
                var timeFlag3 = false; //默认没有选择
                this.tmpFlights.map((e, index) => {
                    //00-06
                    let current = e.qfsj;
                    if (timeArr[0].select) {
                        //加入选中的时间段
                        timeFlag0 = true;
                        let tags = timeArr[0].value.split('-');
                        let begin = currentDateStr + ' ' + tags[0];
                        let end = currentDateStr + ' ' + tags[1];
                        console.log(current, begin, end, DateHelper.inTime(current, begin, end));
                        if (DateHelper.inTime(current, begin, end)) {
                            timeSet.add(e);
                        }
                    }else{
                        timeFlag0 = false
                    }
                    if (timeArr[1].select) {
                        //加入选中的时间段
                        timeFlag1 = true;
                        let tags = timeArr[1].value.split('-');
                        let begin = currentDateStr + ' ' + tags[0];
                        let end = currentDateStr + ' ' + tags[1];
                        console.log(current, begin, end, DateHelper.inTime(current, begin, end));
                        if (DateHelper.inTime(current, begin, end)) {
                            timeSet.add(e);
                        }
                    } else{
                        timeFlag1 = false
                    } 
                    if (timeArr[2].select) {
                        //加入选中的时间段
                        timeFlag2 = true;
                        let tags = timeArr[2].value.split('-');
                        let begin = currentDateStr + ' ' + tags[0];
                        let end = currentDateStr + ' ' + tags[1];
                        console.log(current, begin, end, DateHelper.inTime(current, begin, end));
                        if (DateHelper.inTime(current, begin, end)) {
                            timeSet.add(e);
                        }
                    } else{
                        timeFlag2 = false
                    } 
                    if (timeArr[3].select) {
                        //加入选中的时间段
                        timeFlag3 = true;
                        let tags = timeArr[3].value.split('-');
                        let begin = currentDateStr + ' ' + tags[0];
                        let end = DateHelper.afterDayStr(currentDateStr, 1) + ' 00:00'
                        console.log(current, begin, end, DateHelper.inTime(current, begin, end));
                        if (DateHelper.inTime(current, begin, end)) {
                            timeSet.add(e);
                        }
                    }else{
                        timeFlag3 = false
                    }
                });
                console.log('timeSet.length', timeSet.size);
                if (timeFlag0 || timeFlag1 || timeFlag2 || timeFlag3) {
                    //有选中
                    tmpArr = Array.from(timeSet);
                } else {
                    //没有时间段选中
                    tmpArr = this.tmpFlights;
                }

                if (direct) {
                    //筛选直飞
                    tmpArr = tmpArr.filter(value => {
                        return value.stopNum == '0';
                    });
                }
                if (share) {
                    tmpArr = tmpArr.filter(value => {
                        return value.codeShare != 'Y';
                    });
                }
            
                //机场筛选, 获取选择的机场
                let airports = this.filters[1].filter(e=>{
                    return e.select
                })
                var airportSet = new Set()
                tmpArr.map(e=>{
                    for (var i = 0; i < airports.length; i++) {
                        var obj = airports[i]
                        if(Air.airName(e.qfjc)==obj.value || Air.airName(e.ddjc)==obj.value){
                            airportSet.add(e)
                        }
                    }
                })
                if(airports.length != 0){
                    //有选择机场
                    tmpArr = Array.from(airportSet)
                }
            
                //机型筛选, 获取选择的机型
                let airtypes = this.filters[2].filter(e=>{
                    return e.select
                })
                var airtypeSet = new Set()
                tmpArr.map(e=>{
                    for (var i = 0; i < airtypes.length; i++) {
                        var obj = airtypes[i]
                        if(e.jixing == obj.value){
                            airtypeSet.add(e)
                        }
                    }
                })
                if(airtypes.length != 0){
                    //有选择
                    tmpArr = Array.from(airtypeSet)
                }
            
                //航空公司筛选, 获取选择的机场
                let airtcompanys = this.filters[3].filter(e=>{
                    return e.select
                })
                var aircompanySet = new Set()
                tmpArr.map(e=>{
                    for (var i = 0; i < airtcompanys.length; i++) {
                        var obj = airtcompanys[i]
                        if(e.hkgs==obj.value){
                            aircompanySet.add(e)
                        }
                    }
                })
                if(airtcompanys.length != 0){
                    //有选择
                    tmpArr = Array.from(aircompanySet)
                }
            

                console.log('tmpArr.length', tmpArr.length);
                this.result = tmpArr.length;
                this.showLoading = false;
                this.$emit('filterItemClick', {flights: tmpArr})
            },
            deleteItem(item){
                var obj = {}
                this.filterItems.forEach(e=>{
                    if(e.value == item.value){
                        obj = e
                    }
                })
                console.log(item, obj, item == obj)
                this.filterItems.delete(obj)
                console.log(JSON.stringify(this.filterItems))
                if(item.type == 'zhifei'){
                    this.direct.select = false
                }
                if(item.type == 'gongxiang'){
                    this.share.select = false
                }
            
                if(item.type == 'time' || item.type == 'aircompany'|| item.type == 'airtype'|| item.type == 'airport'){
                    var index = 0
                    if(item.type == 'time'){
                        index = 0
                    }else if(item.type == 'airport'){
                        index = 1
                    }else if(item.type == 'airtype'){
                        index = 2
                    }else{
                        index = 3
                    }
                    this.filters[index].map(e=>{
                        if(e.value == item.value){
                            e.select = false
                        }
                    })
                }
                this.changeHeight(item)
                //强制刷新页面, 有时候存在数据改变了,页面没有改变可以使用此方法来强制刷新页面UI
                this.$forceUpdate()
            }
        },
    }
</script>

<style scoped>
.content{
    background-color: white;
    border-top-right-radius: 30px;
    border-top-left-radius: 30px;
    width: 750;
}
.buttonDiv{
    height: 100;
    flex-direction: row;
    align-items: center;
    justify-content: space-between;
    padding: 20px;
    border-bottom-width: 1px;
    border-bottom-color: #DDDDDD;
}
.button{
    line-height: 100;
    width: 100px;
    text-align: center;
    font-size: 28px;
    color: #333333;
}

.filter-content{
    height: 700px;
    width: 750px;
}
.filter-content-top{
    height: 100px;
    border-bottom-width: 1px;
    border-bottom-color: #DDDDDD;
    flex-direction: row;
    padding-right: 40px;
    padding-left: 40px;
}

.filter-content-top-item{
    flex-direction: row;
    align-items: center;
    /* justify-content: center; */
    flex: 1;
}
.filter-content-top-item-image{
    width: 40px;
    height: 40px;
    margin-right: 20px;
}
.filter-content-top-item-text{
    font-size: 24px;
    color: #333333
}
.scroll-content{
    flex-direction: row;
    height: 400px;
}
.scroll-content-left{
    width: 200px;
}
.scroll-content-left-text{
    line-height: 99px;
    text-align: center;
    font-size: 28px;
    border-bottom-color: #DDDDDD;
    border-bottom-width: 1px;
    border-right-width: 1px;
    border-right-color: #DDDDDD;
}
.scroll-content-right{
    width: 550px;
}
.content-scroller{
    position: absolute;
    width: 550px;
    top: 0px;
    bottom: 0px;
    background-color: #FFFFFF;
}
.content-scroller-item{
    height: 100px;
    width: 550px;
    flex-direction: row;
    justify-content: space-between;
    align-items: center;
    border-bottom-color: #DDDDDD;
    border-bottom-width: 1px;
    padding-left: 30px;
    padding-right: 30px;
}
.content-scroller-item-text{
    font-size: 28px;
    color: #333333
}
.content-scroller-item-image{
    width: 40px;
    height: 40px
}
.loading{
    position: absolute;
    top: 0;
    bottom: 0;
    left: 0;
    right: 0;
    justify-content: center;
    align-items: center;
    background-color: rgba(0, 0, 0, 0.1);
}
.loading-div{
    width: 80;
    height: 80;
    justify-content: center;
    align-items: center;
    background-color: rgba(0, 0, 0, 0.8);
}
.loading-image{
    width: 40;
    height: 40;
}
.filterItem{
    background-color: #F9F9F9;
}
.filterItem-content{
    flex-wrap: wrap;
    flex-direction: row;
}
.filterItem-content-item{
    width: 200;
    margin-left: 38px;
    height: 60px;
    margin-top: 20px;
    margin-bottom: 20px;
    justify-content: center;
    align-items: center;
    border-color: #DDDDDD;
    border-width: 1px;
}
.filterItem-content-item-text{
    width: 200px;
    font-size: 22px;
    color: #666666;
    text-align: center;
}
</style>

DateHelper

const DateHelper = {

    /*
        date: Date
        return '2019-02-28'
    */ 
    currentDateStr(date){
        if (!(date instanceof Date)) {
            console.log('error: 时间类型必须为Date类型')
            return 
        }
        var year = date.getFullYear()
        var month = date.getMonth() + 1
        var monthStr = ''
        if (month < 10) {
            monthStr = '0'+ month
        }else{
            monthStr = month.toString()
        }
        var day = date.getDate()
        var dayStr = ''
        if (day< 10) {
            dayStr = '0' + day
        }else{
            dayStr = day.toString()
        }
        return year + '-' + monthStr + '-' + dayStr
    },

    /*  
        今天开始之后的多少天
        dayCount: int
        return '2019-02-28' 
    */
    manyDayStr(dayCount){
        var date = new Date()
        var amount = date.getTime() + 1000*60*60*24*dayCount
        var feature = new Date(amount)
        return DateHelper.currentDateStr(feature)
    },

    /*
        nowDay: '2019-02-28'
        dayCount: int
        return '2019-02-28'
    */ 
    beforeDayStr(nowDay, dayCount=1){
        var now = new Date(nowDay)
        var amount = now.getTime() - 1000*60*60*24*dayCount
        var feature = new Date(amount)
        return DateHelper.currentDateStr(feature)
    },

    /*
        nowDay: '2019-02-28'
        dayCount: int
        return '2019-02-28'
    */ 
    afterDayStr(nowDay, dayCount=1){
        var now = new Date(nowDay)
        var amount = now.getTime() + 1000*60*60*24*dayCount
        var feature = new Date(amount)
        return DateHelper.currentDateStr(feature)
    },
    
    /*
        timeStr: '2019-02-28'这种类型的字符串, 可以带时间
        reutrn Date()
    */
    transformTime(timeStr){
        var date = new Date(timeStr.replace(/-/g, "/"))
        return date
    },

    /*
        timeStr: '2019-02-28'这种类型的字符串, 可以带时间
        reutrn '09:30'
    */
    airTime(timeStr){
        var date = new Date(timeStr.replace(/-/g, "/"))
        var hour = date.getHours()
        var hourStr = ''
        if (hour < 10) {
            hourStr = '0' + hour
        }else{
            hourStr = hour.toString()
        }
        var minute = date.getMinutes()
        var minuteStr = ''
        if (minute < 10) {
            minuteStr = '0' + minute
        }else{
            minuteStr = minute.toString()
        }

        return hourStr + ':' + minuteStr
    },

    /*
        beginTime: '2019-02-28'
        endTime: 2019-01-28'
        return '23时42分'
    */
    howLongTime(beginTime, endTime){

        var dateBegin = new Date(beginTime.replace(/-/g, "/"))
        var dateEnd = new Date(endTime.replace(/-/g, "/"))

        var amount = dateEnd.getTime() - dateBegin.getTime()

        //小时
        var hour = parseInt(amount/1000/60/60)
        var minute = amount/1000/60%60
        return hour + '时' + minute + '分'
    },

    /*
        timeStr: 2019-02-28'
        return '02-28'
    */
    dayTime(timeStr){

        var date = new Date(timeStr.replace(/-/g, "/"))
        var month = date.getMonth() + 1
        var monthStr = ''
        if (month < 10) {
            monthStr = '0'+ month
        }else{
            monthStr = month.toString()
        }
        var day = date.getDate()
        var dayStr = ''
        if (day< 10) {
            dayStr = '0' + day
        }else{
            dayStr = day.toString()
        }

        return monthStr + '-'+dayStr
    },

    /*
        timeStr: '2019-02-28'
        return 周一
    */
    week(timeStr){
        var date = new Date(timeStr.replace(/-/g, "/"))
        var weeks = [ '周日', '周一', '周二', '周三', '周四', '周五', '周六']
        return weeks[date.getDay()]
    },

    /*
        first '2019-02-28'
        second '2019-02-28'
        return true first在second之后   false first在second之前
    */

    compareTime(first, second){

        var firstDate = DateHelper.transformTime(first)
        var secondDate = DateHelper.transformTime(second)
        if ((firstDate.getTime() - secondDate.getTime()) > 0) {
            return true
        }else{
            false
        }
    },
    /*
        current :  '2019-02-28: 09:09'
        begin :  '2019-02-28: 09:09'
        end :  '2019-02-28: 09:09'
    */
    inTime(current, begin, end){
        var current = DateHelper.transformTime(current)
        var begin = DateHelper.transformTime(begin)
        var end = DateHelper.transformTime(end)
        console.log(current.getTime(), begin.getTime(), end.getTime())
        if (((current.getTime() - begin.getTime()) >= 0) && ((current.getTime() - end.getTime()) <= 0)) {
            return true
        }else{
            return false
        }
    }
};

export default DateHelper;
上一篇 下一篇

猜你喜欢

热点阅读