Skip to content

Commit

Permalink
Merge pull request #409 from 3DStreet/title-and-logo-in-screenshot
Browse files Browse the repository at this point in the history
Title and logo in screenshot
  • Loading branch information
kfarr authored Nov 24, 2023
2 parents be8b997 + afe95d8 commit 33b1371
Showing 1 changed file with 102 additions and 30 deletions.
132 changes: 102 additions & 30 deletions src/components/screentock.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,44 +14,116 @@
// AFRAME.scenes[0].setAttribute('screentock', 'takeScreenshot', true);
// }

takeScreenshotNow = function (filename, type, imgElement) {
var renderer = AFRAME.scenes[0].renderer;

function downloadImageDataURL (filename, dataURL) {
var element = document.createElement('a');
var url = dataURL.replace(/^data:image\/[^;]/, 'data:application/octet-stream');
element.setAttribute('href', url);
element.setAttribute('download', filename);
element.style.display = 'none';
document.body.appendChild(element);
element.click();
document.body.removeChild(element);
}
var saveFilename = filename + '.' + type;

if (type == 'img') {
imgElement.src = renderer.domElement.toDataURL();
return;
}
if (type == 'png') {
downloadImageDataURL(saveFilename, renderer.domElement.toDataURL('image/png'));
} else {
downloadImageDataURL(saveFilename, renderer.domElement.toDataURL('image/jpeg', 0.95));
}
};

AFRAME.registerComponent('screentock', {
schema: {
takeScreenshot: { type: 'boolean', default: false },
filename: { type: 'string', default: 'screenshot' },
type: { type: 'string', default: 'jpg' }, // png, jpg, img
imgElementSelector: { type: 'selector' }
},
tock: function () {
takeScreenshotNow: async function (filename, type, imgElement) {
const inspector = AFRAME.INSPECTOR;
const renderer = AFRAME.scenes[0].renderer;

// hide helpers
toggleHelpers(false);

function toggleHelpers(show) {
if (inspector && inspector.opened) inspector.sceneHelpers.visible = show;
if (show) {
document.querySelector('#cameraRig')
.setAttribute('cursor-teleport', "cameraRig: #cameraRig; cameraHead: #camera;");
} else {
document.querySelector('#cameraRig').removeAttribute('cursor-teleport');
}
}

const createCanvasWithScreenshot = async (aframeCanvas) => {
let screenshotCanvas = document.querySelector('#screenshotCanvas');
if (!screenshotCanvas) {
screenshotCanvas = document.createElement('canvas');
screenshotCanvas.id = 'screenshotCanvas';
screenshotCanvas.hidden = true;
document.body.appendChild(screenshotCanvas);
}
screenshotCanvas.width = aframeCanvas.width;
screenshotCanvas.height = aframeCanvas.height;
const ctxScreenshot = screenshotCanvas.getContext("2d");

// draw image from Aframe canvas to screenshot canvas
ctxScreenshot.drawImage(aframeCanvas, 0, 0);
// add scene title to screenshot
addTitleToCanvas(ctxScreenshot, screenshotCanvas.width, screenshotCanvas.height);
// add 3DStreet logo
await addLogoToCanvas(ctxScreenshot);
return screenshotCanvas;
}

function addTitleToCanvas (ctx, screenWidth, screenHeight) {
ctx.font = "25px Lato";
ctx.textAlign = 'center';
ctx.fillStyle = '#FFF';
ctx.fillText(STREET.utils.getCurrentSceneTitle(),
screenWidth - screenWidth/2,
screenHeight - 43);
}

const addLogoToCanvas = async (ctx) => {

const logoImg = document.querySelector('img.viewer-logo-img')
const logoSVG = document.querySelector('#aframeInspector #logoImg svg');

if (logoImg) {
ctx.drawImage(logoImg, 0, 0, 135, 43, 40, 30, 270, 86);
} else if (logoSVG) {
const image = new Image();
image.src = `data:image/svg+xml;base64,${window.btoa(logoSVG.outerHTML)}`;
await new Promise((resolve) => {
image.onload = resolve;
});

ctx.drawImage(image, 0, 0, 135, 23, 40, 40, 270, 86);
}
}

function downloadImageDataURL (filename, dataURL, scnrenshotCanvas) {
const element = document.createElement('a');
const url = dataURL.replace(/^data:image\/[^;]/, 'data:application/octet-stream');
element.setAttribute('href', url);
element.setAttribute('download', filename);
element.style.display = 'none';
document.body.appendChild(element);
element.click();
document.body.removeChild(element);
}

const saveFilename = filename + '.' + type;

// render one frame
renderer.render(AFRAME.scenes[0].object3D, AFRAME.scenes[0].camera);
const screenshotCanvas = await createCanvasWithScreenshot(renderer.domElement);

if (type == 'img') {
imgElement.src = screenshotCanvas.toDataURL();
return;
}
if (type == 'png') {
downloadImageDataURL(saveFilename, screenshotCanvas.toDataURL('image/png'));
} else {
downloadImageDataURL(saveFilename, screenshotCanvas.toDataURL('image/jpeg', 0.95));
}
// show helpers
toggleHelpers(true);
},
update: function (oldData) {
// If `oldData` is empty, then this means we're in the initialization process.
// No need to update.
if (Object.keys(oldData).length === 0) { return; }

// this should be paused when not in use. could be throttled too
if (this.data.takeScreenshot) {
this.el.setAttribute('screentock', 'takeScreenshot', false);
takeScreenshotNow(this.data.filename, this.data.type, this.data.imgElementSelector);
}
this.data.takeScreenshot = false;
this.takeScreenshotNow(this.data.filename, this.data.type, this.data.imgElementSelector);
}
}
});

0 comments on commit 33b1371

Please sign in to comment.