simplified handling of inline images

This commit is contained in:
or-else
2017-09-26 14:43:46 -07:00
parent cf4b58cab2
commit e495917356
2 changed files with 49 additions and 72 deletions
+9 -11
View File
@@ -89,7 +89,7 @@ Sample JSON representation of the text above:
LN: { name: 'a', isVoid: false }, LN: { name: 'a', isVoid: false },
MN: { name: 'a', isVoid: false }, MN: { name: 'a', isVoid: false },
HT: { name: 'a', isVoid: false }, HT: { name: 'a', isVoid: false },
IM: { name: ['a','img'], isVoid: true } IM: { name: 'img', isVoid: true }
}; };
// Convert base64-encoded string into Blob. // Convert base64-encoded string into Blob.
@@ -142,17 +142,15 @@ Sample JSON representation of the text above:
}, },
props: function(data) { props: function(data) {
var url = base64toObjectUrl(data.val, data.mime); var url = base64toObjectUrl(data.val, data.mime);
return [ return {
{
download: data.name,
href: url
},
{
src: url, src: url,
width: data.width, title: data.name,
height: data.height, 'data-width': data.width,
} 'data-height': data.height,
]; 'data-name': data.name,
'data-size': (data.val.length * 0.75) | 0,
'data-mime': data.mime
};
}, },
} }
}; };
+33 -54
View File
@@ -83,34 +83,34 @@
'data:image/' + photo.type + ';base64,' + photo.data : null; 'data:image/' + photo.type + ';base64,' + photo.data : null;
} }
// Scale liner dimensions to fit uder certain size
function imageScaleDown(width, height, maxWidth, maxHeight) {
if (!width || !height || !maxWidth || !maxHeight) {
return null;
}
var scale = Math.min(
Math.min(width, maxWidth) / width,
Math.min(height, maxHeight) / height
);
return {width: (width * scale) | 0, height: (height * scale) | 0};
}
// Convert uploaded image into a base64-encoded string. // Convert uploaded image into a base64-encoded string.
function imageFileToBase64(file, callback) { function imageFileToBase64(file, callback) {
var img = new Image(); var img = new Image();
img.crossOrigin = 'Anonymous'; img.crossOrigin = 'Anonymous';
img.onload = function() { img.onload = function() {
var width, height; var size = imageScaleDown(this.width, this.height, MAX_IMAGE_SIZE, MAX_IMAGE_SIZE);
if (this.height > this.width) {
height = this.height;
while(height > MAX_IMAGE_SIZE) {
height = height >> 1;
}
width = (this.width * height / this.height) | 0;
} else {
width = this.width;
while(width > MAX_IMAGE_SIZE) {
width = width >> 1;
}
height = (this.height * width / this.width) | 0;
}
var canvas = document.createElement('CANVAS'); var canvas = document.createElement('CANVAS');
canvas.width = width; canvas.width = size.width;
canvas.height = height; canvas.height = size.height;
var ctx = canvas.getContext('2d'); var ctx = canvas.getContext('2d');
ctx.imageSmoothingEnabled = true; ctx.imageSmoothingEnabled = true;
ctx.drawImage(this, 0, 0, this.width, this.height, 0, 0, canvas.width, canvas.height); ctx.drawImage(this, 0, 0, this.width, this.height, 0, 0, canvas.width, canvas.height);
var imageBits = canvas.toDataURL("image/jpeg"); var imageBits = canvas.toDataURL("image/jpeg");
canvas = null; canvas = null;
callback(imageBits, width, height); callback(imageBits, size.width, size.height);
}; };
img.src = URL.createObjectURL(file); img.src = URL.createObjectURL(file);
} }
@@ -2360,41 +2360,21 @@
var formatter = function(style, data, values) { var formatter = function(style, data, values) {
elementKey += 1; elementKey += 1;
if (style == "IM") {
// Handle inline image
var width = data.width, height = data.height;
var style = null;
if (width && height) {
var scale = 1.0;
if (data.width > REM_SIZE * 36) {
scale = REM_SIZE * 36 / data.width;
}
if (data.height * scale > REM_SIZE * 24) {
scale = REM_SIZE * 24 / data.height;
}
style = {
width: Math.round(data.width * scale / REM_SIZE) + "rem",
height: Math.round(data.height * scale / REM_SIZE) + "rem"
}
}
var url = Drafty.getBlobUrl(data);
return (
<img className="inline-image" onClick={this.handlePreviewImage}
data-width={data.width} data-height={data.height}
data-size={Drafty.getAttachmentSize(data)}
data-mime={Drafty.getAttachmentType(data)}
src={url} style={style} alt="" title={data.name} />
);
} else {
var el = Drafty.tagName(style); var el = Drafty.tagName(style);
if (el) { if (el) {
var attr = Drafty.attrValue(style, data) || {}; var attr = Drafty.attrValue(style, data) || {};
attr.key = elementKey; attr.key = elementKey;
if (style == "IM") {
// Additional processing for images
var size = imageScaleDown(data.width, data.height, REM_SIZE * 36, REM_SIZE * 24);
attr.className = "inline-image";
attr.style = size ? { width: size.width + "px", height: size.height + "px" } : null;
attr.onClick = this.handlePreviewImage;
}
return React.createElement(el, attr, values); return React.createElement(el, attr, values);
} else { } else {
return values; return values;
} }
}
}; };
var sideClass = this.props.sequence + " " + (this.props.response ? "left" : "right"); var sideClass = this.props.sequence + " " + (this.props.response ? "left" : "right");
@@ -2984,16 +2964,15 @@
if (!this.props.content) { if (!this.props.content) {
return null; return null;
} }
var instance = this; var instance = this;
var width = null, height = null; var size = imageScaleDown(this.props.content.width, this.props.content.height,
console.log(this.props.content.width, this.props.content.height, this.state.width, this.state.height); this.state.width, this.state.hight);
if (this.props.content.width && this.props.content.height) { if (size) {
width = Math.max(Math.min(this.state.width, this.props.content.width), 8); size.width += "px";
height = Math.max(Math.min(this.state.height, this.props.content.height), 8); size.height += "px";
var scale = Math.min(width / this.props.content.width, height / this.props.content.height, 1.0); } else {
width = (this.props.content.width * scale) | 0; size = (this.props.content.width > this.props.content.height) ?
height = (this.props.content.height * scale) | 0; {width: '100%'} : {height: '100%'};
} }
var filename = this.props.content.filename; var filename = this.props.content.filename;
if (filename.length > 20) { if (filename.length > 20) {
@@ -3009,7 +2988,7 @@
<a href="#" onClick={this.props.onClose}><i className="material-icons gray">close</i></a> <a href="#" onClick={this.props.onClose}><i className="material-icons gray">close</i></a>
</div> </div>
<div id="image-preview-container"> <div id="image-preview-container">
<img src={this.props.content.url} width={width} height={height} /> <img src={this.props.content.url} style={size} />
</div> </div>
<div id="image-preview-footer"> <div id="image-preview-footer">
<div><div><b>File name</b>:</div><div><span title={this.props.content.filename}>{filename}</span></div></div> <div><div><b>File name</b>:</div><div><span title={this.props.content.filename}>{filename}</span></div></div>