Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Enhancement: create blank/empty image of given dimensions/channels #470

Closed
pjarts opened this issue Jun 20, 2016 · 16 comments
Closed

Enhancement: create blank/empty image of given dimensions/channels #470

pjarts opened this issue Jun 20, 2016 · 16 comments
Milestone

Comments

@pjarts
Copy link

pjarts commented Jun 20, 2016

Is it possible to create an empty canvas image with Sharp and process it through a stream or do I need to load a canvas image file from disk?

@lovell
Copy link
Owner

lovell commented Jun 20, 2016

Are you able to provide more information about the problem you're trying to solve? What do you mean by "canvas" in this context?

@pjarts
Copy link
Author

pjarts commented Jun 21, 2016

The lwip node module has a method called "create" (https://github.com/EyalAr/lwip#create-a-new-image) that creates an empty image. I was wondering if it is possible to accomplish the same thing in sharp, or if I always have to start off from an existing image file.

@lovell
Copy link
Owner

lovell commented Jun 21, 2016

You could use a raw pixel input buffer for this, something like this (ES2015) example:

const width = 200;
const height = 100;
const channels = 4;
const rgbaPixel = 0x00000000;

const canvas = Buffer.alloc(width * height * channels, rgbaPixel);

sharp(canvas, { raw : { width, height, channels } })...

@lovell
Copy link
Owner

lovell commented Jul 11, 2016

@pjarts Were you able to make any progress with this?

@strarsis
Copy link

strarsis commented Jul 13, 2016

Would a little helper function ("create(...)"?) in sharp make sense,
like one that uses the canvas code above?

@pjarts
Copy link
Author

pjarts commented Jul 15, 2016

@lovell, sorry for the late reply. Yes your code seems to do what I was looking for, although I agree with @strarsis that a helper function would be nicer.

@lovell
Copy link
Owner

lovell commented Jul 16, 2016

@pjarts Thanks for confirming.

Let's leave this issue open to track adding such a helper - I'll need to have a think about what the API might look like.

@lovell lovell changed the title Create empty canvas Enhancement: create blank/empty image of given dimensions/channels Jul 16, 2016
@lovell lovell removed the question label Jul 16, 2016
@strarsis
Copy link

strarsis commented Jul 16, 2016

  1. A kind of factory/'static' method:

    sharp.empty()
    
  2. With configuration object passed:

    sharp.create/empty/new({ width: 1024, height: 768 });
    
  3. Like 2. but directly with 'constructor' method:

    sharp({ width: 1024, height: 768 });
    
  4. With no arguments passed at all - using resize to achieve the desired dimensions:

    sharp().resize(1024, 768);
    
  5. Like 3. but using an empty dummy image from constant (not very elegant imho
    because of dummy image and even artifacts that may be caused):

    sharp(sharp.EMPTY_IMAGE).resize(1024, 768);
    

@lovell
Copy link
Owner

lovell commented Aug 13, 2016

The forthcoming v0.16.0 release moves all image input logic to a common location, namely the _createInputDescriptor function in JavaScript then CreateInputDescriptor method in C++.

This is the best place to add such a "create image" helper, so any part of the API that can handle input images will be able to use it.

Here's how the API could work:

sharp(null, {
  create: {
    width: 1024,
    height: 768,
    channels: 3,
    background: rgb
  }
})...
sharp('input.jpg')
  .overlayWith(null, create: {
    width: 16,
    height: 32,
    channels: 4,
    background: rgba
  })...

where rgb and rgba are parsed by the color module, the same approach used by the existing background function.

@strarsis
Copy link

[email protected] doesn't seem to support it yet.

@lovell
Copy link
Owner

lovell commented Sep 14, 2016

@strarsis That's correct. My comment about v0.16.0 was that it provided the ground work for this feature request.

@5im0n
Copy link

5im0n commented Jan 13, 2017

Is this feature gonna be available in a next release ?

@lovell
Copy link
Owner

lovell commented Jan 13, 2017

@5im0n I'm happy to help with a PR if you're able.

@lovell
Copy link
Owner

lovell commented Mar 11, 2017

Commit 1aa053c adds the ability to create a blank image using the API described by comment #470 (comment) above. This will be available in v0.17.3.

@lovell lovell added this to the v0.17.3 milestone Mar 11, 2017
@lovell
Copy link
Owner

lovell commented Apr 1, 2017

v0.17.3 now available, thanks for all the suggestions.

@lovell lovell closed this as completed Apr 1, 2017
@wmertens
Copy link

wmertens commented Apr 23, 2017

To combine multiple images, I did this instead of the empty canvas:

	for (let i = 1, left = singleWidth; i < imgCount; i++, left += singleWidth) {
		// only one overlay per pipeline
		if (i > 1) {combined = sharp(await combined.toBuffer())}
		combined.overlayWith(imgBufs[i], {left, top: 0})
	}

so basically forcing sharp to process the pipeline once there is more than one overlay. Async/await makes this nice, with promises this code would be a bit harder.

(incidentally, I wonder if there would be a use for a .perform() call that runs the pipeline and starts a new one?)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants