純JS實(shí)現(xiàn)可拖拽表單的簡(jiǎn)單實(shí)例
因?yàn)橐玫娇赏献П韱危瑐€(gè)人要比較喜歡自己動(dòng)手,不怎么喜歡在不懂實(shí)現(xiàn)或者原理的情況下用插件,所以查找資料實(shí)現(xiàn)了一個(gè)。
思路:放入:用mousedown判斷鼠標(biāo)點(diǎn)擊的位置是否在觸發(fā)控件的位置,如果是,mousemove的時(shí)候clone一個(gè)控件,修改透明度,然后放入容器內(nèi)的時(shí)候remove這個(gè)控件,并且在容器內(nèi)生成一個(gè)放入的控件(放入的控件和觸發(fā)的控件可以不一樣)
拖拽:同樣的, mousedown的時(shí)候判斷是哪個(gè)控件,mousemove的時(shí)候需要放一個(gè)占位div放在原有的位置上,并將元素修改透明度然后設(shè)置為絕對(duì)定位方便拖動(dòng),在進(jìn)行拖動(dòng)的時(shí)候,占位div也會(huì)跟著鼠標(biāo)位置進(jìn)行改變(判斷當(dāng)前鼠標(biāo)位置是否是容器內(nèi)控件的左上角加上控件高度的一半),放下的時(shí)候進(jìn)行判斷占位div的位置進(jìn)行插入。具體看代碼吧,這個(gè)思路加上的時(shí)間距離代碼實(shí)現(xiàn)的時(shí)間有點(diǎn)久遠(yuǎn)了,所有可能不是很準(zhǔn)確,但是大概的思路就是這樣了。
ps:要用到拖拽表單功能的,基本上可能都會(huì)要更改以往設(shè)計(jì)數(shù)據(jù)庫(kù)方式,這里可以提供給你們一個(gè)搜索關(guān)鍵詞 表的縱向存儲(chǔ)
注釋基本上都已經(jīng)寫的很詳細(xì)了,直接上代碼吧。
有什么問(wèn)題請(qǐng)大神們多多指教
<!DOCTYPE html>
<html>
<head>
<title>Test</title>
<style type="text/css" >
html,body
{
height:100%;
width:100%;
padding:0;
margin:0;
}
.dialog
{
/* width:250px;
height:250px;*/
position:absolute;
background-color:#ccc;
-webkit-box-shadow:1px 1px 3px #292929;
-moz-box-shadow:1px 1px 3px #292929;
box-shadow:1px 1px 3px #292929;
/*margin:10px;*/
top:50px;
left: 50px;
opacity:1;
}
.dialog-title
{
color:#fff;
background-color:#404040;
font-size:12pt;
font-weight:bold;
padding:4px 6px;
cursor:move;
position:absolute;
top:50px;
left: 50px;
}
.dialog-content
{
padding:4px;
cursor:move;
}
.none{
display: none;
}
.box{
width: 200px;
height: 500px;
background-color: gray;
line-height: 30px;
margin: 100px;
}
.place{
width: 200px;
height: 50px;
border: 1px dashed red;
}
</style>
<script type="text/javascript" src="js/devWin.js"></script>
</head>
<body>
<!-- <div id="dlgTest" class="dialog"> -->
<div id = "title" class="dialog-title">Dialog</div>
<div id = "title2" class="dialog-title" style ="top:10px">Dialog</div>
<!-- </div> -->
<a id = "a" href="#">123</a>
<input id = "text" type="text" class = "none">
<div id = "box" class = "box">
<!-- <input type="" name="" placeholder=""> -->
</div>
<div class = "place"></div>
</body>
<script type="text/javascript">
//要傳入的變量
//點(diǎn)擊觸發(fā)的對(duì)象
var click = document.getElementById("title");
var click2 = document.getElementById("title2");
//放入的容器
var box = document.getElementById("box");
//容器內(nèi)占位的DIV
var place = document.createElement("div");
place.className = "place";
//往容器內(nèi)添加的對(duì)象
var create = document.createElement("input");
create.type = "text";
var create2 = document.createElement("input");
create2.type = "password";
//是否可以添加多個(gè)
var isMany = true;
createWin(click,create,isMany,place,box);
createWin(click2,create2,isMany,place,box);
</script>
</html>
/**
* author:lzh
* 作用:可拖拽排序表單實(shí)現(xiàn)
* 參數(shù):oclick 點(diǎn)擊觸發(fā)事件的對(duì)象
* ocreate 出發(fā)后在表單中傳入的對(duì)象
* bisMany 單個(gè)oclick對(duì)象是否可拖入多個(gè)ocreate對(duì)象
* oplace 拖入時(shí)占位div對(duì)象
* obox 拖入的容器,不填則默認(rèn)為body
*/
function createWin(oclick,ocreate,bisMany,oplace,obox=document.body)
{
//是否點(diǎn)擊了觸發(fā)對(duì)象
var isClick = false;
//觸發(fā)對(duì)象是否為容器內(nèi)的元素
var isIncludeBox = false;
oplace.style.width = obox.offsetWidth-5 + "px";
oplace.style.height = oclick.offsetHeight-5 + "px";
//移動(dòng)效果的臨時(shí)元素
var oclickClone;
var oclickDown;
//計(jì)算偏移量
var diffObj;
var diffX;
var diffY;
var tmp;
var omove_position;
//點(diǎn)是否包含在容器內(nèi)
function isInclude(x,y,includeBox=obox)
{
if(x > includeBox.offsetLeft
&& y > includeBox.offsetTop
&& x < includeBox.offsetLeft + includeBox.offsetWidth
&& y < includeBox.offsetTop + includeBox.offsetHeight)
return true;
return false;
}
//移動(dòng)效果函數(shù)
function moveMagic(omove,e)
{
// omove_position = window.getComputedStyle(omove).getPropertyValue('position');
omove.style.opacity = 0.4;
omove.style.position = "absolute";
document.body.appendChild(omove);
omove.style.left = e.clientX-diffX+"px";
omove.style.top = e.clientY-diffY+"px";
}
function getdiff(e)
{
diffObj = e.target;
diffX = e.clientX-diffObj.offsetLeft;
diffY = e.clientY-diffObj.offsetTop;
}
//鼠標(biāo)按下事件
function down(e)
{
if(isInclude(e.clientX,e.clientY,oclick))
{
isClick = true;
//克隆點(diǎn)擊的觸發(fā)節(jié)點(diǎn)
oclickClone=oclick.cloneNode(true);
//計(jì)算鼠標(biāo)的偏移量(如果有margin的話會(huì)有偏移現(xiàn)象)
getdiff(e);
}
else
{
getdiff(e);
var child = obox.childNodes;
for(var i=0; i < child.length; i++)
{
//判斷鼠標(biāo)點(diǎn)擊是否是容器內(nèi)的元素,并且不能是占位div(如果不加這個(gè)占位div判斷會(huì)有bug,具體原因不知道)
if(isInclude(e.clientX,e.clientY,child[i])&& child[i] != oplace)
{
isClick = true;
isIncludeBox = true;
//克隆元素用來(lái)拖動(dòng)時(shí)的效果
oclickClone = child[i].cloneNode(true);
//克隆元素用來(lái)放下
oclickDown = child[i].cloneNode(true);
//按下之后刪除元素,并使用移動(dòng)效果來(lái)展示元素
obox.removeChild(child[i]);
moveMagic(oclickClone,e);
//插入占位div來(lái)弄
obox.insertBefore(oplace,child[i]);
// flag = true;
break;
}
}
}
}
//鼠標(biāo)移動(dòng)事件
function move(e)
{
if(isClick)
{
moveMagic(oclickClone,e);
//判斷鼠標(biāo)是否移動(dòng)到了容器內(nèi)部
if(isInclude(e.clientX,e.clientY,obox))
{
//計(jì)算容器內(nèi)的子節(jié)點(diǎn)
var child = obox.childNodes;
//一旦進(jìn)入就可以在首位置插入占位DIV
obox.insertBefore(oplace,child[0]);
//根據(jù)鼠標(biāo)位置放置占位DIV
for(var i = 0; i < child.length; i++)
{
//因?yàn)檎嘉籇IV是唯一的,所以只需要這樣判斷即可
if(e.clientY > child[i].offsetTop+child[i].offsetHeight/2)
{
//判斷是否拖動(dòng)到了結(jié)尾
if(i != child.length-1)
obox.insertBefore(oplace,child[i+1]);
else
obox.appendChild(oplace);
}
}
}
}
}
//鼠標(biāo)抬起事件
function up(e)
{
isClick = false;
//鼠標(biāo)抬起則可以刪除臨時(shí)的拖動(dòng)效果元素
document.body.removeChild(oclickClone);
//如果將元素放置到了容器內(nèi)
if(isInclude(e.clientX,e.clientY))
{
var child = obox.childNodes;
//占位div的位置
var insertPlace;
for(var i=0; i<child.length;i++)
{
//確定占位div的位置
if(oplace === child[i])
{
obox.removeChild(child[i]);
insertPlace = i;
break;
}
}
//判斷是否可以放置多個(gè)
if(!bisMany)
{
if(isIncludeBox)
ocreate = oclickDown;
if(insertPlace==child.length)
obox.appendChild(ocreate);
else
obox.insertBefore(ocreate,child[insertPlace]);
}
else
{
//可以放置多個(gè)則需要每個(gè)都克隆一下
if(isIncludeBox)
var ocreateClone = oclickDown;
else
var ocreateClone = ocreate.cloneNode(true);
if(insertPlace==child.length)
obox.appendChild(ocreateClone);
else
{
obox.insertBefore(ocreateClone,child[insertPlace]);
}
}
}
else
{
if(isIncludeBox)
{
var child = obox.childNodes;
for(var i=0; i<child.length; i++)
{
if(child[i] === oplace)
{
obox.removeChild(child[i]);
obox.insertBefore(oclickDown,child[i]);
}1
}
}
}
isIncludeBox = false;
}
document.addEventListener('mousemove',move);
document.addEventListener('mousedown',down);
document.addEventListener('mouseup',up);
}
以上這篇純JS實(shí)現(xiàn)可拖拽表單的簡(jiǎn)單實(shí)例就是小編分享給大家的全部?jī)?nèi)容了,希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
相關(guān)文章
關(guān)于JS模塊化的知識(shí)點(diǎn)分享
在本篇文章里小編給大家整理的是關(guān)于JS模塊化的知識(shí)點(diǎn)分享,有需要的朋友們可以學(xué)習(xí)下。2019-10-10
前端頁(yè)面適配之postcss-px-to-viewport實(shí)現(xiàn)步驟
postcss-px-to-viewport是一個(gè)PostCSS插件,它可以將px單位轉(zhuǎn)換為視口單位(vw、vh?或?vmin),這篇文章主要給大家介紹了關(guān)于前端頁(yè)面適配之postcss-px-to-viewport的實(shí)現(xiàn)步驟,需要的朋友可以參考下2024-03-03
JavaScript數(shù)組方法-系統(tǒng)性總結(jié)詳解
本文是小編給大家特意整理的關(guān)于js數(shù)組方法的知識(shí),非常實(shí)用,在面試筆試題中經(jīng)常用得到,有需要的朋友可以參考下2021-09-09
JavaScript 實(shí)現(xiàn)HTML DOM增刪改查操作的常見方法詳解
這篇文章主要介紹了JavaScript 實(shí)現(xiàn)HTML DOM增刪改查操作,結(jié)合實(shí)例形式分析了JavaScript針對(duì)HTML DOM元素增刪改查常見操作技巧與使用注意事項(xiàng),需要的朋友可以參考下2020-01-01
JavaScript 函數(shù)的定義-調(diào)用、注意事項(xiàng)
這篇文章主要介紹了JavaScript 函數(shù)的定義-調(diào)用、注意事項(xiàng),需要的朋友可以參考下2017-04-04
javascript實(shí)現(xiàn)table表格隔行變色的方法
這篇文章主要介紹了javascript實(shí)現(xiàn)table表格隔行變色的方法,涉及javascript針對(duì)表格元素與樣式的操作技巧,需要的朋友可以參考下2015-05-05
javascript修改IMG標(biāo)簽的src問(wèn)題
javascript修改IMG標(biāo)簽的SRC,在IE6下面圖片修改正常,但在IE7和Firefox下面卻不刷新,下面有個(gè)解決方法,大家可以參考下2014-03-03

