Add copy to clipboard button on image converter (not supported in all browsers)

This commit is contained in:
HF 2020-05-10 00:03:15 +02:00
parent cc5340bc7a
commit a3d1f33969
6 changed files with 50 additions and 20 deletions

View File

@ -8,8 +8,9 @@ import { connect } from 'react-redux';
import fileDownload from 'js-file-download';
import { utils, applyPalette } from 'image-q';
import printGIMPPalette from '../core/exportGPL';
import type { State } from '../reducers';
import printGIMPPalette from '../core/exportGPL';
import { copyCanvasToClipboard } from '../utils/clipboard';
const titleStyle = {
color: '#4f545c',
@ -190,7 +191,6 @@ async function renderOutputImage(opts) {
palette.add(point);
});
const progEl = document.getElementById('qprog');
progEl.style.display = 'block';
// eslint-disable-next-line no-await-in-loop
pointContainer = await applyPalette(pointContainer, palette, {
colorDistanceFormula: colorDist,
@ -199,7 +199,7 @@ async function renderOutputImage(opts) {
progEl.innerHTML = `Loading... ${Math.round(progress)} %`;
},
});
progEl.style.display = 'none';
progEl.innerHTML = 'Done';
image = drawPixels(
pointContainer.toUint8Array(),
image.width,
@ -267,13 +267,9 @@ function Converter({
scaling: scaleData,
});
} else {
// draw gray rectanglue if no file selected
const output = document.getElementById('imgoutput');
const ctx = output.getContext('2d');
output.width = 128;
output.height = 100;
ctx.fillStyle = '#C4C4C4';
ctx.fillRect(0, 0, 128, 100);
output.width = 0;
output.height = 0;
}
});
@ -595,7 +591,7 @@ function Converter({
</div>
)
: null}
<p id="qprog" />
<p id="qprog">Select an Image</p>
<p>
<canvas
id="imgoutput"
@ -608,6 +604,19 @@ function Converter({
>
Download Template
</button>
{(typeof ClipboardItem === 'undefined')
? null
: (
<button
type="button"
onClick={() => {
const output = document.getElementById('imgoutput');
copyCanvasToClipboard(output);
}}
>
Copy to Clipboard
</button>
)}
</p>
);
}

View File

@ -98,7 +98,7 @@ class LogInForm extends React.Component {
onChange={(evt) => this.setState({ nameoremail: evt.target.value })}
type="text"
placeholder="Name or Email"
/>
/><br />
<input
value={password}
style={inputStyles}

View File

@ -111,7 +111,7 @@ function SettingsModal({
}) {
return (
<Modal title="Settings">
<p style={{ paddingLeft: '5%', paddingRight: '5%' }}>
<p style={{ paddingLeft: '5%', paddingRight: '5%', paddingTop: 30 }}>
<SettingsItem
title="Show Grid"
description="Turn on grid to highlight pixel borders."

View File

@ -107,21 +107,21 @@ class SignUpForm extends React.Component {
onChange={(evt) => this.setState({ name: evt.target.value })}
type="text"
placeholder="Name"
/>
/><br />
<input
style={inputStyles}
value={this.state.email}
onChange={(evt) => this.setState({ email: evt.target.value })}
type="text"
placeholder="Email"
/>
/><br />
<input
style={inputStyles}
value={this.state.password}
onChange={(evt) => this.setState({ password: evt.target.value })}
type="password"
placeholder="Password"
/>
/><br />
<input
style={inputStyles}
value={this.state.confirmPassword}
@ -130,8 +130,7 @@ class SignUpForm extends React.Component {
})}
type="password"
placeholder="Confirm Password"
/>
<br />
/><br />
<button type="submit">
{(this.state.submitting) ? '...' : 'Submit'}
</button>

View File

@ -75,7 +75,7 @@ class UserMessages extends React.Component {
const messages = [...this.props.messages];
return (
<div>
<div style={{ paddingLeft: '5%', paddingRight: '5%' }}>
{(messages.includes('not_verified') && messages.splice(messages.indexOf('not_verified'), 1))
? (
<p className="usermessages">
@ -98,7 +98,7 @@ class UserMessages extends React.Component {
</p>
) : null}
{messages.map((message) => (
<p className="usermessages" key={message} className="message">{message}</p>
<p className="usermessages" key={message}>{message}</p>
))}
</div>
);

View File

@ -24,7 +24,27 @@ function fallbackCopyTextToClipboard(text) {
}
}
export default async function copyTextToClipboard(text) {
export async function copyCanvasToClipboard(canvas) {
canvas.toBlob((blob) => {
try {
if (!navigator.clipboard) {
throw new Error('Clipboard API not implemented');
}
navigator.clipboard.write([
// this is defined in current chrome, but not firefox
// eslint-disable-next-line no-undef
new ClipboardItem({
'image/png': blob,
}),
]);
} catch (e) {
// eslint-disable-next-line no-console
console.log("Couldn't copy canvas to clipboard", e);
}
}, 'image/png');
}
async function copyTextToClipboard(text) {
if (!navigator.clipboard) {
return fallbackCopyTextToClipboard(text);
}
@ -35,3 +55,5 @@ export default async function copyTextToClipboard(text) {
return false;
}
}
export default copyTextToClipboard;