cssAudio - Activefile-genericCSS - ActiveGeneric - ActiveHTML - ActiveImage - ActiveJS - ActiveSVG - ActiveText - Activefile-genericVideo - ActiveLovehtmlicon-new-collectionicon-personicon-teamlog-outoctocatpop-outspinnerstartv

Pen Settings

CSS Base

Vendor Prefixing

Add External Stylesheets/Pens

Any URL's added here will be added as <link>s in order, and before the CSS in the editor. If you link to another Pen, it will include the CSS from that Pen. If the preprocessor matches, it will attempt to combine them before processing.

Quick-add: + add another resource

Add External Scripts/Pens

Any URL's added here will be added as <script>s in order, and run before the JavaScript in the editor. You can use the URL of any other Pen and it will include the JavaScript from that Pen.

Quick-add: + add another resource

Code Indentation

     

Save Automatically?

If active, Pens will autosave every 30 seconds after being saved once.

Auto-Updating Preview

If enabled, the preview panel updates automatically as you code. If disabled, use the "Run" button to update.

            
              <ul>
  <li class="isotopey">1</li>
  <li class="isotopey">2</li>
  <li class="isotopey">3</li>
  <li class="isotopey">4</li>
  <li class="isotopey">5</li>
  <li class="isotopey">6</li>
  <li class="isotopey">7</li>
  <li class="isotopey">8</li>
  <li class="isotopey">9</li>
  <li class="isotopey">10</li>
  <li class="isotopey">11</li>
  <li class="isotopey">12</li>
  <li class="isotopey">13</li>
  <li class="isotopey">14</li>
  <li class="isotopey">15</li>
  <li class="isotopey">16</li>
  <li class="isotopey">17</li>
  <li class="isotopey">18</li>
  <li class="isotopey">19</li>
  <li class="isotopey">20</li>
  <li class="isotopey">21</li>
  <li class="isotopey">22</li>
  <li class="isotopey">23</li>
  <li class="isotopey">24</li>  
</ul>
            
          
!
            
              @import "compass/css3";

$charcoal: #6c6c6c;
ul {
  width: 1000px;
  border: 1px solid black;
  margin: 10px;
}
li {
  width: 100px;
  height: 100px;
  background: #ccc;
  margin: 5px; 
  padding-top: 40px;
  color: white;
  font-size: 25px;
  text-shadow: 0 0 5px $charcoal;
  box-sizing: border-box;
  text-align: center;
  transition: all 500ms ease;
  transition-property: transform, top, left;
  &.ui-sortable-placeholder {
    visibility: visible!important;
    background: #aaa;
    box-shadow: inset 0 0 100px $charcoal;
    &.active {
      box-shadow: inset 0 0 200px $charcoal;                
    }
    &.starting {
      transition-property: none;
    }
  }
  &.grabbing {
    transform: rotate(3deg);            
  }
  &.moving {
    box-shadow: $charcoal 0 0 5px 2px!important;
    transition: transform 200ms ease;    
  }
}

/**** Isotope Filtering ****/

.isotope-item {
  z-index: 2;
}

.isotope-hidden.isotope-item {
  pointer-events: none;
  z-index: 1;
}
            
          
!
            
              var list = $('ul');
list.isotope({  
  transformsEnabled: false
  , itemSelector: '.isotopey'
  , onLayout: function() {
    list.css('overflow', 'visible');
  }  
});
list.sortable({
  cursor: 'move'
  //, tolerance: 'intersection'  //'pointer' is too janky
  , start: function(event, ui) {                        
    //add grabbing and moving classes as user has begun
    //REMOVE isotopey so that isotope does not try to sort our item,
    //resulting in the item moving around and flickering on 'change'
    ui.item.addClass('grabbing moving').removeClass('isotopey');
    
    ui.placeholder
      .addClass('starting') //adding the 'starting' class removes the transitions from the placeholder.
      //remove 'moving' class because if the user clicks on a tile they just moved,
      //the placeholder will have 'moving' class and it will mess with the transitions
      .removeClass('moving')
      //put placeholder directly below tile. 'starting' class ensures the
      //placeholder simply appears and does not 'fly' into place
      .css({
        top: ui.originalPosition.top
        , left: ui.originalPosition.left
      })
      ;
    //reload the items in their current state to override any previous
    //sorting and to include placeholder, but do NOT call a re-layout
    list.isotope('reloadItems');                    
  }                
  , change: function(event, ui) {
    //change only fires when the DOM is changed. the DOM changes when 
    //the placeholder moves up or down in the document order 
    //within the sortable container
    
    //remove 'starting' class so that placeholder can now move smoothly
    //with the interface
    ui.placeholder.removeClass('starting');
    //reload items to include the placeholder's new position in the DOM. 
    //then when you sort, everything around the placeholder moves as 
    //though the item were moving it.
    list
      .isotope('reloadItems')
      .isotope({ sortBy: 'original-order'})
    ;
  }
  , beforeStop: function(event, ui) {
    //in this event, you still have access to the placeholder. this means
    //you know exactly where in the DOM you're going to place your element.
    //place it right next to the placeholder. jQuery UI Sortable removes the
    //placeholder for you after this event, and actually if you try to remove
    //it in this step it will throw an error.
    ui.placeholder.after(ui.item);                    
  }
  , stop: function(event, ui) {      
    //user has chosen their location! remove the 'grabbing' class, but don't
    //kill the 'moving' class right away. because the 'moving' class is 
    //preventing your item from having transitions, you should keep it on
    //until isotope is done moving everything around. it will "snap" into place
    //right where your placeholder was.
    
    //also, you must add the 'isotopey' class back to the box so that isotope
    //will again include your item in its sorting list
    ui.item.removeClass('grabbing').addClass('isotopey');
    
    //reload the items again so that your item is included in the DOM order
    //for isotope to do its final sort, which actually won't move anything
    //but ensure that your item is in the right place
    list
      .isotope('reloadItems')
      .isotope({ sortBy: 'original-order' }, function(){
        //finally, after sorting is done, take the 'moving' class off.
        //doing it here ensures that your item "snaps" and isn't resorted
        //from its original position. since this happens on callback,
        //if the user grabbed the tile again before callback is fired,
        //don't remove the moving class in mid-grab
        
        //for some reason in this code pen, the callback isn't firing predictably
        console.log(ui.item.is('.grabbing')); 
        if (!ui.item.is('.grabbing')) {
          ui.item.removeClass('moving');                        
        }
      })
      ;
  }
});
            
          
!
999px
Loading ..................

Console