旋转相册与导航跟随双向绑定

头部js,转换rem

function IsPC() {
    var userAgentInfo = navigator.userAgent;
    var reg = new RegExp("(Android|iPhone|SymbianOS|Windows Phone|iPad|iPod)", "ig");
    var isPC = !reg.test(userAgentInfo);
    return isPC
}
var initFontSize = function () {
    var n = document.getElementsByTagName("html")[0],
        e = document.documentElement.clientWidth;
    if (IsPC()) {
        if (e > 750) {
            n.style.fontSize = "50px"
        } else {
            n.style.fontSize = e / 750 * 50 + "px"
        }
    } else {
        n.style.fontSize = e / 750 * 50 + "px";
    }
};
initFontSize();
window.onresize = function () {
    initFontSize()
};

 

 

css部分

* {
                padding: 0;
                margin: 0;
            }
            
            body {
                background-color: #fff;
                perspective: 8rem;
                /*filter: grayscale(100%);*/
                width: 15rem;
                overflow: hidden;
            }
            
            .wrapper {
                width: 1.2rem;
                height: 1.2rem;
                /* 当前元素水平居中 */
                margin: 3.6rem auto;
                position: relative;
                /* 当前元素为3d立体的    */
                transform-style: preserve-3d;
                transform: rotateX(-10deg) rotateY(360deg);
                user-select: none;
            }
            
            .wrapper img {
                position: absolute;
                /* width,height的百分比默认会相对于父级 但是会受到自身position的影响而改变 */
                width: 100%;
                height: 100%;
                /* z-index: 100; */
                background-color: transparent;
                /* 监听到transform属性变化的时候会有动画 */
                transition: -ms-text-align-last: left;
                /*transition:all 1s;
            text-align-last: left; 1s;*/
                transform: scale(0);
                /* transform: rotateY(0deg) translateZ(0px); */
                /*-webkit-box-reflect: below 0.2rem -webkit-linear-gradient(top, rgba(0, 0, 0, 0) 50%,rgba(0, 0, 0, 0.5) 100% );*/
            }
            
            .container {
                width: 15rem;
                border-radius: 1rem;
                height: 1rem;
                border: 1px solid #888;
                margin: 0 auto;
                overflow: hidden;
                position: relative;
                color: #000;
            }
            
            .container ul {
                height: 100%;
                margin: 0;
                padding: 0;
                list-style: none
            }
            
            .container li {
                float: left;
                width: 1rem;
                height: 100%;
                position: relative;
                display: flex;
            }
            
            .container li i {
                font-style: normal;
                display: inline-block;
                transform: translate(-50%, 5px);
                font-size: 14px
            }
            
            .container li::after {
                content: "";
                position: absolute;
                border-left: 1px solid #aaa;
                height: 13px;
                left: 0;
                bottom: 5px
            }
            
            .container .center {
                width: 5px;
                height: 100%;
                position: absolute;
                background: #f40;
                left: 50%;
                top: 0;
                transform: translateX(-50%)
            }
            
            #chooseResult {
                text-align: center;
                height: 1rem;
                line-height: 1rem;
                color: #000;
                font-size: 24px;
            }
            
            .main {
                width: 7.5rem;
                height: 6rem;
                margin: 0 auto;
                position: relative;
                overflow: hidden;
            }
            
            .main::before,
            .main::after {
                background: linear-gradient(to right, #fff 0, rgba(255, 255, 255, 0) 100%);
                height: 100%;
                top: 0;
                z-index: 100;
                pointer-events: none;
                display: block;
                content: '';
                left: 0;
                position: absolute;
                width: 40px;
            }
            
            .main::after {
                right: 0;
                left: inherit;
                transform: rotate(180deg);
            }

body部分

      <div class="main">
            <!-- ! + tab/enter -->
            <div class="wrapper" style="transform: rotateX(-10deg) rotateY(0deg);">
                <!-- img[src=./img/$.png]*11 -->
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/d.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/e.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/f.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/g.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/h.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/i.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/j.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/k.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/l.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/m.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/n.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/o.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/p.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/r.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/s.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/t.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/u.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/v.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/w.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/x.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/y.png" alt="" draggable="false">
                <img src="https://4cs.gia.edu/cn/interactive-4cs/img/color/z.png" alt="" draggable="false">
            </div>
        </div>
            
        <h2 id="chooseResult"> </h2>
        <div class="container">
            <ul>
                <li>d</li>
                <li>e</li>
                <li>f</li>
                <li>g</li>
                <li>h</li>
                <li>i</li>
                <li>j</li>
                <li>k</li>
                <li>l</li>
                <li>m</li>
                <li>n</li>
                <li>o</li>
                <li>p</li>
                <li>r</li>
                <li>s</li>
                <li>t</li>
                <li>u</li>
                <li>v</li>
                <li>w</li>
                <li>x</li>
                <li>y</li>
                <li>z</li>
            </ul>
            <div class="center"></div>
        </div>

 

相册旋转js

var imgList = document.getElementsByTagName('img');
            var wrapper = document.getElementsByClassName('wrapper')[0];
            var list_box = document.getElementsByClassName('list_box')[0];
            var main = document.getElementsByClassName('main')[0];
            var list_item = document.querySelectorAll('.list div');
            var rotateY = 0;
            wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + 360 + 'deg)';
            // 每相邻两张图片的夹角
            var deg = 360 / imgList.length;
            window.onload = function() {
                wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + 360 + 'deg)';
                // 每相邻两张图片的夹角
                for(var i = 0; i < imgList.length; i++) {
                    imgList[i].style.transform = "rotateY(" + deg * i + "deg) translateZ(200px) scale(1)";
                    imgList[i].style.transitionDelay = (imgList.length - 1 - i) * 0.1 + 's';
                }
                var lastX = null,
                    lastY = null,
                    nowX = null,
                    nowY = null,
                    disX = null,
                    disY = null,
                    // 当前相册旋转的角度
                    rotateX = -10, //预设角度
                    rotateY = 0;
                var timer = null;
                var nowrotateY = null, //点击 初始旋转角度
                    lastrotateY = null, //点击结束  旋转角度
                    disrotateY = null, //开始与结束旋转的差值
                    activeIndex = 0, //当前显示的图片下标
                    num = null; //当前显示img 与  显示下一张  角度的差值
                main.addEventListener("touchstart", function(e) {
                    wrapper.style.transition = "";
                    lastX = e.changedTouches[0].pageX;
                    lastY = e.changedTouches[0].pageY;
                    noY = e.changedTouches[0].pageX;
                    nowrotateY = getTranslateY(wrapper);
                    falg = true;
                    if(nowrotateY < deg) {
                        wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + 360 + 'deg)';
                    }
                    rotateY = nowrotateY;
                    main.addEventListener("touchmove", function(e) {
                        nowX = e.changedTouches[0].pageX;
                        nowY = e.changedTouches[0].pageY;
                        disX = nowX - lastX;
                        disY = nowY - lastY;
                        rotateX += -disY * 0.15;
                        rotateY += disX * 0.15; //拖拽相册,旋转的角度比例                                        
                        index = isIndex();
                        //设置旋转角度区间
                        if(rotateY > 360 - deg) {
                            rotateY = rotateY - 360;
                        } else if(rotateY < 0) {
                            rotateY = rotateY + 360;
                        }
                        index = isIndex();
                        wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + rotateY + 'deg)';
                        lastY = nowY;
                        lastX = nowX;
                        setChoose(index); //传入当前显示的index触发导航栏跟随滚动   
                    }, false)
                    main.addEventListener("touchend", function(e) {
                        laY = e.changedTouches[0].pageX;
                        lastrotateY = getTranslateY(wrapper)
                        main.removeEventListener("touchmove", function() {}, false);
                        disrotateY = laY - noY; //与开始旋转的差值
                        num = Math.ceil(getTranslateY(wrapper) / deg) * deg - getTranslateY(wrapper); //与下一个36度的差值                                                                               
                        //拖拽相册 旋转顺滑
                        if(laY > noY && falg) {
                            rotateY = getTranslateY(wrapper) + num;
                        } else {
                            rotateY = getTranslateY(wrapper) - (deg - num);
                        }
                        if(falg) {
                            falg = false;
                            wrapper.style.transition = "1s";
                            wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + Math.ceil(rotateY) + 'deg)';
                        }
                        setChoose(isIndex()); //传入当前显示的index触发导航栏跟随滚动                   
                    }, false)
                }, false)

                //判断当前index
                function isIndex() {
                    var rote = getTranslateY(wrapper);
                    var i = Math.round(rote / deg);
                    i = imgList.length - Math.abs(i);
                    if(rote < deg) {
                        i = 0
                    }
                    return Math.abs(i)
                }
            }
            //获取元素rotateY
            function getTranslateY(node) {
                var regRule = /rotateY(Y|\dd)?\(\s*(\w+\s*,)?\s*([^,]+)(\s*,[^)]+)?\s*\)/;
                var transform = node.style.transform;
                var reg;
                if(!transform) {
                    return null;
                }
                reg = regRule.exec(transform);
                return +reg[3].split('deg')[0];
            }

导航拖拽js

//$(function(){
//var activeIn=window.sessionStorage.getItem('activeIndex');
//if (!activeIn) {
//    activeIn = window.sessionStorage.setItem('activeIndex',0)    
//}else{
//    console.log(activeIn)
//}
//$('.but').eq(activeIn).addClass('active').siblings().removeClass('active');
//$('.but').click(function(){
//    console.log($('.but'))
//    let index = $(this).index()-$('.but').length;
//    console.log(index)
//    activeIn = window.sessionStorage.setItem('activeIndex',index)    
//    $(this).addClass('active').siblings().removeClass('active');
////    $(".invitation_card_lst ul").eq(index).addClass('active').siblings().removeClass('active');
//})
//})
//
//


var config = {
    container: document.querySelector(".container"),
    optionWidth: 70,
    title: document.getElementById("chooseResult"),
    newindex:null,
    lastindex:null,
    disindex:null,
    options: [
    {
        value: 0,
        text: "d"
    }, {
        value: 1,
        text: "e"
    }, {
        value: 2,
        text: "f"
    }, {
        value: 3,
        text: "j"
    }, {
        value: 4,
        text: "h"
    }, {
        value: 5,
        text: "j"
    }, {
        value: 6,
        text: "j"
    }, {
        value: 7,
        text: "k"
    }, {
        value: 8,
        text: "l"
    },{
        value: 9,
        text: "m"
    },
    {
        value: 10,
        text: "n"
    }, {
        value: 11,
        text: "o"
    }, {
        value: 12,
        text: "p"
    }, {
        value: 13,
        text: "r"
    }, {
        value: 14,
        text: "s"
    }, {
        value: 15,
        text: "t"
    }, {
        value: 16,
        text: "u"
    }, {
        value: 17,
        text: "v"
    }, {
        value: 18,
        text: "w"
    },{
        value: 19,
        text: "x"
    },
     {
        value: 20,
        text: "y"
    }, {
        value: 21,
        text: "z"
    }]
}
config.ul = config.container.querySelector("ul");
config.containerWidth = config.container.clientWidth;
config.ulWidth = config.options.length * config.optionWidth;
config.maxLeft = config.containerWidth / 2;
config.minLeft = config.maxLeft - config.ulWidth + config.optionWidth;

function forbiddenSelect() {
    config.container.onselectstart = function() {
        return false
    }
}

function createOptions() {
    config.ul.innerHTML = "";
    var frag = document.createDocumentFragment();
    config.ul.style.width = config.ulWidth + "px";
    for(const op of config.options) {
        var li = document.createElement("li");
        li.innerHTML = `<i data-value="${op.value}">${op.text}</i>`;
        li.style.width = config.optionWidth + "px";
        frag.appendChild(li);
    }
    config.ul.appendChild(frag);
}
//导航跟随
function setChoose(value) {
    config.ul.style.transition = ".8s";
    var children = Array.from(config.ul.children);
    var left = config.containerWidth / 2 - value * config.optionWidth;
    config.ul.style.marginLeft = left + "px";
}
//相册跟随
var nowindex=null;
var lastindex=null;
function setRote({value}){    
    nowindex=value;
    rotateY=360-nowindex*deg
    wrapper.style.transition = ".5s";
    wrapper.style.transform = 'rotateX(' + -5 + 'deg) rotateY(' + rotateY+ 'deg)';    
    lastindex=nowindex;
}

function getChoose() {
    var left = getComputedStyle(config.ul).marginLeft;
    left = parseFloat(left) - config.containerWidth / 2;
    left = Math.abs(left);
    var i = left / config.optionWidth;
    i = Math.round(i);
    return config.options[i];
}

function regDragEvent(callback) {
    config.ul.addEventListener("touchstart",function(e) {
        config.ul.style.transition = "";
         wrapper.style.transition = "";
        //保存,深克隆初始位置,避免被更改
        var x = {a:e.changedTouches[0].pageX},
            left ={a:parseFloat(getComputedStyle(this).marginLeft)} ;
            left1={...left};
            x1={...x};
        config.ul.addEventListener("touchmove", function(e) {
            var dis = e.changedTouches[0].pageX - x1.a;
            var newLeft = left1.a + dis;
            if(newLeft < config.minLeft) {
                newLeft = config.minLeft;
            } else if(newLeft > config.maxLeft) {
                newLeft = config.maxLeft;
            }
            
            config.ul.style.marginLeft = newLeft + "px";
            callback && callback(getChoose());            
            setRote(getChoose());    
        })
        config.ul.addEventListener("touchend", function(e) {
            var op = getChoose();
            setChoose(op.value);
            callback && callback(op);
        })
    })
}
function setTitle(op) {
    config.title.innerText = `选中的文本:${op.text},选中的值:${op.value}`;
}

function init() {
    forbiddenSelect();
    createOptions();
    setChoose("0");
    setTitle(config.options[0]);
    regDragEvent(setTitle);
}
init();

....

posted @ 2020-05-12 14:56  混名汪小星  阅读(293)  评论(0编辑  收藏  举报