根据弹出窗口相对于窗口边缘的 X 位置改变引导弹出窗口的位置?

我在互联网上搜索了很多地方,虽然我发现了这篇关于堆栈溢出的文章,很有见地,但是它仍然没有回答我的问题,可能是由于我对位置/偏移的理解有困难。

这就是我要做的。我希望 Twitter 引导弹出窗口的位置是正确的,除非热点弹出窗口将定位在视窗之外,然后我希望它被定位在左边。我正在制作一个 iPad 网络应用程序,它有热点,当你按下热点时,信息就会出现,但是当水平滚动被锁定时,我不希望它出现在视窗之外。

我觉得应该是这样的:

$('.infopoint').popover({
trigger:'hover',
animation: false,
placement: wheretoplace
});
function wheretoplace(){
var myLeft = $(this).offset.left;


if (myLeft<500) return 'left';
return 'right';
}

有什么想法吗,谢谢!

142417 次浏览

所以我想出了一个有效的方法。对于我的特殊项目,我正在构建一个 iPad 网站,这样我就能准确地知道到达屏幕边缘的像素 X/Y 值是多少。你的 this X 和 this Y 值会有所不同。

由于弹出窗口是通过内联样式放置的,所以我只需获取每个链接的左边和顶部值,以决定弹出窗口应该朝哪个方向放置。这是通过附加 html5数据-值来完成的。Popover ()在执行时使用。

if ($('.infopoint').length>0){
$('.infopoint').each(function(){
var thisX = $(this).css('left').replace('px','');
var thisY = $(this).css('top').replace('px','');
if (thisX > 515)
$(this).attr('data-placement','left');
if (thisX < 515)
$(this).attr('data-placement','right');
if (thisY > 480)
$(this).attr('data-placement','top');
if (thisY < 110)
$(this).attr('data-placement','bottom');
});
$('.infopoint').popover({
trigger:'hover',
animation: false,
html: true
});
}

欢迎任何评论/改进,但如果您愿意手动输入值,这就可以完成工作。

我只是注意到,位置选项可以是 绳子返回字符串的函数,每次单击弹出链接时都进行计算。

这使得复制没有初始 每个人函数的代码变得非常容易:

var options = {
placement: function (context, source) {
var position = $(source).position();


if (position.left > 515) {
return "left";
}


if (position.left < 515) {
return "right";
}


if (position.top < 110){
return "bottom";
}


return "top";
}
, trigger: "click"
};
$(".infopoint").popover(options);

根据文档,你应该能够结合使用 auto和首选的位置,例如 auto left

Http://getbootstrap.com/javascript/#popovers : “当指定“ auto”时,它将动态地重新定位 popover。例如,如果位置是“ auto left”,工具提示将尽可能向左显示,否则将向右显示

我尝试做同样的事情,然后意识到这个功能已经存在。

Bchhun 的回答让我找到了正确的方向,但是我想检查源和视窗边缘之间的实际可用空间。如果没有足够的空间,我还希望将 data-place 属性作为一个首选项来考虑,并提供适当的备份。这样的话,“ right”总是向右走,除非没有足够的空间让酥饼显示在右边。我就是这么处理的。对我来说很有用,但是感觉有点麻烦。如果任何人有任何更清晰、更简洁的解决方案的想法,我会很感兴趣地看到它。

var options = {
placement: function (context, source) {
var $win, $source, winWidth, popoverWidth, popoverHeight, offset, toRight, toLeft, placement, scrollTop;


$win = $(window);
$source = $(source);
placement = $source.attr('data-placement');
popoverWidth = 400;
popoverHeight = 110;
offset = $source.offset();


// Check for horizontal positioning and try to use it.
if (placement.match(/^right|left$/)) {
winWidth = $win.width();
toRight = winWidth - offset.left - source.offsetWidth;
toLeft = offset.left;


if (placement === 'left') {
if (toLeft > popoverWidth) {
return 'left';
}
else if (toRight > popoverWidth) {
return 'right';
}
}
else {
if (toRight > popoverWidth) {
return 'right';
}
else if (toLeft > popoverWidth) {
return 'left';
}
}
}


// Handle vertical positioning.
scrollTop = $win.scrollTop();
if (placement === 'bottom') {
if (($win.height() + scrollTop) - (offset.top + source.offsetHeight) > popoverHeight) {
return 'bottom';
}
return 'top';
}
else {
if (offset.top - scrollTop > popoverHeight) {
return 'top';
}
return 'bottom';
}
},
trigger: 'click'
};
$('.infopoint').popover(options);

对于引导程序3来说,有

placement: 'auto right'

这样更容易。默认情况下,它是右边的,但是如果该元素位于屏幕的右侧,则弹出窗口将是左边的。因此,它应该是:

$('.infopoint').popover({
trigger:'hover',
animation: false,
placement: 'auto right'
});

可以在数据布局中使用 auto,比如 data-place = “ auto left”。它将自动调整根据您的屏幕大小和默认位置将留下。

除了 bchhun 的伟大答案,如果你想要绝对定位,你可以这样做

var options = {
placement: function (context, source) {
setTimeout(function () {
$(context).css('top',(source.getBoundingClientRect().top+ 500) + 'px')
},0)
return "top";
},
trigger: "click"
};
$(".infopoint").popover(options);

我用 AngularJS 解决了这个问题:

var configPopOver = {
animation: 500,
container: 'body',
placement: function (context, source) {
var elBounding = source.getBoundingClientRect();
var pageWidth = angular.element('body')[0].clientWidth
var pageHeith = angular.element('body')[0].clientHeith


if (elBounding.left > (pageWidth*0.34) && elBounding.width < (pageWidth*0.67)) {
return "left";
}


if (elBounding.left < (pageWidth*0.34) && elBounding.width < (pageWidth*0.67)) {
return "right";
}


if (elBounding.top < 110){
return "bottom";
}


return "top";
},
html: true
};

此函数根据元素位置将 Bootstrap 弹出浮点的位置设置为最佳位置。

你也可以试试这个,

= = > 获取 viewport 中的目标/源位置
= = > 检查从底部开始的空间是否小于你的工具提示的高度
= = > 如果底部的空间小于工具提示的高度,那么就向上滚动页面

placement: function(context, source){
//get target/source position in viewport
var bounds = $(source)[0].getBoundingClientRect();
winHeight = $(window).height();


//check wheather space from bottom is less that your tooltip height
var rBottom = winHeight - bounds.bottom;


//Consider 180 == your Tooltip height
//if space from bottom is less that your tooltip height, this will scrolls page up
//We are keeping tooltip position is fixed(at bottom)


if (rBottom < 180){
$('html, body').animate({ scrollTop: $(document).scrollTop()+180 }, 'slow');
}


return "bottom";
}

你也可以尝试这一个,如果你需要它在几乎所有的地方在页面上。

您可以通过一般方式配置它,然后使用它。

这样你也可以使用 HTML 元素和任何你想要的:)

$(document).ready(function()
{
var options =
{
placement: function (context, source)
{
var position = $(source).position();
var content_width = 515;  //Can be found from a JS function for more dynamic output
var content_height = 110;  //Can be found from a JS function for more dynamic output


if (position.left > content_width)
{
return "left";
}


if (position.left < content_width)
{
return "right";
}


if (position.top < content_height)
{
return "bottom";
}


return "top";
}
, trigger: "hover"
, animation: "true"
, html:"true"
};
$('[data-toggle="popover"]').popover(options);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.0/jquery.min.js"></script>
<link href="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" rel="stylesheet"/>
<script src="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js"></script>




<div class="container">
<h3>Popover Example</h3>
<a id="try_ppover" href="#" data-toggle="popover" title="Popover HTML Header" data-content="<div class='jumbotron'>Some HTML content inside the popover</div>">Toggle popover</a>
</div>

加法


为了设置更多的选项,你可以选择 这里

甚至可以找到更多的 翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳翻译: 奇芳

更新


如果您希望在单击后弹出,您可以将 JS 选项更改为 trigger: "click",如下所示-

        return ..;
}
......
, trigger: "click"
......
};

你也可以定制它在 HTML 广告 data-trigger="click"喜欢这样-

<a id="try_ppover" href="#" data-toggle="popover" data-trigger="click" title="Popover Header" data-content="<div class='jumbotron'>Some content inside the popover</div>">Toggle popover</a>

我认为它将更加面向代码,更加可重用,对所有人都更有帮助:)。

$scope.popoverPostion = function(event){
$scope.pos = '';


if(event.x <= 207 && event.x >= 140){
$scope.pos = 'top';
event.x = '';
}
else if(event.x < 140){
$scope.pos = 'top-left';
event.x = '';
}
else if(event.x > 207){
$scope.pos = 'top-right';
event.x = '';
}


};

有一个简单的方法可以自动改变位置:

$element.popover("update")

以及更多的细节检查链接: https://mdbootstrap.com/docs/b4/jquery/javascript/popovers/