knockout/Layout
Knockout Layout
by MKGaru
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.3.0/knockout-debug.js"></script>
<script src="https://mbest.github.io/knockout.punches/knockout.punches.js"></script>
<script src="https://rawgit.com/SteveSanderson/knockout-es5/master/dist/knockout-es5.js"></script>
<div class="gridder">
<div class="gridder-item" x="2" y="0" width="1" height="1">
<div class="gridder-item-content">運転席</div>
</div>
<div class="gridder-item" x="0" y="0" width="1" height="1">
<div class="gridder-item-content">添乗員</div>
</div>
<div class="gridder-item" x="0" y="1" width="1" height="2">
<div class="gridder-item-content">ベッド</div>
</div>
<div class="gridder-item" x="1" y="1" width="1" height="1">
<div class="gridder-item-content">B</div>
</div>
<div class="gridder-item" x="2" y="1" width="1" height="1">
<div class="gridder-item-content">C</div>
</div>
<div class="gridder-item" x="1" y="2" width="2" height="1">
<div class="gridder-item-content">車いす</div>
</div>
</div>
CSS
body{
width: calc(100px * 12);
overflow:hidden;
}
.gridder{
position:relative;
}
.gridder-item{
position:absolute;
transition: all 500ms ease;
}
.gridder-item.over{
border: 1px dashed #000;
}
.gridder-item[draggable]{
user-select: none;
/* Required to make elements draggable in old WebKit */
-khtml-user-drag: element;
-webkit-user-drag: element;
cursor:pointer;
}
.gridder-item.drag{
opacity: 0.7;
}
.gridder-item-content {
background: white;
color: #2c3e50;
font-family: 'Indie Flower', cursive;
text-align: center;
font-size: 20px;
height:100%;
width:100%;
}
.gridder-item-content .fa {
font-size: 64px;
display: block;
margin: 20px 0 10px;
}
body{
background:#cecece;
}
TypeScript
namespace gridder{
var defaultOptions = {
prefix: '', //data-gs-
columns: 3,
rows: 4,
margin: 5,
width: 50,
height: 50
};
export class Gridder{
private observer: MutationObserver;
private latestDragInfo={
element:null,
offsetX:0,
offsetY:0
};
public options;
constructor(element,options={}){
var gridder = this;
gridder.options = options;
Object.keys(defaultOptions).forEach((key)=>{
if(options[key] === void 0) options[key] = defaultOptions[key];
});
if(typeof element =='string')
element = document.querySelector(element);
if(element.jquery)
element = element[0];
gridder.onInitGrid(element);
}
public getCollisions(x,y,w,h,excludes=[]){
var gridder = this;
var options = gridder.options;
var collisions =[];
var blocks = [];
for(var c=0;c<w;c++)
for(var r=0;r<h;r++)
blocks.push([x+c,y+r]);
blocks.forEach(block=>{
document.elementsFromPoint(
options.margin * (block[0]) + block[0] * (options.width + options.margin)+options.width/2,
options.margin * (block[1]) + block[1] * (options.height + options.margin)+options.height/2
)
.filter((collision)=>collision.classList.contains('gridder-item'))
.filter((collision)=>excludes.indexOf(collision)==-1)
.forEach((collision)=>collisions.push(collision))
});
return collisions;
}
public isEmpty(column,row){
var gridder = this;
}
public onInitGrid(element){
var gridder = this;
var options = gridder.options;
element.style.width = `${(options.width+options.margin*2)*options.columns}px`;
element.style.height = `${(options.height+options.margin*2)*options.rows}px`;
element.addEventListener('dragover',function(event){
event.preventDefault();
var x = event.pageX - gridder.latestDragInfo.offsetX;
var y = event.pageY - gridder.latestDragInfo.offsetY;
var w = gridder.latestDragInfo.element.getAttribute(options.prefix+'width');
var h =...