js拼图

;(function($){
  
  function arrayIndexOf(r, num){
    if( Array.prototype.indexOf ){
      return r.indexOf(num);
    }else{
      for(var i=0, len=r.length; i<len; i++){
        if( r[i] === num ) return i;
      }
      
      return -1;
    }
  }
  
  /* 
    初始化范围数字
    @x x轴最大值
    @y y轴最大值
    数字从 0 开始填
    最后一行,只有最后一个算合法格子
    ret 上下左右,一组一组存
  */
  function getRangeNum(x, y){
    var ret = [];
    
    var cur = -1;
    
    for(var i=0; i<y; i++){
      for(var j=0; j<x; j++){
        
        cur++;
        
        var temp = [];
        
        //上
        if( i > 0){
          temp.push( cur - x );
        }else{
          temp.push( -1 );
        }
        
        //下
        if( i < y-1 ){
          temp.push( cur + x );
        }else{
          temp.push( -1 );
        }
        
        //左
        if( j > 0 ){
          temp.push( cur - 1 );
        }else{
          temp.push( -1 );
        }
        
        //右
        if( j < x - 1){
          temp.push( cur + 1 );
        }else{
          temp.push( -1 );
        }
        
        ret.push(temp);
      }//for
      
      
    }//for
    
    return ret;
  }
  
  var direction = {
    "0" : "s", // 上
    "1" : "x", // 下
    "2" : "z", // 左
    "3" : "y"  // 右
  }
  
  var emptyFun = function(){};
  
  function pintu(option){
    
    var imgSrc = option.imgSrc;
    var imgWidth = option.imgWidth;
    var imgHeight = option.imgHeight;
    var block = option.block || 100;
    var id = option.id || "J_paper_pintu";
    var begin = option.begin || emptyFun;
    var success = option.success || emptyFun;
    
    var x = parseInt( imgWidth / block, 10);
    var y = parseInt( imgHeight / block, 10);
    
    var num = 0;
    var beginEmpty = 0;
    var empty = 0;
    
    $(function(){
      var $id = $("#" + id);
      var frag = document.createDocumentFragment();
      
      for(var i = 0; i < y; i++){ //行
        for(var j = 0; j < x; j++){ //列
          var div = document.createElement("div");
          div.style.width = block + "px";
          div.style.height = block + "px";
          div.style.left = block * j + "px";
          div.style.top = block * i + "px";
          
          var imgx = block * j * -1 + "px";
          var imgy = block * i * -1 + "px";
          div.style.background = "url("+ imgSrc +") "+ imgx +" "+ imgy +" no-repeat";
          
          div.setAttribute("data-num", num);
          num++;
          frag.appendChild(div);
        }
      }
      
      //多加一行
      for(i = y, j = 0; j < x; j++ ){
        var span = document.createElement("span");
        span.setAttribute("data-num", num);
        
        if(j == x - 1){
          span.className = "last";
          empty = num;
          beginEmpty = num;
        }else{
          num++;
        } 
        
        span.style.width = block + "px";
        span.style.height = block + "px";
        span.style.left = block * j + "px";
        span.style.top = block * i + "px";

        frag.appendChild(span);
      }
      
      $id.css({
        width : x * block + "px",
        height : (y+1) * block + "px",
      }).append(frag);
      
      var $blocks = $id.find("div");
      var blocksLength = $blocks.length;
      var ret = getRangeNum(x, y+1);
      
      function moveBlock($elem, isHuman){
        if( isHuman && begin ){
          begin();
          begin = null;
        }
        
        var num = +$elem.attr("data-num"),
            rangeNum = ret[num],
            i = arrayIndexOf(rangeNum, empty);

        if( i > -1 ){
          $elem.attr("data-num", empty);
          empty = num;
          
          //移动方块
          var d = direction[ i.toString() ];
          
          switch(d){
            case "s" : $elem.css("top", parseInt($elem.css("top"), 10) - block + "px");break;
            case "x" : $elem.css("top", parseInt($elem.css("top"), 10) + block + "px");break;
            case "z" : $elem.css("left", parseInt($elem.css("left"), 10) - block + "px"); break;
            case "y" : $elem.css("left", parseInt($elem.css("left"), 10) + block + "px"); break;
          }
          
          isHuman && checkSuccess();
        }
      }//end moveBlock
      
      //随机打乱图片
      function randomGame(){
        var max = 1000;
        var a = 0;
        
        function fn(){
          if( a++ > max ) return;
          
     
          var n = parseInt( Math.random()*4, 10);
          var i = ret[empty];
          var e = i[n];
          
          if( e != -1 && e < blocksLength ){
            var $elem = $blocks.eq(e);
            moveBlock($elem);
          }

          fn();
        }
        
        fn();
      }
      
      //判断是否成功
      function checkSuccess(){
        if( empty == beginEmpty){

          for(var i = 0; i < blocksLength; i++){
            if( +$blocks.eq(i).attr("data-num") != i ){
              return;
            }
          }
          
          success();
        }
      }
      
      randomGame();
      
      $id.on("click", "div", function(){
      
        moveBlock($(this), true);
        
      });
      
    });//ready
    
    
    
  }//end pintu
  
  window.pintu = pintu;
  
})(jQuery);

 例子:

<!doctype html>
<html>
<head>
  <meta charset="UTF-8">
  <title>pintu</title>
  <script src="http://www.18touch.com/Public/js/jquery.min.js"></script>
  
  <link rel="stylesheet" href="pintu.css" />
  <script src="pintu.js"></script>
</head>
<body>

  <div class="paper-pintu-wrap" style="float:left;">
    <div id="J_paper_pintu" class="paper-pintu">
      
    </div>
  </div>
  
  <img src="t3.jpg" alt="" style="float:right;" />
  
  <script>
    pintu({
      imgSrc : "./t3.jpg",
      imgWidth : 300,
      imgHeight : 300,
      begin : function(){
        //console.log("begin");
      },
      success : function(){
        //console.log("success");
        alert("success")
      }
    });

  </script>
</body>
</html>

 

posted on 2014-12-08 18:07  kudosharry  阅读(261)  评论(0编辑  收藏  举报

导航