使用 css 将元素中心放在左上角,以便将 "transform" 引用到元素的中心
Place element center to top left with css in order to reference "transform" to the element's center
我想将元素的中心放置在单击的同一位置:
为此,我想使用转换,但对于初始 css 属性 我不能使用:
#element{
position:fixed;
top:0;
left:0;
transform:translate(-50%, -50%);
}
因为初始参考位置是一样的,使用transform,翻译的时候就不行了,举个例子:
let action1=document.querySelector("#actions1");
let action2=document.querySelector("#actions2");
let action3=document.querySelector("#actions3");
let action4=document.querySelector("#actions4");
let boton1=document.querySelector("#me1");
let boton2=document.querySelector("#me2");
let boton3=document.querySelector("#me3");
let boton4=document.querySelector("#me4");
boton1.addEventListener("click",move1);
boton2.addEventListener("click",move2);
boton3.addEventListener("click",move3);
boton4.addEventListener("click",move4);
function move1(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action1.style.display="grid";
action2.style.display="none";
action3.style.display="none";
action4.style.display="none";
action1.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move2(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action2.style.display="grid";
action1.style.display="none";
action3.style.display="none";
action4.style.display="none";
action2.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move3(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action3.style.display="grid";
action1.style.display="none";
action2.style.display="none";
action4.style.display="none";
action3.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move4(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action4.style.display="grid";
action1.style.display="none";
action2.style.display="none";
action3.style.display="none";
let size=action4.getBoundingClientRect();
action4.style.top=startY-(size.height/2)+"px";
action4.style.left=startX-(size.width/2)+"px";
}
#actions1,#actions2,#actions3,#actions4{
display:none;grid-template-columns:auto;grid-gap:5px;
padding:10px;
}
#actions1{
position:fixed;top:0;left:0;
}
#actions2{
position:fixed;top:0;left:0;
transform:translate(-50%, -50%);
}
#actions3{
position:fixed;top:-40px;left:-45px;
}
#actions4{
position:fixed;top:0;left:0;
}
#botons{
position:fixed;
top: 50px;left:0;right:0;
display:flex;
justify-content: space-around;
}
<div id="botons">
<button id="me1">normal</button>
<button id="me2">not posible to reference with transform</button>
<button id="me3">desirable</button>
<button id="me4">old school</button>
</div>
<div id="actions1">
<button>open1</button>
<button>new1</button>
<button>delete1</button>
</div>
<div id="actions2">
<button>open2</button>
<button>new2</button>
<button>delete2</button>
</div>
<div id="actions3">
<button>open3</button>
<button>new3</button>
<button>delete3</button>
</div>
<div id="actions4">
<button>open4</button>
<button>new4</button>
<button>delete4</button>
</div>
如您所见,第一个示例和第二个示例的行为方式相同,因为元素的初始参考位置没有改变,两者都有:
#element{
position:fixed;top:0;left:0;
}
第三个例子显示了理想的结果,但是这个方法让我一直知道宽度和高度,如果我向这个元素添加子元素,它就不会工作,最后一个例子显示了老派会怎么做,那会取大小然后除以 2,问题是它是一个 hack,因为 transform 比直接改变位置有 better 性能。
如果您单击演示按钮中的任意位置,它会在按钮内光标单击的中心点显示一个 .dropdown-menu
。
也不是太老套,因为它的 position: absolute
在 .btn-group
中,使用 transform: translate(-50%,-50%)
使其在左上角很好地居中。
您可以向 .dropdown-menu
添加任意数量的按钮,它会始终以您的点击为中心。
可能最好在页面加载时在 .dropdown-menu
内呈现按钮,但如果您要通过 javascript 添加动态按钮,则可以根据需要添加按钮。
您需要在单击关闭菜单时触发 .hide()
和 .dropdown-menu
方法,这应该很容易。
如果你想玩也可以看看http://jsfiddle.net/joshmoto/sdn5eboa/
运行 下面的代码查看示例...
// demo button click event
$('.btn-demo').on('click', function(e) {
// get the next element matching .dropdown-menu
var $dropdown_menu = $(this).next('.dropdown-menu');
// your custom button or add these however method you are doing
var btn_1 = '<button class="dropdown-item" type="button">Button 1</button>';
var btn_2 = '<button class="dropdown-item" type="button">Button 2</button>';
var btn_3 = '<button class="dropdown-item" type="button">Button 3</button>';
// add the desired buttons to the .dropdown-menu on click
$dropdown_menu.html(btn_1 + btn_2 + btn_3);
// add this css to .dropdown-menu menu on click
$dropdown_menu.css({
// top postion: cursor click postion minus .btn-demo top-offset position
top: (e.pageY - $(this).offset().top),
// left postion: cursor click postion minus .btn-demo left-offset position
left: (e.pageX - $(this).offset().left),
// display block to reveal the .dropdown-menu or use .show() function
// display: 'block'
}).show();
});
@import 'http://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css';
HTML,
BODY {
height: 100%;
min-height: 100%;
cursor: crosshair;
width: 100%;
}
BUTTON {
cursor: crosshair !important;
}
.btn-group {
position: relative;
display: inline-flex;
vertical-align: middle;
}
.dropdown-menu {
transform: translate(-50%,-50%);
position: absolute;
display: none;
z-index: 1000;
float: left;
min-width: 0;
}
<!-- demo containers to center .btn-group please ignore this -->
<div class="d-flex align-items-center h-100">
<div class="container">
<div class="col-12 text-center">
<!-- question related code only -->
<div class="btn-group">
<button class="btn btn-primary btn-demo">
Long demo button title for testing
</button>
<div class="dropdown-menu"></div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
仅翻译版本
见下文 transform: translate()
唯一将下拉菜单中心定位在鼠标光标上的按钮内的版本。
这也是一个 jsfiddle:http://jsfiddle.net/joshmoto/2qLvp5a3/
// demo button click event
$('.btn-demo').on('click', function(e) {
// get the next element matching .dropdown-menu
var $dropdown_menu = $(this).next('.dropdown-menu');
// your custom button or add these however method you are doing
var btn_1 = '<button class="dropdown-item" type="button">Button 1</button>';
var btn_2 = '<button class="dropdown-item" type="button">Button 2</button>';
var btn_3 = '<button class="dropdown-item" type="button">Button 3</button>';
// add the desired buttons to the .dropdown-menu on click
$dropdown_menu.html(btn_1 + btn_2 + btn_3);
// show the dropdown menu so we can get its width height
// currently hidden using css opacity: 0;
$dropdown_menu.show();
// dropdown menu width height
var ddm_w = $dropdown_menu.outerWidth();
var ddm_h = $dropdown_menu.outerHeight();
// click position values inside button
var click_x = e.pageX - $(this).offset().left;
var click_y = e.pageY - $(this).offset().top;
// new translate positions for center menu
var trans_x = click_x - (ddm_w / 2);
var trans_y = click_y - (ddm_h / 2);
// add this css to .dropdown-menu menu on click
$dropdown_menu.css({
// translate position to top left corner of dropdown
'transform' : 'translate(' + trans_x + 'px,' + trans_y + 'px)',
// reveal the dropdown menu
'opacity' : 1
});
});
@import 'http://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css';
HTML,
BODY {
height: 100%;
min-height: 100%;
cursor: crosshair;
width: 100%;
}
BUTTON {
cursor: crosshair !important;
}
.btn-group {
position: relative;
display: inline-flex;
vertical-align: middle;
}
.dropdown-menu {
opacity: 0;
position: absolute;
top: 0;
left: 0;
display: block;
float: left;
min-width: 0;
margin: 0;
}
<!-- demo containers to center .btn-group please ignore this -->
<div class="d-flex align-items-center h-100">
<div class="container">
<div class="col-12 text-center">
<!-- question related code only -->
<div class="btn-group">
<button class="btn btn-primary btn-demo" type="button">
Long demo button title for testing
</button>
<div class="dropdown-menu">
</div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
我想将元素的中心放置在单击的同一位置:
为此,我想使用转换,但对于初始 css 属性 我不能使用:
#element{
position:fixed;
top:0;
left:0;
transform:translate(-50%, -50%);
}
let action1=document.querySelector("#actions1");
let action2=document.querySelector("#actions2");
let action3=document.querySelector("#actions3");
let action4=document.querySelector("#actions4");
let boton1=document.querySelector("#me1");
let boton2=document.querySelector("#me2");
let boton3=document.querySelector("#me3");
let boton4=document.querySelector("#me4");
boton1.addEventListener("click",move1);
boton2.addEventListener("click",move2);
boton3.addEventListener("click",move3);
boton4.addEventListener("click",move4);
function move1(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action1.style.display="grid";
action2.style.display="none";
action3.style.display="none";
action4.style.display="none";
action1.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move2(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action2.style.display="grid";
action1.style.display="none";
action3.style.display="none";
action4.style.display="none";
action2.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move3(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action3.style.display="grid";
action1.style.display="none";
action2.style.display="none";
action4.style.display="none";
action3.style.transform="translate("+startX+"px,"+startY+"px)";
}
function move4(e){
let startX=e.clientX || e.touches[0].clientX;
let startY=e.clientY || e.touches[0].clientY;
action4.style.display="grid";
action1.style.display="none";
action2.style.display="none";
action3.style.display="none";
let size=action4.getBoundingClientRect();
action4.style.top=startY-(size.height/2)+"px";
action4.style.left=startX-(size.width/2)+"px";
}
#actions1,#actions2,#actions3,#actions4{
display:none;grid-template-columns:auto;grid-gap:5px;
padding:10px;
}
#actions1{
position:fixed;top:0;left:0;
}
#actions2{
position:fixed;top:0;left:0;
transform:translate(-50%, -50%);
}
#actions3{
position:fixed;top:-40px;left:-45px;
}
#actions4{
position:fixed;top:0;left:0;
}
#botons{
position:fixed;
top: 50px;left:0;right:0;
display:flex;
justify-content: space-around;
}
<div id="botons">
<button id="me1">normal</button>
<button id="me2">not posible to reference with transform</button>
<button id="me3">desirable</button>
<button id="me4">old school</button>
</div>
<div id="actions1">
<button>open1</button>
<button>new1</button>
<button>delete1</button>
</div>
<div id="actions2">
<button>open2</button>
<button>new2</button>
<button>delete2</button>
</div>
<div id="actions3">
<button>open3</button>
<button>new3</button>
<button>delete3</button>
</div>
<div id="actions4">
<button>open4</button>
<button>new4</button>
<button>delete4</button>
</div>
如您所见,第一个示例和第二个示例的行为方式相同,因为元素的初始参考位置没有改变,两者都有:
#element{
position:fixed;top:0;left:0;
}
如果您单击演示按钮中的任意位置,它会在按钮内光标单击的中心点显示一个 .dropdown-menu
。
也不是太老套,因为它的 position: absolute
在 .btn-group
中,使用 transform: translate(-50%,-50%)
使其在左上角很好地居中。
您可以向 .dropdown-menu
添加任意数量的按钮,它会始终以您的点击为中心。
可能最好在页面加载时在 .dropdown-menu
内呈现按钮,但如果您要通过 javascript 添加动态按钮,则可以根据需要添加按钮。
您需要在单击关闭菜单时触发 .hide()
和 .dropdown-menu
方法,这应该很容易。
如果你想玩也可以看看http://jsfiddle.net/joshmoto/sdn5eboa/
运行 下面的代码查看示例...
// demo button click event
$('.btn-demo').on('click', function(e) {
// get the next element matching .dropdown-menu
var $dropdown_menu = $(this).next('.dropdown-menu');
// your custom button or add these however method you are doing
var btn_1 = '<button class="dropdown-item" type="button">Button 1</button>';
var btn_2 = '<button class="dropdown-item" type="button">Button 2</button>';
var btn_3 = '<button class="dropdown-item" type="button">Button 3</button>';
// add the desired buttons to the .dropdown-menu on click
$dropdown_menu.html(btn_1 + btn_2 + btn_3);
// add this css to .dropdown-menu menu on click
$dropdown_menu.css({
// top postion: cursor click postion minus .btn-demo top-offset position
top: (e.pageY - $(this).offset().top),
// left postion: cursor click postion minus .btn-demo left-offset position
left: (e.pageX - $(this).offset().left),
// display block to reveal the .dropdown-menu or use .show() function
// display: 'block'
}).show();
});
@import 'http://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css';
HTML,
BODY {
height: 100%;
min-height: 100%;
cursor: crosshair;
width: 100%;
}
BUTTON {
cursor: crosshair !important;
}
.btn-group {
position: relative;
display: inline-flex;
vertical-align: middle;
}
.dropdown-menu {
transform: translate(-50%,-50%);
position: absolute;
display: none;
z-index: 1000;
float: left;
min-width: 0;
}
<!-- demo containers to center .btn-group please ignore this -->
<div class="d-flex align-items-center h-100">
<div class="container">
<div class="col-12 text-center">
<!-- question related code only -->
<div class="btn-group">
<button class="btn btn-primary btn-demo">
Long demo button title for testing
</button>
<div class="dropdown-menu"></div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
仅翻译版本
见下文 transform: translate()
唯一将下拉菜单中心定位在鼠标光标上的按钮内的版本。
这也是一个 jsfiddle:http://jsfiddle.net/joshmoto/2qLvp5a3/
// demo button click event
$('.btn-demo').on('click', function(e) {
// get the next element matching .dropdown-menu
var $dropdown_menu = $(this).next('.dropdown-menu');
// your custom button or add these however method you are doing
var btn_1 = '<button class="dropdown-item" type="button">Button 1</button>';
var btn_2 = '<button class="dropdown-item" type="button">Button 2</button>';
var btn_3 = '<button class="dropdown-item" type="button">Button 3</button>';
// add the desired buttons to the .dropdown-menu on click
$dropdown_menu.html(btn_1 + btn_2 + btn_3);
// show the dropdown menu so we can get its width height
// currently hidden using css opacity: 0;
$dropdown_menu.show();
// dropdown menu width height
var ddm_w = $dropdown_menu.outerWidth();
var ddm_h = $dropdown_menu.outerHeight();
// click position values inside button
var click_x = e.pageX - $(this).offset().left;
var click_y = e.pageY - $(this).offset().top;
// new translate positions for center menu
var trans_x = click_x - (ddm_w / 2);
var trans_y = click_y - (ddm_h / 2);
// add this css to .dropdown-menu menu on click
$dropdown_menu.css({
// translate position to top left corner of dropdown
'transform' : 'translate(' + trans_x + 'px,' + trans_y + 'px)',
// reveal the dropdown menu
'opacity' : 1
});
});
@import 'http://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css';
HTML,
BODY {
height: 100%;
min-height: 100%;
cursor: crosshair;
width: 100%;
}
BUTTON {
cursor: crosshair !important;
}
.btn-group {
position: relative;
display: inline-flex;
vertical-align: middle;
}
.dropdown-menu {
opacity: 0;
position: absolute;
top: 0;
left: 0;
display: block;
float: left;
min-width: 0;
margin: 0;
}
<!-- demo containers to center .btn-group please ignore this -->
<div class="d-flex align-items-center h-100">
<div class="container">
<div class="col-12 text-center">
<!-- question related code only -->
<div class="btn-group">
<button class="btn btn-primary btn-demo" type="button">
Long demo button title for testing
</button>
<div class="dropdown-menu">
</div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>