【问题标题】:Beginner questions with AngularJS and directives - wrapping a jQuery componentAngularJS 和指令的初学者问题 - 包装一个 jQuery 组件
【发布时间】:2013-03-21 00:46:30
【问题描述】:

首先,我应该提到我正在努力过渡到客户端编程。我对 js 很陌生。我以前的经验主要是 C 和一些汇编。几年前我还做了一些非常简单的 php,当时它还是 4.0。简而言之,对 javascript 来说是新手,但我有点想了解它。

我已经做了很多搜索和潜伏,但无法纠正我的问题。

我正在了解 AngularJS 的一些基础知识,它非常好,但是我很难理解指令的工作原理以及如何从自定义控件访问数据。

长话短说,我正在尝试使用 angularjs 为引导程序制作一个自定义控件,以便我可以在表单中正确使用它。

这里是控件:http://tarruda.github.com/bootstrap-datetimepicker/

我还有一些其他的控件想要工作,但我想如果我能完成这个,我可能会很容易地完成其他的。

这里是我目前拥有的基本框架的链接:http://jsfiddle.net/uwC9k/6/

首先,我想了解如何在模板正常工作后初始化控件(我认为此时我几乎是这样做的)

link: function(scope, element, attr) {
            attr.$observe('dpid', function(value) {
                if(value) {
              $('#' + scope.dpid).datetimepicker({
                  language: 'en',
                  pick12HourFormat: true
            });
}

当我把它放在链接指令中时,它什么也没做。我什至没有看到任何错误。 scope.dpid 确实显示了控件的 ID,所以我认为它会起作用。但是,唉,我对 javascript 的浅薄理解告诉我,我超出了范围或无法访问该元素的一些废话。

一旦开始,我也不确定如何让这些数据以表单的形式访问。

非常感谢任何帮助。

更新 有了基本的工作,现在我需要知道如何将数据从新控件获取到我的控制器中。这是更新的新 jsfiddle 的链接。 http://jsfiddle.net/tmZDY/1/

更新 2 我想我对如何使这些数据可访问有一个想法,但是我对 javascript 知识的缺乏让我再次感到厌烦。

当我创建对象时,我会这样做。

var elDatepicker = element.datetimepicker({
language : 'en',
pick12HourFormat : true,
});

但是,当我尝试使用这个对象时,它似乎没有得到正确的对象,或者我只是缺少一些基本知识。无论哪种方式,这肯定会让我感到愚蠢。

console.log(elDatepicker.getDate());

这个失败,getDate确实是一个方法,至少在插件的代码中看起来是这样的。

【问题讨论】:

  • 这不是一个论坛,它是一个问答网站,您应该分别提出每个问题。同样,如果您对自己的问题有答案,请将其作为答案发布,不要更新原始问题。

标签: jquery angularjs


【解决方案1】:

您可以find() 模板的第一个div,然后应用datetimepicker(),而不是隔离范围。因此,您的 HTML 中不需要 id

<datepicker model="mydate"></datepicker>
mydate = {{mydate}}

我也建议replace: true:

.directive('datepicker', function ($parse) {
    return {
        restrict: 'E',
        replace: true,
        template: '<div class=\"well\"><div class=\"input-append\">'
         + '<input data-format=\"MM/dd/yyyy HH:mm:ss PP\" type=\"text\"></input>'
         + '<span class=\"add-on\"><i data-time-icon=\"icon-time\" data-date-icon=\"icon-calendar\"></i></span>'
         + '</div></div>',
        link: function (scope, element, attr) {
            var picker = element.find('div').datetimepicker({
                language: 'en',
                pick12HourFormat: true
            });
            var model = $parse(attrs.model);
            picker.on('changeDate', function(e) {
               console.log(e.date.toString());
               console.log(e.localDate.toString());
               model.assign(scope, e.date.toString());
               scope.$apply();
           });
        }
    };
})

Fiddle

$parse 有点棘手。我展示的是它的主要用例:我们解析一个属性并返回一个函数,该函数上有一个 assign() 方法,允许我们更改范围属性。

【讨论】:

  • 太好了,这解决了第一个问题。现在我只需要弄清楚如何使用该字段中的内容更新控制器中的数据。用我正在尝试的内容更新了一个 jsfiddle。不太顺利!
  • @Patrick,我没用过那个插件。您需要将其配置为在值更改时调用函数......也许是 onSelect 选项或其他东西。然后使用回调函数中的新值更新范围属性。如果您通过 Angular 显示数据,您可能还需要调用 scope.$apply()。这个关于日期选择器的答案可能会有所帮助:stackoverflow.com/a/11880559/215945
  • 我明白了,非常感谢您的帮助。我真的很难访问 datetimepicker。我(想)我可以看到我需要用来获取值/日期的函数,但我似乎无法访问该对象。当我使用 element.getDate() 或任何其他原型时,它说该方法不存在。不完全确定如何访问它。更新了第一篇文章以显示更多代码。
  • @Patrick,我查看了文档,我们想要的是 changeDate 事件。查看我更新的答案和小提琴。
  • 太棒了,我想出了如何让它链接/更新模型,这正是我所需要的!非常感谢您的帮助,我学到了很多东西。 scope.$apply( function(){ ctrl.$setViewValue(e.localDate.toString()); });
【解决方案2】:

其中一种方法可能是这样,如this fiddle所示。 http://jsfiddle.net/uwC9k/10/

由于datepicker 元素必须替换为模板字符串,这将是使用编译功能的一个很好的用例。所以在编译函数中,我用模板字符串替换了datepicker 元素。

编译完成后,我们将进入链接函数,它只是从编译函数内部返回的函数。链接函数将使用

使用日期选择器功能初始化此 &lt;div class=\"input-append\"&gt; 元素
element.datetimepicker({
                      language: 'en',
                      pick12HourFormat: true
                });

由于您包含 jquery,因此链接函数中的元素属性是 jquery 扭曲元素。所以你可以直接调用datetimepicker方法。

【讨论】:

  • "由于必须将 datepicker 元素替换为模板字符串,这将是使用 compile 函数的一个很好的用例。" -- 这就是replace: true, template: ..., 自动为你做的事情。即,不需要编译功能。
【解决方案3】:

您可以将datetimepicker 之类的类添加到必须转换为日期时间选择器的 div 中,然后使用该类查找元素。

.directive('datepicker', function() {
    return {
        restrict: 'E',
        template: '<div class=\"well\"><div id={{dpid}} class=\"input-append datetimepicker\"><input data-format=\"MM/dd/yyyy HH:mm:ss PP\" type=\"text\"></input>    <span class=\"add-on\"><i data-time-icon=\"icon-time\" data-date-icon=\"icon-calendar\">      </i>    </span>  </div></div>',
        scope: { dpid: '@'},
        link: function(scope, element, attr) {
            attr.$observe('dpid', function(value) {
                if(value) {
              $(element).find('.datetimepicker').datetimepicker({
                  language: 'en',
                  pick12HourFormat: true
            });
                }
            });
        }
    };
})

演示:Fiddle

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-08-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-01-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多