【问题标题】:inserting tag thru interpolation通过插值插入标签
【发布时间】:2020-07-20 19:12:52
【问题描述】:

我想显示一个由句子组成的大文本,它是合理的,并且在特定位置有换行符。这些换行符当然与句子的结束位置无关。一个句子可以从一行的中间开始,并继续到下一行。

我有一个 sentences.json 文件,其中包含有关全文的文本片段(“句子”)的信息

让我们说:

[
  {
  "line":1,
  "text": "Hello<br>",
  "time": "00:10"
  },
  {
  "line":2,
  "text": "How are you?",
  "time": "00:25"
  },
  {
  "line":3,
  "text": "Great and <br> you?",
  "time": "01:10"
  },
...]

这是通过

导入到sentence.component.ts
import * as data from '../sentences.json';
...
export class SentenceComponent implements OnInit {
  sentences: any = (data as any).default;

我想将每个句子显示为 a,以便在悬停时更改背景颜色。这样当点击时,我可以根据句子的“时间”字段播放来自特定位置的音频。

所以在 sentence.component.html 我做

<span *ngFor="let sentence of sentences"
  [id]="sentence.line"
  [ngStyle]="hoveredID === sentence.line ? hoveredStyle : normalStyle"
  (mouseover) = "showHovered(sentence.line)"
  (mouseout) = "showNormal()"
  (click)="play(sentence.time)">
      {{sentence.text}}
</span>

根据 Aurelien Giraud 对 ["How can I add a class to an element on hover?"] (How can I add a class to an element on hover?) 的回答 ["How can I add a class to an element on hover?"] (How can I add a class to an element on hover?) by Aurelien Giraud]

现在,所有跨度都在一个 div 中,因为在 app.component.html 我有

<div>
    <app-sentence></app-sentence>
</div>

并且 div 有样式(在 app.component.css 中设置) text-align: justify;

一些“句子”应该在其中有一个换行符,因为它们从一行中间开始并在下一行继续。 我尝试将&lt;br&gt; 作为“文本”的一部分并没有帮助。因为当我使用{{sentence.text}}在span里面输入文字时,并没有生成&lt;br&gt;标签,只是在句子中间显示文字"&lt;br&gt;"。 任何想法如何做到这一点? 当点击某个句子时,从特定时间播放音频/视频文件最简单的方法是什么?

【问题讨论】:

    标签: json angular


    【解决方案1】:

    我不推荐这种方法,因为它绕过了 Angular 内置的安全性。您会注意到链接中的第一部分是“安全风险”。在以这种方式呈现内容之前,您应该确保您绝对信任内容。

    如果您将 HTML 作为要呈现的字符串的一部分,则需要使用 DomSanitizer

    export class SentenceComponent {
    
        sentences: any = (data as any).default;
        unsafeSentences: string[] = [];
    
        constructor(private sanitizer: DomSanitizer){}
    
        ngOnInit() {
           sentences.forEach(sentence => {               
               this.unsafeSentences.push(
                   sanitizer.bypassSecurityTrustHtml(sentence)
               );
           });
        }
    }
    

    那么你可以使用innerHTML来设置内容:

    <span *ngFor="let sentence of unsafeSentences"
      [id]="sentence.line"
      [ngStyle]="hoveredID === sentence.line ? hoveredStyle : normalStyle"
      (mouseover) = "showHovered(sentence.line)"
      (mouseout) = "showNormal()"
      (click)="play(sentence.time)"
      [innerHTML]="sentence">
    </span>
    

    【讨论】:

    • 感谢两位的回答。他们做这项工作。但我注意到我插入&lt;br&gt; 标签并没有做我希望它会做的事情,即模拟 Word 上的“shift-Enter”,这迫使该行证明
    • 我遇到了一个“问题”:'SafeHtml' 类型的参数不能分配给'string'.ts(2345) 类型的参数 无论如何,string要传递给 HTML 的应该是 sentence.text 因此我将代码编辑为:ngOnInit(): void { this.sentences.forEach((sentence: any) =&gt; {this.unsafeSentences.push(this.sanitizer.bypassSecurityTrustHtml(sentence).toString()); });} 但这仍然不够,即使它有效,但它没有,因为 unsafeSentences 只会包含 "text" 的值,并且我无法再访问 "line""time"
    【解决方案2】:

    您需要做的就是使用innerHTML 属性绑定

    只需用这个替换您的代码

    <span *ngFor="let sentence of sentences"
      [id]="sentence.line"
      [ngStyle]="hoveredID === sentence.line ? hoveredStyle : normalStyle"
      (mouseover) = "showHovered(sentence.line)"
      (mouseout) = "showNormal()"
      (click)="play(sentence.time)"
      [innerHTML]="sentence.text">
    </span>
    

    那你就可以走了!

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-07-13
      • 2017-07-12
      • 1970-01-01
      • 1970-01-01
      • 2019-04-20
      相关资源
      最近更新 更多