question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Question: Dragging blocks into a Text block?

See original GitHub issue

This is not a bug but an implementation question. If this is not the right place to ask these questions, please let me know.

We’re working on an implementation where we want to use GrapesJS to allow users to create an e-mail template. As part of this implementation we are working to create mail-merge functionality: we’ve introduced the concept op ‘merge-fields’ or ‘placeholders’ which we will replace with the proper values on the server side. This means we send over the components JSON structure and turn it into HTML server-side, replacing values as we go.

So, as an example, one of our users might enter the text: Hello <<username>> and we’ll replace that merge-field <<username>> with the proper field.

But, we haven’t been able to implement this this way quite yet as we’re not able to drag these blocks into a Text block. We can only drag it around it. So, for now we’re extending the RTE with a merge-field ‘inline block’ ( <input type=text readonly class=mergeField data-isMergefield=1 />) and creating a merge-field block with the same HTML in the block manager. Implementing a DomComponent type to recognize it offers a method to configure it. But it feels suboptimal, we’d really like to be able to drag that mergefield block onto the right place in the textfield.

To allow this, I imagine GrapesJS would have to be able to grab the textNode and split it in to (atleast) two textnodes and a tag for the merge-field but I’m not sure where to start with this. Could you advise as to how we might implement this?

Issue Analytics

  • State:closed
  • Created 6 years ago
  • Comments:42 (13 by maintainers)

github_iconTop GitHub Comments

10reactions
artfcommented, Nov 6, 2017

Have you checked API-Rich-Text-Editor? You can add a custom action like this

editor.RichTextEditor.add('custom-vars', {
  icon: `<select class="gjs-field">
		<option value="">- Select -</option>
        <option value="[[firstname]]">FirstName</option>
        <option value="[[lastname]]">LastName</option>
        <option value="[[age]]">Age</option>
      </select>`,
    // Bind the 'result' on 'change' listener
  event: 'change',
  result: (rte, action) => rte.insertHTML(action.btn.firstChild.value),
  // Reset the select on change
  update: (rte, action) => { action.btn.firstChild.value = "";}
})

rte-action

4reactions
artfcommented, Apr 9, 2019

Probably in the next release, this feature will be available. textable

So textable will be just another property, this will allow any component to be dropped inside Text components. Here is the code of the component from the example above:

// Define a component with `textable` property
editor.DomComponents.addType('var-placeholder', {
      model: {
        defaults: {
          textable: 1,
          placeholder: 'VARIABLE-1',
        },
        toHTML() {
          return `{{ ${this.get('placeholder')} }}`;
        },
      },
	  // The view below it's just an example of creating a different UX
      view: {
        tagName: 'span',
        events: {
          'change': 'updatePlh',
        },
        // Update the model once the select is changed
        updatePlh(ev) {
          this.model.set({ placeholder: ev.target.value });
          this.updateProps();
        },
        // When we blur from a TextComponent, all its children components are
        // flattened via innerHTML and parsed by the editor. So to keep the state
        // of our props in sync with the model so we need to expose props in the HTML
        updateProps() {
          const { el, model } = this;
          el.setAttribute('data-gjs-placeholder',  model.get('placeholder'));
        },
        onRender() {
          const { model, el } = this;
          const currentPlh = model.get('placeholder');
          const select = document.createElement('select');
          const options = [ 'VARIABLE-1', 'VARIABLE-2', 'VARIABLE-3' ];
          select.innerHTML = options.map(item => `<option value="${item}" ${item === currentPlh ? 'selected' : ''}>
			${item}
		  </option>`).join('');
          while (el.firstChild) el.removeChild(el.firstChild);
          el.appendChild(select);
          select.setAttribute('style', 'padding: 5px; border-radius: 3px; border: none; -webkit-appearance: none;');
          this.updateProps();
        },
      }
    });
	
	// Use the component in blocks
    editor.BlockManager.add('simple-block', {
      label: 'Textable block',
      content: { type: 'var-placeholder' },
    });
Read more comments on GitHub >

github_iconTop Results From Across the Web

Tutorial: Working with blocks in the email editor
Explore the email editor and learn how to work with blocks using drag and drop [Duration 3:11] In this video tutorial, you'll learn...
Read more >
Block Options - Qualtrics
Your questions will now be placed in a new block at the bottom of your survey. To move your block elsewhere, drag and...
Read more >
Text Blocks - Squarespace Help Center
In the classic editor, two or more text blocks stacked vertically always merge into one. To prevent this, separate each text block with...
Read more >
How Do I Move Text Blocks in Squarespace? - website builder
If you want to move a text block in the drag-and-drop editor, simply click on the text block and drag it to the...
Read more >
Drag and drop a word or phrase from a block of text using ...
While this is an interesting problem you're trying to solve, you should attempt to solve it on your own first instead of asking...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found