6

我正在使用angularJSrequirejsviaangularAMD来连接一个复杂的应用程序。

我的一个州有两个简单的观点,如下所示:

  $stateProvider
    .state("common", {
      url: "/",
      views: {
        "view1": {
          templateUrl: "view1.tpl.html"
          },
        "view2": {
          templateUrl: "view2.tpl.html"
        }
      }
    });

html

<div ui-view="view1"></div>
<div ui-view="view2"></div>

View1有一个指令:

  .directive('checkViewOneBoxWidth', function ($timeout) {
    return {
      restrict: 'A',
      link: function (scope, elem, attrs) {
        var linkFunctionAfterDomComplete = function () {
          console.log(elem[0].scrollWidth);
        }
        $timeout(linkFunctionAfterDomComplete, 0);
      }
    }
  })

并且view2有一个样式表,可以对页面应用一些样式,包括更改容器的height和。widthview1

我希望函数在 DOM 被样式表修改linkFunctionAfterDomComplete计算元素heightwidth属性,所以我将函数包装在.view2linkFunctionAfterDomComplete$timeout()

console.logfrom here 是在checkViewOneBoxWidth样式表中的样式view2修改此元素的大小之前报告此元素的大小,尽管我们希望在应用样式之后$timeout导致linkFunctionAfterDomComplete函数计算此元素的大小view2DOM 已完成。

在完全渲染并应用所有样式后,如何linkFunctionAfterDomComplete计算反映元素真实状态的元素属性?

http://plnkr.co/edit/WjGogh?p=preview

4

1 回答 1

4

您需要将函数传递给$timeout

$timeout(function() {
  console.log('timeout: view 1 linked')
}, 0);

或者:

var fn = function () {
  console.log('timeout: view 1 linked');
};

$timeout(fn, 0);

以下:

$timeout(console.log('timeout: view 1 linked'), 0);

console.log立即执行,然后将返回值 ( undefined) 作为第一个参数传递给$timeout.

演示: http ://plnkr.co/edit/zWgoJihcMH693fWfUp09?p=preview

不确定您在实际应用程序中是否有同样的问题,但我认为无论如何我都应该发布这个。


基于编辑的新答案

问题是您的链接元素位于视图模板中,而不是 index.html 中。

如果将其移至 index.html ,它将按预期工作(在这种情况下您不需要$timeout,除非您的真实应用程序从指令中添加自定义 HTML):

演示: http ://plnkr.co/edit/m3sriF2YYH5T8y42R5Lr?p=preview

如果您将链接保留在视图模板中并保留超时,则基本上会发生以下情况:

  1. Angular 将运行它的编译函数来准备所有的绑定和视图。
  2. 来自视图的 HTML 将被插入到 DOM 中,指令将被执行并且console.log将被添加到超时队列中。
  3. 链接元素现在已插入 DOM,浏览器将开始检索 CSS。超时队列中的console.log将执行。

请注意,CSS 的获取是异步的,并且console.log来自超时队列的将在 CSS 的获取和解析完成之前执行。

另请注意,您可能会在不同的浏览器中看到不同的行为。

有解决方案,但它可能会变得非常混乱。

要了解更多信息:

什么时候真正加载样式表?

我建议将链接移至 index.html。

于 2015-11-10T10:26:27.247 回答