【问题标题】:jquery ui dialog fixed positioningjquery ui对话框固定定位
【发布时间】:2011-02-09 01:38:15
【问题描述】:

即使页面滚动,我也需要对话框保持其位置固定,所以我使用了 http://forum.jquery.com/topic/dialog-position-fixed-12-1-2010 的扩展名,但有两个问题:

  • 在 IE 和 Firefox 中页面滚动时会闪烁(在 Safari/Chrome 中很好)

  • 在关闭再重新打开时,它会失去粘性并随着页面滚动。

这是我用于创建对话框的代码:

$('<div id="'+divpm_id+'"><div id="inner_'+divpm_id+'"></div><textarea class="msgTxt" id="txt'+divpm_id+'" rows="2"></textarea></div>')
                .dialog({
                autoOpen: true,
                title: user_str,
                height: 200,
                stack: true,
                sticky: true //uses ui dialog extension to keep it fixed
     });

这是我用来重新打开它的代码:

jQuery('#'+divpm_id).parent().css('display','block');

建议/解决方案?

谢谢

【问题讨论】:

  • 如果您知道另一个 jquery 插件,用于保持固定且不闪烁的对话框,我也很感兴趣

标签: jquery-ui css jquery-ui-dialog


【解决方案1】:

我尝试了此处发布的一些解决方案,但如果在打开对话框之前已滚动页面,它们将不起作用。问题是它在计算位置时没有考虑滚动位置,因为在这个计算过程中位置是绝对的。

我找到的解决方案是在打开对话框之前将对话框的父级 CSS 设置为固定。

$('#my-dialog').parent().css({position:"fixed"}).end().dialog('open');

这假设您已经初始化了对话框并将 autoOpen 设置为 false。

注意,如果对话框可调整大小,这将不起作用。必须在禁用调整大小的情况下对其进行初始化,以使位置保持固定。

$('#my-dialog').dialog({ autoOpen: false, resizable: false });

对此进行了彻底的测试,目前没有发现任何错误。

【讨论】:

  • 我发现在 create 事件中运行这个逻辑会更好,这样你就可以在其他地方调用标准的 .dialog('open') ,而不必每次都运行这个 hack...@987654323 @
  • setting dialogClass: to a class with position:fixed 在 1.8.24 中工作,但从 1.9.0 开始,如果在打开之前向下滚动,它会离开屏幕
  • Scotts 答案适用于 jQuery-UI 1.11。只是对@Langdon 评论的一个小改进:使用$("selector").dialog("widget") 可以让您对 jQuery 对话框 DOM 结构的未来变化更加稳健。这样就变成了:$('#metadata').dialog({ create: function(event) { $(event.target).dialog("widget").css({ "position": "fixed" }); });
【解决方案2】:

我将一些建议的解决方案结合到以下代码中。 在 Chrome、FF 和 IE9 中滚动、移动和调整大小对我来说效果很好。

$(dlg).dialog({
    create: function(event, ui) {
        $(event.target).parent().css('position', 'fixed');
    },
    resizeStop: function(event, ui) {
        var position = [(Math.floor(ui.position.left) - $(window).scrollLeft()),
                         (Math.floor(ui.position.top) - $(window).scrollTop())];
        $(event.target).parent().css('position', 'fixed');
        $(dlg).dialog('option','position',position);
    }
});

更新:

如果您想将其设为所有对话框的默认值:

$.ui.dialog.prototype._oldinit = $.ui.dialog.prototype._init;
$.ui.dialog.prototype._init = function() {
    $(this.element).parent().css('position', 'fixed');
    $(this.element).dialog("option",{
        resizeStop: function(event,ui) {
            var position = [(Math.floor(ui.position.left) - $(window).scrollLeft()),
                            (Math.floor(ui.position.top) - $(window).scrollTop())];
            $(event.target).parent().css('position', 'fixed');
            // $(event.target).parent().dialog('option','position',position);
            // removed parent() according to hai's comment (I didn't test it)
            $(event.target).dialog('option','position',position);
            return true;
        }
    });
    this._oldinit();
};

【讨论】:

  • 这在我看来是最完整的解决方案,效果很好 - 谢谢。
  • 请删除更新部分中的.parent()$(event.target).parent().dialog('option','position',position);
  • 这让我省了很多苦头!谢谢!
  • 谢谢!!!!使用旧版本的 jquery UI (1.8.7)。刚刚为我节省了很多时间
  • 这很好用,只是在调整大小时框会消失。
【解决方案3】:

我无法得到 Scott 使用 jQuery UI 1.9.1 的答案。我的解决方案是在来自open 事件的回调中重新定位对话框。首先将css位置设置为固定。然后将对话框放置在您想要的位置:

$('selector').dialog({
    autoOpen: false,
    open: function(event, ui) {
        $(event.target).dialog('widget')
            .css({ position: 'fixed' })
            .position({ my: 'center', at: 'center', of: window });
    },
    resizable: false
});

注意:如另一个答案中所述,调整对话框大小将再次将其位置设置为 absolute,因此我禁用了 resizable

【讨论】:

    【解决方案4】:

    基于上面的Langdons's 评论,我尝试了以下方法,它适用于 jQuery-UI 1.10.0 和可调整大小的对话框:

    $('#metadata').dialog(
    {
        create: function (event) {
        $(event.target).parent().css('position', 'fixed'); 
        },
        resizeStart: function (event) {
        $(event.target).parent().css('position', 'fixed'); 
        },
        resizeStop: function (event) {
        $(event.target).parent().css('position', 'fixed'); 
        }
    });
    

    【讨论】:

    • 这是唯一可靠的方法
    【解决方案5】:

    尝试:

    $(document).ready(function() {
      $('#myDialog').dialog({dialogClass: "flora"});
      $('.flora.ui-dialog').css({position:"fixed"});
    )};
    

    (来自http://dev.jqueryui.com/ticket/2848

    【讨论】:

    • 假设您使用的是 jqueryui.com 的对话框
    • 如果用户在滚动后打开对话框,这将不起作用。问题在于 jQuery 的对话框计算相对于窗口滚动偏移量的对话框位置,而 position:fixed 不需要。当我弄清楚时我会发布更新(不分叉源)。
    • 嘿。只是用谷歌搜索了如何做到这一点并得到了我自己的答案!奇怪。
    • 刚刚发布了一个非常接近您的解决方案,但修复了我在之前评论中描述的错误。
    【解决方案6】:

    使用 CSS 将对话框的位置强制为 position:fixed

    $('.selector').dialog({ dialogClass: 'myPosition' });
    

    并将 myPosition css 类定义为:

    .myPosition {
        position: fixed;
    }
    

    【讨论】:

      【解决方案7】:
      $("#myDilog").dialog({
          create:function(){
              $(this).parent().css({position:"fixed"});
          }
      });
      

      【讨论】:

      • 虽然这段代码 sn-p 可以解决问题,including an explanation 确实有助于提高您的帖子质量。请记住,您是在为将来的读者回答问题,而这些人可能不知道您提出代码建议的原因。
      【解决方案8】:
       $('#myDialog').dialog({ dialogClass: "flora" });
              $('.flora.ui-dialog').css({ top: "8px" });
      

      无论我们点击了什么,这都会使对话框保持在顶部。

      【讨论】:

        【解决方案9】:
        $('#'+tweetidstack.pop()).dialog("open").parent().css({position:"fixed"});
        

        为什么要使用 $(document).ready ?这可能是最近的发展,但现在可以正常工作。

        【讨论】:

        • 通过这样做,您可以在每次打开对话框时设置 css 属性。如果您将其设置为文档就绪,则设置一次即可用于所有未来的打开。
        【解决方案10】:
        $( ".ui-dialog" ).css("position","fixed");  
        
        $( ".ui-dialog" ).css("top","10px");
        

        将此代码放在对话框的打开功能上

        【讨论】:

          【解决方案11】:

          首先,创建您的对话框。像这样的:

          $("#dialog_id").dialog({
                          autoOpen : false,
                          modal : true,
                          width: "auto",
                          resizable: false,
                          show: 'fade',
                          hide: { effect:"drop",duration:400,direction:"up" },
                          position: top,
                          height: 'auto',
                          title: "My awesome dialog",
                          resizeStart: function(event, ui) {
                              positionDialog();
                          },
                          resizeStop: function(event, ui) {
                              positionDialog();
                          }
                      });
                      $("#dialog_id").dialog('open');
          

          然后让它自动居中:

              function positionDialog (){
                  setInterval(function(){
                      if($("#dialog_id").dialog( "isOpen" )){
                          $("#dialog_id").dialog('option','position',$("#dialog_id").dialog( "option", "position" ));
                      }
                  },500);
              }
          //setInterval is for make it change position "smoothly"
          //You can take it off and leave just the if clausule and its content inside the function positionDialog.
          

          【讨论】:

            【解决方案12】:

            解决方案实际上非常简单。我不知道在问这个问题时这是否适用,但现在仍然适用。

            //First a container/parent-div with fixed position is needed
            var dialogContainer=document.body.appendChild(document.createElement("div"));
            dialogContainer.style.position="fixed";
            dialogContainer.style.top=dialogContainer.style.left="50%";//helps centering the window
            

             

            //Now whenever a dialog is to be created do it something like this:
            $(myDialogContent).dialog({
                appendTo: dialogContainer,
                position: { 
                    at: 'center center',
                    of: dialogContainer
                }
            });
            

            关于“appendTo”:http://api.jqueryui.com/dialog/#option-appendTo
            关于“职位”:http://api.jqueryui.com/position/

            【讨论】:

              【解决方案13】:

              虽然与上面的其他一些答案类似,但我发现我必须做的不仅仅是position: fix 对话框,但我还必须position: static 将其内容保持在对话框中。

              $('<div id="myDialog" class="myClass">myContent</div>')
                      .dialog(dialogOptions)
                      .parent()
                      .css({ position: 'fixed' })
                      .end()
                      .position({ my: 'center', at: 'center', of: window })
                      .css({ position: 'static' });
              

              之后,我可以随时致电.dialog('open'),它会简单地出现在我离开的地方。实际上,我在一个函数中有这个,它将返回现有对话框或根据需要创建一个新对话框,然后我只需在调用 .dialog('open') 之前更改对话框的值。

              【讨论】:

                【解决方案14】:

                正如我在博客中所写的那样https://xbrowser.altervista.org/informatica-portata/jquery-easyui-bug-fix-window-dialog-position-widget/ 我在“window”元素或“dialog”元素中发现了一个错误。 当您实例化此小部件时,它会离开主窗口浏览器,特别是在顶部和左侧位置(当您拖动或调整它的大小时)。 为了解决这个问题,我实现了这个解决方案。

                您可以阅读下面的源代码:

                $(dialog).window({
                   onMove: function(left, top) {
                   if (left < 0 || top < 0) {
                     left = (left < 0) ? 0 : left;
                     top = (top < 0) ? 0 : top;
                     $(this).window('move', {left: left, top: top});
                   }
                },
                onResize: function(width, height) {
                  var opt = $(this).window("options");
                  var top = opt.top;
                  var left = opt.left;
                  if (top < 0) {
                    top = (top < 0) ? 0 : top;
                    $(this).window('move', {left: left, top: top});
                  }
                }
                }).window("open");
                
                The same code is for dialog:
                
                $(dialog).dialog({
                  onMove: function(left, top) {
                  if (left < 0 || top < 0) {
                     left = (left < 0) ? 0 : left;
                     top = (top < 0) ? 0 : top;
                     $(this).dialog('move', {left: left, top: top});
                  }
                },
                onResize: function(width, height) {
                   var opt = $(this).window("options");
                   var top = opt.top;
                   var left = opt.left;
                   if (top < 0) {
                     top = (top < 0) ? 0 : top;
                     $(this).dialog('move', {left: left, top: top});
                   }
                }
                }).dialog("open");
                

                此外,当您在“onResize”方法中调用“$(this).window(“options”);”并启动您的应用程序时, 你看不到窗户;所以我必须插入“.window(“open”);”在对话框的声明处。

                希望能帮到你。

                【讨论】:

                  【解决方案15】:

                  我发现这些答案对我不起作用,但将其中一些答案结合起来确实有效。 我使用 create 函数将对话框设置为固定,因此在创建对话框时它不会向下滚动窗口。

                  create: function (event) { 
                          $(event.target).parent().css('position', 'fixed')
                      }
                  

                  我还使用 open 函数通过更改顶部值来确保对话框不会从屏幕上消失。

                  open: function(event, ui) {
                          $(event.target).parent().css('top', '30%')
                      }
                  

                  这适用于自动打开和调整大小。

                  【讨论】:

                    猜你喜欢
                    • 1970-01-01
                    • 2011-12-22
                    • 1970-01-01
                    • 1970-01-01
                    • 2010-10-31
                    • 1970-01-01
                    • 2017-11-16
                    • 1970-01-01
                    • 2011-01-05
                    相关资源
                    最近更新 更多