Directive在AngularJS中的标签选择/页面滚动上不会触发 [英] Directive doesn't fire on tab selection/page scrolling in AngularJS

查看:136
本文介绍了Directive在AngularJS中的标签选择/页面滚动上不会触发的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想要做的是在真实图像完全加载之前显示占位符图像。我发现答案此处。我使用与接受的答案完全相同的代码。这个答案在正常情况下效果很好。



然而,我的情况有点不同。在我的页面上,我有两个选项卡。我使用 ion-slide-box 作为标签选择。当用户切换选项卡时,我加载了不同的内容。在每个标签下,这是一个很长的项目列表。每个项目都有一个图像,我在其上实现了这个占位符图像显示方法。用户可以向下滚动查看更多项目。所以当用户向下滚动时,我会加载更多的项目。



以下是我的代码,简化了它:

HTML:

 < div class =tab-bar> 
< div class =tab-optionng-class =(slide == 0?'active':'')ng-click =setSlide(0)>
Tab 1
< / div>
< div class =tab-optionng-class =(slide == 1?'active':'')ng-click =setSlide(1) >
标签2
< / div>

 <离子视图> 
< ion-content>
< div class =list>
< ion-slide-box on-slide-changed =slideHasChanged($ index)active-slide =slide>
< ion-slide>
< ion-list ng-repeat =item in items>
我的内容和图片在这里
< img hires ={{item.realImageUrl}}src =placeholderImage.jpg/>
< / ion-list>
< / ion-slide>
< ion-slide>
< ion-list ng-repeat =item in items>
我的内容和图片在这里
< img hires ={{item.realImageUrl}}src =placeholderImage.jpg/>
< / ion-list>
< / ion-slide>
< / ion-slide-box>
< / div>
< / ion-content>



在我的控制器中简化了很多,我不想打扰不相关的代码):

  slideHasChanged = function(index){
getMoreItems(); //从服务器获取更多数据。
};

这是指令:

  app.directive('hires',function(){
return {
restrict:'A',
scope:{hires:'@'},
link:function(scope,element,attrs){
console.log('link fired');
element.one('load',function(){
console .log('load fired');
element.attr('src',scope.hires);
});
}
};
}) ;

问题在于,占位符图像在我第一次访问此页面时运行良好,第一批物品。但是,无论何时我需要向下滚动或切换选项卡,占位符图像都不起作用。行为是,它总是显示占位符图像,真正的图像是完全下载/加载后不显示。



我不知道是否因为这种方法只适用于你加载页面?并不起作用,因为切换选项卡或向下滚动不会触发页面加载?如果我希望这适用于我的情况,这种方法需要什么变化?

我在我的指令中放置了两条调试消息,我注销了链接激活和'负载解雇'。事实证明,链接函数被正确触发,它只是 element.one('load',function())不会被触发。某种程度上不符合该范围吗?任何想法?



我一直在尝试很多代码。实际上,有时它可以工作,当我切换标签或向下滚动时。但大多数时间不起作用。这是令人困惑的,我不知道它为什么有时会起作用。

解决方案

所以我终于找到了正确的方法来做到这一点,只需将指令的链接函数更改为:

  link:function (scope,element,attrs){
if(scope.hires!= element.attr('src')){
element.attr('src',scope.hires);


$ / code $ / pre

删除元素。一个。这就是它只能使用一次的原因。


What I want to do is to display a placeholder image before the real image fully loaded. And I found the answer here. I am using exactly the same code as the accepted answer. This answer works pretty good for normal situation.

However, my case is a little bit different. On my page, I have two tabs. I'm using ion-slide-box for the tab selection. And I load different content when user switch the tabs. Under each tab, it's a long list of items. Each item has a image, on which I implement this placeholder image display method. User is able to scroll down to see more items. So when user scroll down, I'll load more items.

Here is a peek of my code, it's simplified:

HTML:

<div class="tab-bar">
<div class="tab-option" ng-class="(slide == 0 ? 'active' : '') ng-click="setSlide(0)">
    Tab 1
</div>
<div class="tab-option" ng-class="(slide == 1 ? 'active' : '') ng-click="setSlide(1)">
    Tab 2
</div>

<ion-view>
<ion-content>
    <div class="list">
        <ion-slide-box on-slide-changed="slideHasChanged($index)" active-slide="slide">
            <ion-slide>
                <ion-list ng-repeat="item in items">
                    My content and Image Here
                    <img hires="{{item.realImageUrl}}" src="placeholderImage.jpg"/>
                </ion-list>
            </ion-slide>
            <ion-slide>
                <ion-list ng-repeat="item in items">
                    My content and Image Here
                    <img hires="{{item.realImageUrl}}" src="placeholderImage.jpg"/>
                </ion-list>
            </ion-slide>
        </ion-slide-box>
    </div>
</ion-content>

In my controller(this is simplified a lot, I don't want to bother with un-related code):

slideHasChanged = function (index) {
    getMoreItems(); //get more data from server here.
};

This is the directive:

app.directive('hires', function() {
    return {
        restrict: 'A',
        scope: { hires: '@' },
        link: function(scope, element, attrs) {
            console.log('link fired');
            element.one('load', function() {
                console.log('load fired');
                element.attr('src', scope.hires);
            });
        }
     };
});

The issue is, the placeholder image works good for the first time I come to this page and load the first batch of items. But whenever I need to scroll down, or switch tab, the placeholder image doesn't work anymore. The behavior is that, it's always showing placeholder image, the real image is not displayed after it's fully downloaded/loaded.

I wonder is it because this method only works when you load a page? And doesn't work because switching tab or scrolling down doesn't trigger page loading? If I want this to work for my situation, what change is needed on this method?

I put two debugging messages in my directives, I log out 'link fired' and 'load fired'. Turns out that the link function is fired correctly, it's just the element.one('load', function()) is not fired. Is it that the scope somehow doesn't match? Any thoughts?

I've been trying the code a lot. And actually sometimes it works, when I switch tab or scroll down. But most time doesn't work. This is confusing, I don't know why it works sometimes.

解决方案

So I finally got the right way to do it, just change the link function of directive to this:

link: function (scope, element, attrs) {
    if (scope.hires != element.attr('src')) {
        element.attr('src', scope.hires);
    }
}

Get rid of element.one. That's the reason it only works once.

这篇关于Directive在AngularJS中的标签选择/页面滚动上不会触发的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆