Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
93 changes: 63 additions & 30 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ module.exports = class MonoImage extends MonoLazy {

onEnter () {
if (this.loaded) return

// find best image size for the container
var elWidth = this.element.offsetWidth * this.deviceRatio
var imgWidth = closest(this.sizes, elWidth)
Expand Down Expand Up @@ -45,43 +45,76 @@ module.exports = class MonoImage extends MonoLazy {

createElement (image, opts) {
opts = opts || {}

this.image = image
this.sizes = Object.keys(this.image.sizes).map(s => parseInt(s))
this.sizes = Object.keys(this.image.sizes).map(s => parseInt(s)).sort()
if (typeof opts.onload === 'function') this.handleCallback = opts.onload

var attributes = {
class: `monoimage${this.loaded ? ' monoimage-loaded' : ''}`
}
var els = []

// first iteration constructs lazy-loaded element
// second iteration constructs noscript vanilla element
for (var i = 0; i < 2; i++) {
var noscript = (i == 1)

var attributes = {
class: `monoimage${(this.loaded || noscript) ? ' monoimage-loaded' : ''}`
}

var styles = `
width:100%;
display:${opts.inline ? 'inline-block' : 'block'};
`

if (opts.background) {
styles += `
background-position:center;
background-repeat:no-repeat;
background-size:${opts.background === 'contain' ? 'contain' : 'cover'};
${this.loaded ? `background-image:url(${this.loaded});` : ''}
var display = opts.inline ? 'inline-block' : 'block'

// the lazy-loaded element should be hidden until
// javascript runs on the client (only applicable for SSR)
if (typeof window == 'undefined' && !noscript) {
display = 'none'
}

var styles = `
width:100%;
display:${display};
`
} else {
if (this.loaded) {
attributes.src = this.loaded

if (opts.background) {
styles += `
background-position:center;
background-repeat:no-repeat;
background-size:${opts.background === 'contain' ? 'contain' : 'cover'};
`
}
}

if (opts.fill) {
styles += 'height:100%;'
} else if (!this.loaded || opts.background) {
styles += `padding-top:${image.dimensions.ratio}%;`
}
if (this.loaded || noscript) {
// noscript elements load largest image size to be safe
var largestWidth = this.sizes[this.sizes.length - 1]
var src = this.loaded || this.image.sizes[largestWidth]

if (opts.background) {
styles += `
background-image:url(${src});
`
} else {
attributes.src = src
}
}

if (opts.fill) {
styles += 'height:100%;'
} else if ((!this.loaded && !noscript) || opts.background) {
styles += `padding-top:${image.dimensions.ratio}%;`
}

attributes.style = styles.replace((/ |\r\n|\n|\r/gm),"")
attributes.style = styles.replace((/ |\r\n|\n|\r/gm),"")

var el = opts.background
? html`<div ${attributes}></div>`
: html`<img ${attributes}>`

if (noscript) {
el = html`<noscript>${el}</noscript>`
}

els.push(el)
}

return opts.background
? html`<div ${attributes}></div>`
: html`<img ${attributes}>`
return html`<div>${els}</div>`
}
}