我在组件的列表中显示了一系列项目。该项目的一个属性是描述字段,其范围可以从一个单词到几个句子长。
当描述太长时,我想截断它并显示一个按钮,在单击时显示全文。截断和显示按钮的条件是基于此函数返回布尔值:
checkOverflow(element) {
if (element.offsetHeight < element.scrollHeight ||
element.offsetWidth < element.scrollWidth) {
return true;
} else {
return false;
}
}
然后我从组件的模板端使用这个函数(这是ngFor的一小部分):
<p #refDescription
class="item-description--max-height"
[class.fade--read-more]="checkOverflow(refDescription)">
{{item.description}}
</p>
<button class="button button--read-more" *ngIf="checkOverflow(refDescription">Read more</button>
这里使用的CSS很简单:
.item-description--max-height {
font-size: 20px;
@include font-fira-sans-italic;
line-height: 28px;
margin-bottom: 0;
max-height: 2.9em;
overflow: hidden;
}
.fade--read-more {
height: 2.9em; /* exactly two lines */
}
目前行为非常突然,我在控制台中出错:
ExpressionChangedAfterItHasBeenCheckedError:表达式在检查后发生了变化。上一个值:'ngIf:false'。当前值:'ngIf:true'。
我相信我在错误的轨道上将类绑定到函数 - 任何建议都非常感激。我使用的是Angular版本7。
谢谢。
通常这种错误是由模板内部调用的方法引起的。
尝试将checkOverflow()调用移动到组件中:
// use view children to get references to dom elements
@ViewChildren('refDescription') descRef: QueryList<ElementRef>;
ngAfterViewInit(): void {
// wait when dom rendered
setTimeout(() => {
// get dom elements
const elements = this.descRef.toArray().map(i => i.nativeElement);
// check overflow and put result into 'overflow' property
elements.forEach((el, index) => {
this.items[index]['overflow'] = this.isOverflow(el);
});
});
}
相应地更新模板:
<p #refDescription
class="item-description--max-height"
[class.fade--read-more]="item.overflow">
{{item.description}}
</p>
<button class="button button--read-more" *ngIf="item.overflow">Read more</button>