点击效果 拖拽效果 拖拽边界 tab切换-选项卡

案例

点击效果

<style>
    *{
        margin: 0;
        padding:0;
    }

    body{
        height: 50000px;
    }

    div{
        width: 100px;
        height: 100px;
        background: pink;
        position: fixed;
        top:0px;
        left:0px;
    }
</style>
</head>
<body>
<div></div>

<script>
    // 点击鼠标,让div出现在,鼠标点击的位置上
    // 实现方式:
    // 点击时,获取鼠标点击位置的坐标,是针对视窗窗口的坐标
    // 将这个数值,作为标签定位的数据

    var oDiv = document.querySelector('div');

    // 如果没有,padding和border,只要获取宽度就可以
    // 有px单位,parseInt() 只获取数值,不要px
    // 实际项目中,还需要定义兼容性
    // var oDivHeight1 = parseInt(window.getComputedStyle(oDiv).height) ;
    
    // 如果要有是有,padding和border,需要使用 offsetHeight 来获取
    // 只有数值,没有px单位
    // 推荐使用
    var oDivHeight2 = oDiv.offsetHeight;

    // console.log(oDivHeight1 , oDivHeight2);

    var oDivWidth = oDiv.offsetWidth;

    window.onclick = function(e){
        // console.log(e);
        // 这个数值只有 数, 没有px单位
        // 作为定位的属性值,需要拼接px单位

        // 让标签的左上角和鼠标点击的位置重合
        // oDiv.style.left = e.clientX + 'px' ;
        // oDiv.style.top = e.clientY + 'px' ;

        // 让标签的左上角 和 鼠标点击位置 有间距
        // 在原始数值的基础上,再多加上一定的数值
        // 这个数值,是根据客户需求而定,现在随便加个数,意思意思
        // oDiv.style.left = e.clientX + 20 + 'px' ;
        // oDiv.style.top = e.clientY + 20 + 'px' ;

        // 让标签的中心 和 鼠标点击位置 重合
        // 在原始数值的基础上,再减去定位标签,宽高的一半
        oDiv.style.left = e.clientX - oDiv.offsetWidth/2  + 'px' ;
        oDiv.style.top = e.clientY - oDiv.offsetHeight/2 + 'px' ;
    }

</script>

拖拽效果

<style>
    *{
        margin: 0;
        padding:0;
    }

    body{
        height: 5000px;
    }

    div{
        width: 100px;
        height: 100px;
        background: pink;
        position: fixed;
        top:200px;
        left:200px;
    }
</style>
</head>
<body>
<div></div>
<script>
    // 拖拽的效果
    // 当鼠标按下时
    //    并且鼠标移动时

    var oDiv = document.querySelector('div');

    // 在div移动之前,先记录原始的定位数据
    var oldTop = window.getComputedStyle(oDiv).top;
    var oldLeft = window.getComputedStyle(oDiv).left;

    // 当鼠标按下时,鼠标移动,添加事件
    window.onmousedown = function(){
        window.onmousemove = function(e){
            // 将鼠标的坐标,作为div定位的数值,定位的是中心的位置
            oDiv.style.left = e.clientX - oDiv.offsetWidth/2  + 'px' ;
            oDiv.style.top = e.clientY - oDiv.offsetHeight/2 + 'px' ;
        }
    }

    // 当鼠标抬起时,鼠标移动,赋值null,就没有事件执行了
    window.onmouseup = function(){
        window.onmousemove = null;
        // 可以再给div定义,定位位置,可以返回原始位置
        // 也在函数之外,记录存储原始位置
        oDiv.style.left = oldLeft;
        oDiv.style.top = oldTop;
    }

    // 如果想要鼠标移动的快点 把 oDiv 改变成 window 或者 document


    // 先 鼠标移动,里面定义鼠标按下,抬起

    // 鼠标移动时,执行鼠标按下,鼠标按下,计算机只会触发一次  
    // 鼠标按下,即时是一直按,只会触发一次
    // 定义的程序,只会回执一次

    // window.onmousemove = function(){
    //     window.onmousedown = function(){
    //         console.log(123);
    //     }
    // }
    
    
    // 按下的时候,执行鼠标移动
    // 鼠标移动会一直触发,移动中定义的程序,会一直执行

    // window.onmousedown = function(){
    //     window.onmousemove = function(){
    //         console.log(456);
    //     }
    // }

</script>
</body>

拖拽边界

第一

<style>
        *{
            margin: 0;
            padding:0;
        }
        body{
            height: 5000px;
        }
        div{
            width: 100px;
            height: 100px;
            padding: 100px;
            background: pink;
            border:10px solid black;
            position: fixed;
            top:0px;
            left:0px;
        }
 </style>
	<body>
  	<div></div>
 <script>
    // 拖拽的效果 --- 边界值
    // 鼠标移动出页面,但是div要留在页面范围内
    // 给定位数值,添加极限范围数值,
    // 定位的最大值,最小值,都要有范围
    // 最小值 : 上  左  都是 0
    // 

    var oDiv = document.querySelector('div');

    var oldTop = window.getComputedStyle(oDiv).top;
    var oldLeft = window.getComputedStyle(oDiv).left;

    // 视窗窗口的宽度,高度
    var winWidth = document.documentElement.clientWidth;
    var winHeight = document.documentElement.clientHeight;

    // 当鼠标按下时,鼠标移动,添加事件
    window.onmousedown = function(){
        window.onmousemove = function(e){
            // 根据 鼠标坐标,根据项目需求,计算定位的数值
            var x = e.clientX - oDiv.offsetWidth/2;
            var y = e.clientY - oDiv.offsetHeight/2;

            // 极限值判断
            // 最小值都是 0 0 
            if(x < 0){
                x = 0;
            }

            if(y < 0){
                y = 0;
            }

            // 最大值 可视窗口的宽度/高度 - ( 标签x轴方向 / y轴方向 最终占位 )

            if(x > winWidth - oDiv.offsetWidth){
                x = winWidth - oDiv.offsetWidth;
            }

            if(y > winHeight - oDiv.offsetHeight){
                y = winHeight - oDiv.offsetHeight;
            }
            console.log(x,y);
            // 将数值作为标签定位的坐标
            oDiv.style.left = x  + 'px' ;
            oDiv.style.top =  y + 'px' ;
        }
    }

    window.onmouseup = function(){
        window.onmousemove = null;
    }


    // 总结思路

    // 1,一定是 先按下事件,后移动事件  --- 先砍头再移尸
    // 2,鼠标抬起,给移动定义事件为null
    //   也可以添加其他操作,例如,让标签回到原位
    //   回到原始位置,需要在程序的起始位置,先记录原始的定位坐标
    // 3,基本思路
    //   (1),在定义函数之外,获取浏览器窗口的宽度,高度
    //       不能带有滚动条
    //   (2),获取鼠标的坐标,根据项目需求,来计算表现定位的数值
    //       鼠标的坐标,要根据实际需求而定,目前使用的是相对可视窗口左上角的定位
    //       项目需求不同,+ / - 的数值也不同
    //   (3),设定极值
    //       最小值为 0   0
    //       最大值为 可视窗口宽度/高度 - 标签X轴/Y轴最终占位
    //   (4),将最终的数据,作为标签定位的坐标
    //       必须拼接px单位


</script>

第二

	</body>
 	   <style>
    * {
        padding: 0;
        margin: 0;
    }

    body {
        height: 5000px;
    }

    .box {
        width: 800px;
        height: 800px;
        border: 10px solid #000;
        margin: 40px auto;
        position: relative;
        background: skyblue;
    }

    .inner {
        width: 100px;
        height: 100px;
        background: pink;
        position: absolute;
        top: 0;
        left: 0;
    }
</style>
</head>

<body>
<div class="box">
    <div class="inner"></div>
</div>

<script>

    // 1,获取标签对象
    var oBox = document.querySelector('.box');
    var oInner = document.querySelector('.inner');

    // 2,获取相应的数据

    // 获取父级标签的---占位---不包括边框线
    var oBoxWidth = oBox.clientWidth;
    var oBoxHeight = oBox.clientHeight;


    // 获取子级标签的---占位---包括边框线
    var oInnerWidth = oInner.offsetWidth;
    var oInnerHeight = oInner.offsetHeight;

    // 给父级标签添加事件
    oInner.onmousedown = function () {

        document.onmousemove = function (e) {

            // 获取计算,设定子级标签定位的数值

            // page坐标 - 外边距 - 边框线 - 子级宽度的一半
            var x = e.pageX - oBox.offsetLeft - oBox.clientLeft - oInnerWidth / 2;
            var y = e.pageY - oBox.offsetTop - oBox.clientTop - oInnerHeight / 2;

            // 设定极限值

            // 最小值是0
            if (x < 0) {
                x = 0;
            }

            if (y < 0) {
                y = 0;
            }

            // 最大值 
            // 父级标签占位(没有border) - 移动标签占位(计算border)
            if (x > oBoxWidth - oInnerWidth) {
                x = oBoxWidth - oInnerWidth;
            }

            if (y > oBoxHeight - oInnerHeight) {
                y = oBoxHeight - oInnerHeight
            }

            // 将设定好的数值,作为子级标签的定位
            oInner.style.left = x + 'px';
            oInner.style.top = y + 'px';
        }
    }


    window.onmouseup = function () {
        document.onmousemove = null;
    }

    // 思路步骤和问题
    // 1, 事件,到底是绑定给 父级,子级,还是document,还是window
    //    事件,取消,到底是通过谁取消
    //    没有固定的写法,看你需要的效果
    //    还是document和window效果相同,没有区别

    //    鼠标按下
    //    oInner.onmousedown   鼠标在粉色div上,按下鼠标,并且移动鼠标,才会有效果
    //    oBox.onmousedown     鼠标在蓝色div上,按下鼠标,并且移动鼠标,才会有效果
    //    window.onmousedown   鼠标在全屏上,按下鼠标,并且移动鼠标,都会有效果

    //    鼠标移动
    //    最好写成 document.onmousemove  /  window.onmousemove
    //    鼠标可以快速移动,不怕移出粉色div

    //    鼠标抬起
    //    oInner.onmouseup     鼠标在粉色div上抬起,才会执行,标签不跟随移动
    //    oBox.onmouseup       鼠标在蓝色div上抬起,才会执行,标签不跟随移动
    //    window.onmouseup     鼠标在整个页面上抬起,都会执行,标签不跟随移动

    // 2, 闪烁问题
    //    原因: 相对于标签内容的左上角的定位
    //          会因为鼠标经过不同的标签对象,获取不同的数据
    //          而且JavaScript执行时,有时还会有bug产生
    //          offsetX  offsetY  我们是不推荐使用的
    //    解决: 使用 pageX 和  pageY 
    //    定位: page距离 - 父级标签外边距 - 父级border - 移动标签占位/2(标签中心点和鼠标重合)
    //   极值1: 左   上   都是 0
    //   极值2: 右   下   父级标签占位(不算border) - 移动标签占位(计算border)
</script>

tab切换-选项卡

   <style>
    *{
        margin: 0;
        padding:0;
    }

    ul,ol,li{
        list-style: none;
    }

    .cont{
        width: 800px;
        height: 600px;
        border: 5px solid #333;
        margin: 0 auto;
        display: flex;
        flex-direction: column;
    }

    .cont ul{
        width: 100%;
        height: 60px;
        display: flex;
    }

    .cont ul li{
        flex:1;
        font-size: 35px;
        color: #fff;
        border-left: 2px solid blue;
        border-right: 2px solid blue;
        background: hotpink;
        display: flex;
        justify-content: center;
        align-items: center;

    }

    .cont ol{
        flex:1;
        position: relative;
    }

    .cont ol li{
        width: 100%;
        height: 100%;
        font-size: 150px;
        display: flex;
        justify-content: center;
        align-items: center;
        position: absolute;
        top:0;
        left:0;
        background: burlywood;
        display: none;
    }

    /* 按钮标签 哪个标签有这个属性,哪个就显示特殊背景颜色 */
    .cont ul li.active{
        background: skyblue;
        color: black;
    }

    /* 内容标签 哪个标签有这个属性,哪个就显示 */
    .cont ol li.active{
        display: flex;
    }

</style>
</head>
<body>
<div class="cont">
    <ul>
        <li class="active">按钮1</li>
        <li>按钮2</li>
        <li>按钮3</li>
    </ul>
    <ol>
        <li class="active">内容1</li>
        <li >内容2</li>
        <li>内容3</li>
    </ol>
</div>

<script>
    // tab切换 / 选项卡 效果

    // 实现思路:
    // 1, ul中的li标签个数  和 ol中li标签个数是相同的
    //    按钮和内容是一一对应的

    // 2, 点击按钮标签,也就是ul中的li标签
    //    给当前这个li标签,添加class样式,给其他的li标签,去除class样式
    //    实现思路: 先给所有的li标签,去除class样式
    //             再给当前的li标签,添加class样式

    // 3, 点击按钮标签,也就是ul中的li标签
    //    给 ol 中所有的 li标签,去除class样式
    //    给 与 当前 ul>li 索引相同的 ol>li标签,添加样式


    var oUllis = document.querySelectorAll('ul li');
    var oOllis = document.querySelectorAll('ol li');

    // 循环 ul中的所有li,添加点击事件
    oUllis.forEach(function(item , key){
        // ul中的li标签 , item就是ul中的li标签
        item.onclick = function(){
            // 1,清除所有的ul,ol,中li的class样式属性
            // 循环遍历所有的ul和ol中的标签
            oUllis.forEach(function(v , k){
                // v是ul中的li标签
                v.className = '';
                // ul>li和ol>li索引是相同的
                // 通过ul中li的索引也可以获取ol中的li标签
                // oOllis[k] 就是 ol中的li标签
                oOllis[k].className = '';
            })
            // 循环结束,所有的ul,ol中,li都没有active


            // 给当前点击的item标签,也就是ul,li标签,添加样式
            item.className = 'active';

            // 给ol中,对应的这个标签的索引的li标签,添加样式
            oOllis[key].className = 'active';
        }
    })

    // 不想用forEach,也可以试试事件委托


    // 总结
    // 核心思路:
    //   利用 ul 和 ol 中 li标签个数相同的 特点,优化程序,简化代码
    // 1,获取标签对象
    // 2,给所有的ul中的li标签,添加点击事件
    // 3,点击事件执行的内容
    //   (1),给所有的ul和ol中的li标签,清除样式
    //   (2),给当前点击的ul中的li标签,添加样式
    //   (3),给索引相同的ol中的li标签,添加样式

    // 可以用自己的方式实现,比如多写几个循环,分别操作ul和ol中的标签
    // 不过我的方法比较简单

    // 也可以尝试事件委托的方式,给div标签,添加点击事件
    // 判断点击的li标签,定义程序
    // 不过这样的话,要给ul中li标签,添加不少的设定,以区别ul>li和ol>li

</script>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值