[QUESTION]: How can I create block with background image with behavior like built-in "image"?
Question
Hello, I'm trying to create block with background image (similar to Grapedrop Image Box). I added new component like this:
domc.addType('image-block', {
extend: 'image',
model: {
defaults: function() {
return {
name: 'Background Image',
type: 'image-block',
tagName: 'div',
void: false,
droppable: true,
resizable: true
}
}
},
view: {
tagName: 'div',
updateSrc: function() {
const { model, em } = this;
const srcResult = model.getSrcResult();
const style = model.getStyle();
const isDefaultSrc = model.isDefaultSrc();
const url = "url('".concat(srcResult, "')");
if (srcResult) {
model.addStyle({
'__bg-type': 'img',
'background-image': isDefaultSrc && style['background-image'] || url,
'background-size': style['background-size'] || 'cover',
'background-position': style['background-position'] || 'center center',
'background-attachment': style['background-attachment'] || 'scroll',
'background-repeat': style['background-repeat'] || 'no-repeat'
});
em.trigger('component:toggled');
}
this.$el[srcResult ? 'removeClass' : 'addClass'](this.classEmpty)
},
onRender: function() {
this.updateSrc()
}
}
})
And also I added block:
bm.add('image-block', {
label: 'Background Image',
category: 'Basic',
content: {
name: 'Background Image',
type: 'image-block',
activeOnRender: 1,
style: {
height: '200px'
}
}
})
But unfortunatelly I cannot drop any block inside of it:

Grapedrop Image Box has the same issue. Is it possible to drop elements inside of such compoent?
Answers (2)
@noogen Thanks for advise, implemented it like this:
const domc = editor.DomComponents
domc.addType('image-block', {
extend: 'default',
model: {
defaults: function () {
return {
name: 'Background image',
type: 'image-block',
tagName: 'div',
void: false,
droppable: true
}
}
},
view: {
init () {
this.listenTo(this.model, 'active', this.onActive)
this.listenTo(this.model, 'change:src', this.updateImage)
},
events: {
dblclick: 'onActive'
},
onActive () {
editor.runCommand('open-assets', {
target: this.model,
types: ['image'],
accept: 'image/*'
})
},
updateImage (model, url) {
if (url) {
const style = model.getStyle()
model.setStyle({
'background-image': style['background-color'] || `url("${url}")`,
'background-size': style['background-size'] || 'cover',
'background-position': style['background-position'] || 'center center',
'background-repeat': style['background-repeat'] || 'no-repeat',
'min-height': style['min-height'] || '200px'
})
}
}
}
})
const bm = editor.BlockManager
bm.add('image-block', {
label: 'Background Image',
category: 'Basic',
content: {
type: 'image-block',
activeOnRender: true,
style: {
'background-image': `url('${window.origin}/images/image-placeholder.png')`,
'min-height': '200px',
'background-size': 'cover',
'background-position': 'center center',
'background-repeat': 'no-repeat'
}
}
})
@kuhelbeher because, ultimately, it is still an image. It's not for use/override the way you want because in the back-end code (look at both image component model and view) https://github.com/artf/grapesjs/blob/dev/src/dom_components/view/ComponentImageView.js#L55 and https://github.com/artf/grapesjs/blob/dev/src/dom_components/model/ComponentImage.js#L83 are still very much ties together. It's better that you create a wrapper component and execute command open-assets in onActive of the view. Hint, see issue - https://github.com/artf/grapesjs/issues/2250
Related Questions and Answers
Continue research with similar issue discussions.
Issue #2697
[QUESTION] Problem with custom component type and table cell
Hello! I'm trying to add custom component type: And also I'm adding new block: But when I drop this block on the canvas the <td> tag doesn'...
Issue #2777
[QUESTION] How to update styles in Style Manager
Hello. I created custom component where I set backgraound-image via custom asset manager Custom block code: Command which I run to set new...
Issue #2103
[QUESTION] Custom Component dragging issue
This is how I've created a custom component: This is my custom block: The thing is that I have wrapped the image tag inside <a> tag when it...
Issue #2549
[QUESTION] Update component view on property change
Hi everyone, I'm trying to create a component that will update it's view based on a property value My approach is bassed on #1227 and on th...
Paid Plugins That Match This Issue
Curated by issue keywords and label relevance to help you ship faster.
Loading paid plugin recommendations...
Browse Plugin Categories
Jump directly to plugin category pages on the marketplace.