screenshot canvas getUserMedia Chrome - javascript

I want to make a screnshot of the wecam video in Chrome beta.
The code only produces a screenshot of a small part of the video, what went wrong?
here the code:
http://jsfiddle.net/N9XKh/

You haven't specified the dimensions of your canvas element so it is being created at the default size (300x150) which is smaller than the dimensions of the video element. As a result, when you draw the video to the canvas the snapshot is being cropped.
I would update the snapshot method to set the canvas width and height to match those of the video element like so:
// create snapschot
function snapshot() {
// set the canvas to the dimensions of the video
canvas.width = video.clientWidth;
canvas.height = video.clientHeight;
ctx.drawImage(video, 0, 0);
document.getElementById("huhu").src = canvas.toDataURL('image/webp');
}
Updated fiddle here.

Related

Is it possible to scale a drag image

I am doing drag and drop and want to use a different drag image than the default. But I would also like to scale the size of the drag image depending on the size of the element where the drag starts. I have tried doing the following:
<div id="drag-with-image" draggable="true">drag me</div>
<script>
document.getElementById("drag-with-image").addEventListener("dragstart", function(e) {
var img = document.createElement("img");
img.src = "https://www.w3schools.com/css/paris.jpg";
img.style.width = "60px";
img.style.height = "40px";
e.dataTransfer.setDragImage(img, 0, 0);
}, false);
</script>
But the drag image is always displayed as full size.
Is there any way the drag image size can be scaled dynamically?
Yes, it is possible to scale a custom drag image.
The Problem
If you're using setDragImage with an image element, what will be drawn is the image in its intrinsic size (content size before any modification). This means that setting the image size doesn't help. However, as mentioned in MDN Docs, you can also set a drag image to be something else:
If Element is an img element, then set the drag data store bitmap to the element's image (at its intrinsic size); otherwise, set the drag data store bitmap to an image generated from the given element (the exact mechanism for doing so is not currently specified).
Furthermore, it also mentions that the "other elements" can be any visible element or even a <canvas>:
However, if a custom image is desired, the DataTransfer.setDragImage() method can be used to set the custom image to be used. The image will typically be an element but it can also be a or any other visible element.
Solution
To draw an image that is smaller than its intrinsic size and setting it to drag image, you can:
Load the image to an image element
Create a canvas to be drawn with the image
When drawing to the canvas, adjust the width and height of the drawn image accordingly
Here's a working example.
document.getElementById('drag-with-image').addEventListener('dragstart', function(e) {
var img = document.createElement('img')
var canvas = document.createElement('canvas')
var ctx = canvas.getContext('2d')
// Setting img src
img.src = 'https://www.w3schools.com/css/paris.jpg'
// Drawing to canvas with a smaller size
canvas.width = img.width * 0.1
canvas.height = img.height * 0.1
ctx.drawImage(img, 0, 0, canvas.width, canvas.height)
// Setting drag image with drawn canvas image
e.dataTransfer.setDragImage(canvas, 0, 0)
}, false)
<div id="drag-with-image" draggable="true">drag me</div>

Images Rendered to Canvas in Node Webkit are Blurry

When I try to load an image in my node webkit app with the following code:
var canvas = document.getElementById('cytoBkg');
var ctx = canvas.getContext('2d');
ctx.imageSmoothingEnabled = false;
var map = new Image();
map.src = './maps/map.jpg';
map.onload = function() {
ctx.drawImage(map, 0, 0, map.width, map.height, 0, 0, canvas.width, canvas.height);
console.log(map.width, map.height);
}
the image that is rendered to the canvas is very blurry. After about a minute, the following error comes up in the console:
[7583:7583:0519/153517.738479:ERROR:CONSOLE(0)] "Denying load of chrome-extension://dekacdafkimiiblogellomljhcemdaab/maps/map.jpg. Resources must be listed in the web_accessible_resources manifest key in order to be loaded by pages outside the extension.", source: chrome-devtools://devtools/bundled/inspector.html?remoteBase=https://chrome-devtools-frontend.appspot.com/serve_file/#691bdb490962d4e6ae7f25c6ab1fdd0faaf19cd0/&dockSide=undocked (0)
How can I make my image load properly? I have tried adding the image to as a web accessible resource in my package.json file, but this did not help.
This issue seems to arise when you set the height and width of the canvas in it's style attribute before drawing the image on the canvas. In the above example, the issue can be remedied by setting:
canvas.width = map.width;
canvas.height = map.height;
after the image's onload event, and removing any css related to the height or width of your canvas.

How to resize canvas contents and upload image to server?

I have been trying to figure out how I could resize the canvas contents to get roughly a 100x100 thumbnail and upload it to the server. I would like to keep my existing canvas in its current size, because all these actions have to be invisible to the user.
I know I can get the contents in the current size of the canvas by using toDataURL, but how could I resize it and then upload to the server?
var image = canvas.toDataURL("image/png");
You can create canvas in your JS script (without appending it to DOM), then draw on it your content from working canvas (your image), resize it in context of your temp canvas ( Post about resizing in canvas ). And only then do canvas.toDataURL("image/png"); to get resized image. Then you send it as base64 string and save on your server as png file.
Thanks to Alexander Kremenets I managed to put together the code I needed. I used the Hermite resize from the question Alexander linked. Also combined code from other questions coming up with this:
var originalCanvas = document.getElementById("c");
// Create canvas for resizing
var resizeCanvas = document.createElement("canvas");
resizeCanvas.height = originalCanvas.height;
resizeCanvas.width = originalCanvas.width;
var resizeCtx = resizeCanvas.getContext('2d');
// Put original canvas contents to the resizing canvas
resizeCtx.drawImage(originalCanvas, 0, 0);
// Resize using Hermite resampling
resampleHermite(resizeCanvas, resizeCanvas.width, resizeCanvas.height, 150, 90);
// Use the resized image to do what you want
var image = resizeCanvas.toDataURL("image/png");

Make Html5 Canvas and Its contained image responsive across browsers

I have a canvas object that I want to put an image in for a web application. I can get the image loaded, but I've run into 2 problems: The image won't stretch to the canvas, and the canvas won't stretch to cover the entire div in any browser but Firefox.
http://jsfiddle.net/LFJ59/1/
var canvas = $("#imageView");
var context = canvas.get(0).getContext("2d");
$(document).ready(drawImage());
$(window).resize(refreshCanvas());
refreshCanvas();
function refreshCanvas() {
//canvas/context resize
canvas.attr("width", $(window).get(0).innerWidth / 2);
canvas.attr("height", $(window).get(0).innerHeight / 2);
drawImage();
};
function drawImage() {
//shadow
context.shadowBlur = 20;
context.shadowColor = "rgb(0,0,0)";
//image
var image = new Image();
image.src = "http://www.netstate.com/states/maps/images/ca_outline.gif";
$(image).load(function () {
image.height = canvas.height();
image.width = canvas.width();
context.drawImage(image);
});
};
Is there a solution to making the canvas responsive? Or do I just need to lock the canvas and image down to predefined sizes?
width and height of image are read-only so that won't work.
Try instead:
context.drawImage(image, 0, 0, canvas.width, canvas.height);
This will draw the image the same dimension as the canvas is (you don't need to reload the image every time btw. - just load it once globally and reuse the image variable.)
<canvas id="imageView" width="1000" height="1000" style="width:100%; height:100%"></canvas>
Both CSS and height and width attributes can be used and do not need to agree in size. The CSS style will determine the displayed size, you asked for a canvas that can stretch. The width and height control the number of pixels the canvas uses for drawing.
for example this will be scaled 10 to 1, and with anti-aliasing scrolling an drawing in this canvas would be as smooth as silk.
<canvas id="imageView" width="1000" height="1000" style="width:100px; height:100px"></canvas>
If CSS is not used, their defaults will be the width and height attributes of the canvas element.

How to get color that is behind a transparent element?

I am working on a site where the body has many color. When the content is scrolled down the background of the content changes.
In the below image u can see body text with blue color background. So when the content is scrolled down with the scrollbar then the background image should also scroll along with the content.
So what happens is when scroll bar stops at a color like blue then automatically the menu header(Home) background should change to blue.
First of all we should know what we want to do. Step one is actually get a color of the image, thus acces a property of the image.
However the browser cannot get direct information of the image itself(You can, of course, get information from the element of the image). However one webbrowser drawing method let us control every aspect of a image: Canvas.
So first we have to convert our image to an canvas element.
This is fairly simply done with drawImage(img, posx, posy, canvasWidth, canvasHeight);
We will also stretch the canvas image + the element to the entire screen. The reason we want to define to size also at the canvas is because this way the canvas will calculate every new generated pixel, so we can acces every of the new pixels:
var screenWidth = window.innerWidth,
screenHeight = window.innerHeight,
c = document.createElement('canvas');
ctx = c.getContext("2d"),
img = document.getElementById("image");
c.width = screenWidth;
c.height = screenHeight;
ctx.drawImage(img, 0, 0, screenWidth, screenHeight);
$(c).attr('id', 'c');
$('body').prepend(c);
$(img).remove();
An Canvas element as is dynamically made and will fit to the screen size(Note that this is only at first start of the webbrowser. So when you resize the canvas will not resize with the screen).
We remove the image as it is no use anymore. It's a good practive to transform from image to canvas in my opinion. As you will be certain that the image will be loaded in the browser first and then transformed to a canvas element.
Next we're going to acces a pixel. You can acces pixel data with getImageData(offsetX, offsetY, sizeX, sizeY).data; And RGBA color array will be returned.
Now the offsetX and offsetY will be the offset of the element color picker. Note that this elements offset should be relative to the webbrowsers viewport as the background is fixed You can do this with getBoundingClientRect();
The size is just 1x1 as we want 1 pixel.
This all should happen when the user is scrolling, you can catch the scroll event with .scroll(function); :
$(window).scroll(function () {
var offset = document.getElementById('color').getBoundingClientRect(),
offsetX = offset.left,
offsetY = offset.top;
var color = document.getElementById('c').getContext('2d').getImageData(offsetX, offsetY, 1, 1).data;
$('header').css('background-color',"rgba("+ color[0] + ', ' + color[1] + ', '+ color[2] + ', ' + color[3] + ")");
});
Where we add the rgba array colors just with the first 4 indexes(Because and rgba collor pattern never has more as 4 values) with plain css to the header element.
Loading External image into a canvas
When you want to transform an external image to a canvas element you might get this error:
Cross-origin image load denied by Cross-Origin Resource Sharing policy.
It is for security reasons that you can't fully acces this image.
As explained here: HTML 5 canvas getImageData from an externally-loaded image
There are some external hosts that supports this, for example dropbox.
Local
However when you just store it locally it will just work fine.
jsFiddle
This method was tested in chrome, IE and firefox.
I want to use those external (dropbox) files
I'm not sure why this happens but for some reason with this method there are still some security diffecults. To enable this CORS you have to add a image property .crossOrigin = "Anonymous";. However when you load the image with HTML the the element has been made without this property. So you should assign this property when the image is created:
var canvas = document.getElementById("c"),
ctx = canvas.getContext("2d"),
screenWidth = window.innerWidth,
screenHeight = window.innerHeight;
// Using image WITH crossOrigin=anonymous
// Succeeds in Chrome+Mozilla, Still fails in IE
var externalImage2 = new Image();
externalImage2.onload = function(){
canvas.width= screenWidth;
canvas.height= screenHeight;
ctx.drawImage(externalImage2, 0, 0, screenWidth, screenHeight);
// this will FAIL on a CORS violation
}
externalImage2.crossOrigin = "Anonymous";
externalImage2.src="https://dl.dropboxusercontent.com/s/8g8lgmdx341j1d6/rainbow_gradient_horizontal.jpg";
This is just an picture i uploaded to my dropbox where i just shared the photo. Note:
The way to convert a share link to a direct link is to change the domain from "www.dropbox.com" to "dl.dropboxusercontent.com". See https://www.dropbox.com/developers/blog/53/programmatically-download-content-from-share-links.
source: Cross-origin image load from cross-enabled site is denied
This creates an image and puts it into an excisting canvas element. So note that you should have a canvas element into your HTML.
jsFiddle
This method does only work for chrome and firefox as other browsers still have some security issues.
Additional note is the pixel that gets captured is the top-left pixel of the 'color-pick' element. You can adjust this offset if you want it to catch, for example, the middle pixel of the element.
This was a very interesting question. I hope it helped!
well, you may give background color of the home bar as transparent if you have no band between the home and the content.
.home{
background:transparent;
}

Categories

Resources