Bootstrap/TinyMCE

7 posts by 3 authors in: Forums > CMS Builder
Last Post: April 16   (RSS)

By glennp - March 22

Hello,

I was wondering if there is any info about integrating Bootstrap features grid with TinyMCE.

Thanks!

Glenn

By glennp - March 22

Hi Dave,

Thanks for the reply!

Am I correct that the current version of CMSB uses TinyMCE 4? If so, I think I'd need to upgrade that first.

Glenn

By kitsguru - March 23

I use bootstrap 5.3+ with TinyMCE by using a wysiwyg_custom.php. I have used bootstrap from 3 to 5 over the years upgrading as needed.

Here is a snippet from that you can modify as required. I build a separate editor.css file from bootstrap that only has the classes I want to use in the editor.

      // add file modified time on end of url so updated files won't be cached by the browser
      // reference: https://www.tinymce.com/docs/configure/content-appearance/#content_css

      content_css: "$wysiwygCssUrl, /css/editor.min.css",

      content_css_cors: true,

      importcss_groups: [
        {title: 'Fonts Classes', filter: /\.h\d+|\.fs|\.display-|\.fw/}, // regex
        {title: 'Text Classes', filter: /\.lead|\.small|\.mark|\.text-|\.lh/}, // regex
        {title: 'Background Color', filter: /\.bg-/}, // regex
        {title: 'Buttons', filter: /\.btn/}, // regex
        {title: 'Cards', filter: /\.card/}, // regex
        {title: 'Columns', filter: /\.col|\.row|\.offset/}, // regex
        {title: 'Lists', filter: /\.list/}, // regex
        {title: 'Spacing', filter: /\.gap|\.g-|\.gx-|\.gy-|\.m-|\.mx-|\.my-|\.ms-|\.me-|\.mt-|\.mb-|\.p-|\.px-|\.py-|\.py-|\.ps-|\.pe-|\.pt-|\.pb-/}, // regex
        {title: 'Tables', filter: /\.table/}, // .class
        {title: 'Special Classes', filter: /\.dropcap|\.island|\.blockquote/},
        {title: 'Remaining classes', filter: /\./}, // .class
        {title: 'Other styles'}, // The rest
      ],

      importcss_append: true,
      importcss_merge_classes: true,
      importcss_exclusive: true,

// bootstrap template for a simple card
      templates: [
        {title: 'Simple Card', description: 'Simple Card template', content: '<div class="card"> \
        <div class="card-body"> <img src="..." class="card-img-top" alt="no image specified"> \
        <h5 class="card-title">Card title</h5> \
        <p class="card-text">Some quick example text to build on the card title and make up the bulk of the card content.</p> \
        <a href="#" class="btn btn-primary">Go somewhere</a> \
        </div> \
        </div>'},

// bootstrap template for a 2 card
        {title: '2 Cards', description: '2 Card template side by side', content: '<div class="row"> \
        <div class="col-sm-6"> \
          <div class="card"> \
            <div class="card-body"> \
              <h5 class="card-title">Special title treatment</h5> \
              <p class="card-text">With supporting text below as a natural lead-in to additional content.</p> \
              <a href="#" class="btn btn-primary">Go somewhere</a> \
              </div> \
            </div> \
          </div> \
          <div class="col-sm-6"> \
            <div class="card"> \
              <div class="card-body"> \
                <h5 class="card-title">Special title treatment</h5> \
                <p class="card-text">With supporting text below as a natural lead-in to additional content.</p> \
                <a href="#" class="btn btn-primary">Go somewhere</a> \
              </div> \
            </div> \
          </div> \
        </div>'},
],
Jeff Shields

By glennp - April 16

Thanks, Jeff!

I think I'm missing something because I'm not getting the card template to appear. I've gotten a previous post of yours (https://www.interactivetools.com/forum/forum-posts.php?postNum=2240125#post2240125) to work.

The site I'm working on uses Bootstrap 4. Is there any chance you have complete working files with your example?

Glenn

By kitsguru - April 16

The snippet above was lacking the included plugins and toolbar entries for the templates to work.

For the current version of TinyMCE that ships with CMSB 3.67, here is the entire JS code I use for Bootstrap 5.3.2:

<script>
  document.addEventListener('DOMContentLoaded', () => {
    tinyMCE.init({
      mode: "exact",
      theme: "modern",
      branding: false,
      language: "{$SETTINGS['wysiwyg']['wysiwygLang']}",
      language_url: '$languageUrl',

      // Menubar: set to true to display the menus on top of the editor buttons. To configure the menu items, see: https://www.tinymce.com/docs/configure/editor-appearance/#menu
      menubar: false,
      // menubar: 'edit insert view table tools help',
      // menu: {
      //   edit: { title: 'Edit', items: 'undo redo | cut copy paste | selectall | searchreplace' },
      //   view: { title: 'View', items: 'code | visualaid visualchars visualblocks | preview fullscreen' },
      //   insert: { title: 'Insert', items: 'image link media template codesample inserttable | charmap emoticons hr | pagebreak nonbreaking anchor toc | insertdatetime' },
      //   tools: { title: 'Tools', items: 'wordcount code' },
      //   table: { title: 'Table', items: 'inserttable | cell row column | tableprops deletetable' },
      //   help: { title: 'Help', items: 'help' }
      // },

      // Define toolbar buttons. See list of toolbar buttons here: https://www.tinymce.com/docs/advanced/editor-control-identifiers/#toolbarcontrols
      // formatselect
      toolbar1: "undo redo | styleselect visualblocks | bold italic underline strikethrough | alignleft aligncenter alignright | bullist numlist | outdent indent | superscript subscript charmap emoticons ",

      toolbar2: "link unlink | blockquote hr image media table codesample | pastetext paste | | removeformat searchreplace fullscreen | template  | code | wordcount",
      toolbar3: '',

      indentation : '2rem',
      // block_formats: 'Paragraph=p;Header 2=h2;Header 3=h3;Header 4=h4;Header 5=h5;Header 6=h6;Div=div;Figure=figure;Section=section',
      formats: {
          alignleft: {selector: 'p,figure,h1,h2,h3,h4,h5,h6,td,th,div,ul,ol,li,table,img', classes: 'text-start'},
          aligncenter: {selector: 'p,figure,h1,h2,h3,h4,h5,h6,td,th,div,ul,ol,li,table,img', classes: 'text-center'},
          alignright: {selector: 'p,figure,h1,h2,h3,h4,h5,h6,td,th,div,ul,ol,li,table,img', classes: 'text-end'},
          // alignjustify: {selector: 'p,figure,h1,h2,h3,h4,h5,h6,td,th,div,ul,ol,li,table,img', classes: 'text-justify'},
          blockquote: {block: 'blockquote', classes: 'blockquote', wrapper: true },


          removeformat: [
          {
              selector: 'p,h1,h2,h3,h4,h5,h6',
              remove: 'all',
              split: true,
              expand: false,
              block_expand: true,
              deep: true
            },
            {selector: 'b,strong,em,i,font,u,strike', remove : 'all', split : true, expand : false, block_expand: true, deep : true},
            {selector: 'span', attributes : ['style', 'class'], remove : 'empty', split : true, expand : false, deep : true},
            {selector: '*', attributes : ['style', 'class'], split : false, expand : true, deep : true}
          ],
      },
      // Add custom style formats which will be rendered as list options in the 'Formats' dropdown
      // IMPORTANT: you need to add 'styleselect' toolbar button above to enable the 'Formats' dropdown
      // Selecting a 'style format' from the 'Formats' dropdown list options will add a 'class', ie 'exampleClass'
      // ... and the corresponding CSS style of that class (see /cmsb/lib/wysiwyg.css) to the selected text or HTML element in the WYSIWYG editor
      // reference: https://www.tinymce.com/docs/configure/content-formatting/#style_formats
      style_formats: [

          { title: 'Block Elements', items: [
            { title: 'paragraph', block: 'p' },
            { title: 'lead para', block: 'p', classes: 'lead' , wrapper: false, merge_siblings: false },
            { title: 'header 2', block: 'h2' },
            { title: 'header 3', block: 'h3' },
            { title: 'header 4', block: 'h4' },
            { title: 'header 5', block: 'h5' },
            { title: 'header 6', block: 'h6' },
            { title: 'pre', block: 'pre' },

            { title: 'article', block: 'article', wrapper: true, merge_siblings: false },
            { title: 'aside', block: 'aside', wrapper: true, merge_siblings: false  },
            { title: 'div', block: 'div', wrapper: true, merge_siblings: false  },
            { title: 'section', block: 'section', wrapper: true, merge_siblings: false },
            { title: 'blockquote', block: 'blockquote', classes: 'blockquote', wrapper: true },
            { title: 'figure', block: 'figure', wrapper: true },
            { title: 'figure left', block: 'figure', classes: 'island island-left' , wrapper: true },
            { title: 'figure right', block: 'figure',classes: 'island' ,  wrapper: true },

          ]},

          {title: 'Inline Elements', items: [
            { title: 'code', inline: 'code'},
            { title: 'kdb', inline: 'kbd'},
            { title: 'mark', inline: 'mark'},
            { title: 'span', inline: 'span'},
            { title: 'small', inline: 'small'},

          ]},
      ],
      style_formats_autohide: false,

      // Toolbar buttons size
      toolbar_items_size: 'medium',

      // Statusbar: set to true to display status bar with editor resize handle at the bottom. See: https://www.tinymce.com/docs/configure/editor-appearance/#statusbar
      statusbar: true,

      // Load Plugins - list of available plugins can be found here: https://www.tinymce.com/docs/plugins/
      plugins: "contextmenu table fullscreen paste media lists advlist charmap textcolor link anchor hr paste image code imagetools visualblocks searchreplace codesample wordcount emoticons importcss template",

      audio_template_callback: function(data) {
       return '<audio controls class="audio">' + '<source src="' + data.source1 + '"' + (data.source1mime ? ' type="' + data.source1mime + '"' : '') + ' />' + '</audio>';
      },

      // configure image plugin
      toolbar: "image",
      image_caption: true,
      image_class_list: [
        {title: 'None', value: 'img-fluid'},
        {title: 'Circle', value: 'rounded-circle img-fluid'},
        {title: 'Rounded', value: 'rounded img-fluid'},
        {title: 'Shadow', value: 'shadow img-fluid'},
        {title: 'Inline', value: 'd-inline pa-0'},
      ],
      visualblocks_default_state: true,
      end_container_on_empty_block: true,
      object_resizing : 'img',

      // Paste Settings - Docs: https://www.tinymce.com/docs/plugins/paste/
      paste_as_text: true, // enabled paste as text by default: https://www.tinymce.com/docs/plugins/paste/#paste_as_text

      // v2.50 - allow style in body (invalid XHTML but required to style html emails since many email clients won't display remote styles or styles from head)
      valid_children: "+body[style]", // docs: https://www.tinymce.com/docs/configure/content-filtering/#valid_children

      // Spellchecker plugin - No longer supported as Google no longer has a Public API.  Now using built in browser spellchecks
      browser_spellcheck: true,

      // Force <br> instead of <p> - see: https://www.tinymce.com/docs/configure/content-filtering/#forced_root_block
      // Uncomment these lines to enable this for new records
      //forced_root_block: false,

      //
      elements: '$fieldname',
      file_picker_callback: function(callback, value, meta) {
          $uploadBrowserCallback(callback, value, meta);
      },
      relative_urls: false,
      document_base_url: "/",

      entity_encoding: "raw", // don't store extended chars as entities (&ntilde) or keyword searching won't match them

      verify_html: false, // allow all tags and attributes


      // add file modified time on end of url so updated files won't be cached by the browser
      // reference: https://www.tinymce.com/docs/configure/content-appearance/#content_css
      content_css: "$wysiwygCssUrl, /css/editor.min.css",
      content_css_cors: true,

      importcss_groups: [
        {title: 'Fonts Classes', filter: /\.h\d+|\.fs|\.display-|\.fw/}, // regex
        {title: 'Text Classes', filter: /\.lead|\.small|\.mark|\.text-|\.lh/}, // regex
        {title: 'Background Color', filter: /\.bg-/}, // regex
        {title: 'Buttons', filter: /\.btn/}, // regex
        {title: 'Cards', filter: /\.card/}, // regex
        {title: 'Columns', filter: /\.col|\.row|\.offset/}, // regex
        {title: 'Lists', filter: /\.list/}, // regex
        {title: 'Spacing', filter: /\.gap|\.g-|\.gx-|\.gy-|\.m-|\.mx-|\.my-|\.ms-|\.me-|\.mt-|\.mb-|\.p-|\.px-|\.py-|\.py-|\.ps-|\.pe-|\.pt-|\.pb-/}, // regex
        {title: 'Tables', filter: /\.table/}, // .class
        {title: 'Special Classes', filter: /\.dropcap|\.island|\.blockquote/},
        {title: 'Remaining classes', filter: /\./}, // .class
        {title: 'Other styles'}, // The rest
      ],

      importcss_append: true,
      importcss_merge_classes: true,
      importcss_exclusive: true,


      templates: [
        {title: 'Simple Card', description: 'Simple Card template', content: '<div class="card"> \
        <div class="card-body"> <img src="..." class="card-img-top" alt="no image specified"> \
        <h5 class="card-title">Card title</h5> \
        <p class="card-text">Some quick example text to build on the card title and make up the bulk of the card content.</p> \
        <a href="#" class="btn btn-primary">Go somewhere</a> \
        </div> \
        </div>'},

        {title: '2 Cards', description: '2 Card template side by side', content: '<div class="row"> \
        <div class="col-sm-6"> \
          <div class="card"> \
            <div class="card-body"> \
              <h5 class="card-title">Special title treatment</h5> \
              <p class="card-text">With supporting text below as a natural lead-in to additional content.</p> \
              <a href="#" class="btn btn-primary">Go somewhere</a> \
              </div> \
            </div> \
          </div> \
          <div class="col-sm-6"> \
            <div class="card"> \
              <div class="card-body"> \
                <h5 class="card-title">Special title treatment</h5> \
                <p class="card-text">With supporting text below as a natural lead-in to additional content.</p> \
                <a href="#" class="btn btn-primary">Go somewhere</a> \
              </div> \
            </div> \
          </div> \
        </div>'},
      ],
    });  // end tinyMCE.init
  });

</script>

I don't allow the user to use an H1 element as I reserve that for the page title but they can use the .h1 class. Also, I build a separate editor.css file with only those styles from Bootstrap or any custom CSS I want to use.

Feel free to edit and expend the above code to your heart's conent.

Jeff Shields

By glennp - April 16

Thank you for your help, Jeff.

Glenn