tinymce Angular 2 集成:如何设置编辑器的内容?

Tinymce Angular 2 integration : how to set the content of the editor?

我将 TinyMCE 集成到我的 angular 2 应用程序中,它运行良好。 现在我想传递一个@Input 属性 以便可以设置编辑器的默认内容。

有什么想法吗?

你必须为此实现一个包装器,或者尝试现有的包装器 https://github.com/zackarychapple/ng2-tinymce-wyswig
https://github.com/luigiinred/ng2-tinymce

或者我知道这肯定有效:https://github.com/chymz/ng2-ckeditor

假设您正在实施 @Directive,如 TinyMCE official documentation 中所述:

添加一个额外的 @Input 参数:

@Input() initialContent: String;

ngAfterViewInit() 您必须将 tinymce.init({}) 具有编辑器配置和运行时选项的对象。您还必须在其中添加一个新函数:

        init_instance_callback: (editor: any) => {
            editor && this.initialContent && this.editor.setContent(this.initialContent)
        },

最后,当您调用指令时,您必须添加一个新属性,其名称与您在 @Input 参数中使用的名称与您在指令定义中使用的名称相同。

<textarea class="form-control" id="wysiwygText" name="body" rows="3" [htmlEditor] initialContent="{{model.body}}" [(ngModel)]="model.body" #body="ngModel" (onEditorKeyup)="keyupHandlerFunction($event)"></textarea>

此实现基于 this article

的评论

我遇到了同样的问题并实施了@nicofx 的回答。但是,当通过异步 http 调用设置内容时,这并没有起到作用。

对于遇到同样问题的人:您可以使用事件发射器,它会在 http 调用完成时更新内容:

定义一个输入:

@Input() contentEvent: EventEmitter<string>;

如果通过则订阅事件发射器:

ngAfterViewInit() {
    tinymce.init({
        selector: '#' + this.elementId,
        plugins: ['link', 'paste', 'table'],
        skin_url: '/assets/skins/lightgray',
        setup: editor => {
            this.editor = editor;

            if (this.contentEvent) {
                this.contentEvent.subscribe(c => {
                    this.setContent(editor, c);
                });
            }
        }
    });
}

以及 setcontent 函数:

private setContent(editor, content) {
    if (editor && content) {
        this.editor.setContent(content);
    }
}

你也可以做得简单一点。 只需在使用 tinyMCE 组件的视图中添加 @Input 文本:

<tinymce-editor 
  [desiredInitialText]="text" 
  (onEditorKeyup)="editorChangesHandler($event)">
</tinymce-editor>

然后在你的 Tinymce 组件中添加

@Input() desiredInitialText: string //Or any other special typing

...

ngOnChanges() {
  if (this.editor) {
    if (this.desiredInitialText && this.desiredInitialText.length > 0) {
      this.editor.setContent(this.desiredInitialText)
    } else {
      this.editor.setContent('');
    }
  }
}

这可能会有帮助

import { Component, AfterViewInit, OnDestroy, Input, Output, EventEmitter, ElementRef, provide, forwardRef, View } from 'angular2/core';
import { RdComponent, RdLib } from '../../../../../node_modules/mulberry/core';

declare let tinymce: any;

@Component({
  selector: 'aril-mail-template',
  template: `<textarea style="height:15em"><p>{{model}}</p></textarea>`
})

export class MailTemplatesComponent extends RdComponent {

  @Input("rd-model") model;
  @Input("rd-default") default;
  @Input("rd-required") required;
  @Output("mail-template-save") mailTemplateSave: EventEmitter<any> = new EventEmitter<any>();

  editor;

  ngOnInit() {
    let that = this;
    tinymce.init({
      selector: 'textarea',
      height: "25em",
      menubar: true,
      plugins: [
        'advlist autolink lists link image charmap print preview anchor',
        'searchreplace visualblocks code fullscreen hr',
        'insertdatetime media table contextmenu paste spellchecker',
        'wordcount'
      ],
      toolbar: 'styleselect | bold italic | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | link image spellchecker code',
      table_toolbar: "tableprops cellprops tabledelete | tableinsertrowbefore tableinsertrowafter tabledeleterow | tableinsertcolbefore tableinsertcolafter tabledeletecol",
      powerpaste_allow_local_images: true,
      powerpaste_word_import: 'prompt',
      powerpaste_html_import: 'prompt',
      spellchecker_language: 'en',
      spellchecker_dialog: true,
      content_css: [
        '//fonts.googleapis.com/css?family=Lato:300,300i,400,400i',
        '//www.tinymce.com/css/codepen.min.css'],

        setup: editor => {
          this.editor = editor;
          editor.on('init', () => {
            this.model && this.editor.setContent(this.model, {format: 'raw'});
          });
          editor.on('change', () => {
            const content = editor.getContent();
            this.mailTemplateSave.emit(content);
          });
        }

    });    
  }


  ngOnDestroy() {
    tinymce.remove(this.editor);
  }

}
 <rd-service-provider #saveMailTemplateProvider [rd-service-proxy]="serviceProxy" (rd-success)="toastr.info(translate('Mail Şablonu Başarıyla Oluşturuldu.'));close()"></rd-service-provider>
 
 
 <aril-mail-template [(rd-model)]="data.MailContent" (mail-template-save)="mailContent = $event" [rd-required]="true"></aril-mail-template>
 
<rd-footer>
        <rd-submit [rd-text]="translate('Save')" rd-size="medium" (rd-          click)="saveMailTemplateProvider.call(saveMailTemplates($event, mailContent))"></rd-submit>
</rd-footer>

import {
    Component,
    OnInit
} from '@angular/core';
import {
    FormBuilder,
    FormControl,
    FormGroup
} from '@angular/forms';

@Component({
    selector: 'my-app',
    templateUrl: './app.component.html',
    styleUrls: ['./app.component.css']
})

export class AppComponent {

    editorForm: FormGroup;
    tinymceInit: any = {};

    constructor(private fb: FormBuilder) {


        this.tinymceInit = {
            content_css: 'assets/skins/ui/oxide/content.min.css',

            base_url: '/tinymce',
            plugins: [
                'advlist autolink lists link image charmap print preview hr anchor pagebreak',
                'searchreplace wordcount visualblocks visualchars code fullscreen',
                'insertdatetime media nonbreaking save table contextmenu directionality',
                'emoticons template paste textcolor colorpicker textpattern code'
            ],
            toolbar1: 'insertfile undo redo | styleselect | bold italic | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | link image',
            toolbar2: 'print preview media | forecolor backcolor emoticons',
            image_advtab: true,
            paste_data_images: true,
            automatic_uploads: true,
            file_picker_types: 'image',
            file_picker_callback(cb, value, meta) {
                if (meta.filetype == 'image') {
                    const input: any = document.createElement('input');
                    input.setAttribute('type', 'file');
                    input.setAttribute('accept', 'image/*');
                    input.click();
                    input.onchange = function() {
                        const file = input.files[0];
                        const reader = new FileReader();
                        reader.onload = function(e: any) {
                            cb(e.target.result, {
                                alt: file.name
                            });
                        };
                        reader.readAsDataURL(file);
                    };
                    input.remove();
                }
            }
        };
    }
    ngOnInit() {
        this.editorForm = this.fb.group({
            'tinyMice': ''
        })
    }

    name = 'Angular';

    imageFilePicker(callback, value, meta) {
        if (meta.filetype == 'image') {
            console.log(value, meta)
        }
    }
}