我怎样才能可靠地将焦点设置在我的 AngularStrap 工具提示中的元素上?

How can I reliably set focus on elements inside of my AngularStrap tooltip?

我的团队使用 AngularStrap 将 Bootstrap 模式(例如弹出窗口、工具提示等)集成到我们的 Angular 1.5 应用程序中。不幸的是,我发现很难可靠地将焦点设置在这些模态框内的元素上,因为 AngularStrap 显示它们的方式很奇怪。这个逻辑在这里:

https://github.com/mgcrea/angular-strap/blob/b13098d9d658da9408930b25f79182df920718d2/src/tooltip/tooltip.js

本质上,所有 AngularStrap 模态都以隐藏状态开始:

// Set the initial positioning.  Make the tooltip invisible
// so IE doesn't try to focus on it off screen.
tipElement.css({top: '-9999px', left: '-9999px', right: 'auto', display: 'block', visibility: 'hidden'});

然后它们会响应某些内部 Angular requestAnimationFrame 服务回调而变得可见:

$$rAF(function () {
  // Once the tooltip is placed and the animation starts, make the tooltip visible
  if (tipElement) tipElement.css({visibility: 'visible'});
  ...
});

不幸的是,这意味着在构建工具提示的所有 DOM 元素时,工具提示通常还不可见,并且对这些元素调用 focus() 的任何尝试都会失败。请注意,根据我的经验,这种情况会间歇性发生(对我来说大约占时间的 20%)。

我试过在工具提示上禁用动画,但在那种情况下跳过整个 hidden/visible 舞蹈似乎不够聪明。我显然可以尝试一些超级 hacky(例如,在尝试设置焦点之前使用任意超时),但我正在寻找更可靠的选择。

为什么不使用 onShow 事件?它的记录有点错误,但您可以附加一个将元素聚焦到 bs-on-show 的处理程序。此外,您可以使处理程序通用,寻找具有 focus-me 属性的元素并关注 :

<div bs-popover
  data-content='this input should be focused: <input type="text" focus-me>'
  data-placement="bottom"
  bs-on-show="setFocus"
  data-html="true">
    click me to show popover
</div>

<div bs-tooltip
  data-title='this input should be focused: <input type="text" focus-me style="color:#000;">'
  data-placement="bottom"
  data-trigger="click"
  bs-on-show="setFocus"
  data-html="true">
    click me to show tooltip
</div>   

通用处理程序

$scope.setFocus = function(e) {
  e.$element.find('[focus-me]').focus()    
} 

http://plnkr.co/edit/3wTinmNb5zsKnfUZQ9tT?p=preview