zoukankan      html  css  js  c++  java
  • 基于vue的新组件开发

    前天完成了一个新组件的开发,做的过程也是各种遇到问题,彻底弄懂了slot,巩固了一些flex布局和jquery的知识,比起自己第一次做组件开发,现在已经是能够下手做,遇到问题解决问题,还算有进步。

    但是昨天写博客的时候,就在我快写完的时候,chrome崩溃了。。。我也崩溃了。。。写的东西全没有了!!!我还是继续重新码字吧。。。崩溃。。。

    做的这个组件给它起个什么名字比较合理我想了半天也没想出来。。。

    需求是这样的:

    • 由两部分组成,上面是导航条,下面每一块显示内容。如下图。
    • 导航条固定在顶部
    • 点击导航里的每一个标签,该标签高亮,该标签相应的div自动跳到内容部分第一栏的位置(这里最后一栏无法跳到第一栏,因为要撑开整个页面)
    • 滑动下面的内容,滑到哪个div对应的navs的标签高亮

    核心代码写在下面~供参考哦 

    html插入nav-list模板:

    <div id="main">
        <nav-list :navs="navs" :contents="contents">
            <div v-for="con in contents" :class="'con_' + con.en_name" :slot="'con_' + con.en_name">{{ con.text }}</div>   // :class要写在这里,而不要写在<slot>上
        </nav-list>
    </div>
    

    子组件模板:

    这里重点是如何使用slot,并且如何将navs的每一个标签和下面的div对应联系起来!

    <template>
        <div class="navList">
            <div class="nav">
                <div v-for="nav in navs" v-bind:class="{ active: cur == nav.en_name }" v-on:click="changeNav(nav.en_name)">{{ nav.name }}</div>
            </div>
            <div class="list">
                <slot v-for="nav in navs" :name="'con_' + nav.en_name"></slot>
            </div>
        </div>
    </template>
    

    子模板的操作代码:

    return{
        props: {
            navs: {
                type: Array
                , default: function(){
                    return {}
                }
            }
            , contents: {
                type: Array
                , default: function(){
                    return {}
                }
            }
    
        }
        , data: function(){
                return {
                    cur: this.navs[0].en_name   // 可以在data中这样定义初始值, 这里是将cur的初始值设定为navs的第一个en_name值
                }
            }
            , methods: {
                changeNav: function(index){   // 点击任意标签,调用该事件,改变其相应div的位置,即使整个页面向上滑动一定的距离。
                    this.cur = index
                    var pos = $(".con_" + index).position().top
                    var pos2 = $('.navList').position().top      // 这个是整个组件距离页面顶端的距离。
                    $(window).scrollTop(pos+pos2)
                }
                , scroll: function(){    // scroll()这个事件是div滑动停止时触发的,事件内部定义了:如何确定是哪个div在第一个显示位置,从而找到相应的navs的标签
                    var _this = this
                    $(window).on('scrollStop', function(event) {
                        for( attr in _this.navs ){
        
                            var curPos = $(".con_" + _this.navs[attr].en_name).offset().top
                            var curPos2 = curPos + $(".con_" + _this.navs[attr].en_name).height()
                            if( curPos <= $(window).scrollTop() + $(".nav").height() && $(window).scrollTop() + $(".nav").height() <= curPos2){
                                _this.cur = _this.navs[attr].en_name
                            }else if($(window).scrollTop() < $('.navList').offset().top){
                                _this.cur = _this.navs[0].en_name
                            }
                        }
        
                    })
                }
            }
            , mounted: function(){
                this.scroll()
        
                this.$nextTick(function(){
                    $('.nav').sticky({       // 这个也是直接写好的置于顶部的组件,我也是直接将它用在nav上
                        infinity: true
                    })
                })
            }
        }
    

      以上是所有vue组件代码,下面创建一个父实例的js文件:

    var sticky = require('core/m/sticky_vue')
    
    var vm = new Vue({
        el: "#main"
        ,components: {
            navList: require('navList.vue')
        }
        , data: function(){
            return {
                navs: [{ name: '美妆', en_name: 'makeup' }
                     , { name: '时尚', en_name: 'fashion' }
                     , { name: '鞋履', en_name: 'shoes' }
                     , { name: '大牌', en_name: 'board'}
                     , { name: '潮服', en_name: 'clothes'}
                ]
                , contents: [
                    { en_name: 'makeup', text: '美妆美妆'}
                    , { en_name: 'fashion', text: '时尚在哪里时尚在哪里'}
                    , { en_name: 'shoes', text: '鞋鞋鞋子'}
                    , { en_name: 'board', text: '大牌驾到'}
                    , { en_name: 'clothes', text: '服饰!!!'}
                ]
            }
        }
    
    })
    

      以上就是所有的代码了~在整个过程中遇到的问题都是基础知识不扎实,还有vue的使用不很流畅。大致有以下几点:

    1. jQuery的offset().top和position().top区分使用,offsetTop得到的是undefined,$(window).scrollTop()可以获取页面的整个垂直的滚动高度,$(window).scrollTop(值)则是设置滚动高度。在做的过程中,对于div要滚动多少、要获取的是div距页面的高还是句定位父级的高、页面要滚动多少、是否要包含nav的高度等等都是需要考虑的问题,所以这一部分自己还是理解的不到位,所以滚动的高度具体的调节都是通过实验的方式得到的。
    2. scroll()事件何时触发是我一开始不太明白的,比如changeNav(){}我定义在methods中,然后使用v-on:click="changeNav()"调用即可,那么scroll()这类事件应该放在哪里触发呢?在vue中我们将这些事件定义在methods中,然后在mounted或是created中调用即可!

      

  • 相关阅读:
    【JAVA】BitSet的源码研究
    【JAVA】大整数数据量排序
    三层架构的DCOM配置
    .NET+COM+组件注册方法
    开博感言
    about Cache
    代码HTML
    取远程用户IP地址
    ShowModalDialog页面传值
    about char变量
  • 原文地址:https://www.cnblogs.com/ningyn0712/p/6135194.html
Copyright © 2011-2022 走看看