How to save a html5 canvas.toDataURL as a png file on the server

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
8 messages Options
Reply | Threaded
Open this post in threaded view
|

How to save a html5 canvas.toDataURL as a png file on the server

Bob Nemec
(I also posted this in stack overflow)

I have an image that users can annotate on the browser. I can access the image using
    canvas.toDataURL() 
...I'd like to add a 'save' option for the user to save the image on the server.

This question has been answered for php...
    file_put_contents('test.png', base64_decode(substr($data, strpos($data, ",")+1))); 
...what I need is a Seaside callback with the PNG file contents.

Is there a way to do this in Seaside?

Thanks,
Bob 

_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Bob Nemec
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Johan Brichau-2
I also responded this on stack overflow.

Depending on how you want your website to behave, I guess there are multiple ways of doing it. Here is the raw sample of one possibility I can think of using a jQuery ajax callback:

html jQuery ajax 
callback: [:value | (FileStream newFileNamed: 'test.png') nextPutAll: value base64Decoded ] 
value: (JSStream on: 'canvas.toDataURL()')

I did not test this myself. Maybe the filestream needs to be sent the #binary message to make a correct png file. Let me know if there are troubles.

Hope it helps.

On 26 Jul 2011, at 22:01, Bob N. wrote:

(I also posted this in stack overflow)

I have an image that users can annotate on the browser. I can access the image using
    canvas.toDataURL() 
...I'd like to add a 'save' option for the user to save the image on the server.

This question has been answered for php...
    file_put_contents('test.png', base64_decode(substr($data, strpos($data, ",")+1))); 
...what I need is a Seaside callback with the PNG file contents.

Is there a way to do this in Seaside?

Thanks,
Bob 
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside


_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Bob Nemec
Thanks Johan, feels like I almost have it. 

I'm doing this work in VW. Could someone show the VW equivalent of #base64Decoded? Or is it in some Seaside compatibility library? I'm using 'Seaside 3.0 - 87' from the Cincom public repository.  

In VW, I see the callback value content as a String starting with 'data:image/png;base64,iVBORw...'. 

I'm also trying this in Pharo to help understand the  #base64Decoded method, but the #onClick: code is not being triggered as it is in VW...

html button
onClick: (html jQuery ajax 
callback: [:value | 
Transcript cr; show: 'Save button callback triggered'.
(FileStream newFileNamed: ('c:\data\sketchpad_', Time now asSeconds printString ,'.png')) 
nextPutAll: value base64Decoded] 
value: (JSStream on: 'sketchpadCanvas.toDataURL()'));
with: 'Save'.

...am I missing something obvious?

I have another test button rendered that works fine...
html button
onClick: 'window.open(sketchpadCanvas.toDataURL())'; 
with: 'Open'.

Thanks for any help,
Bob

On Wed, Jul 27, 2011 at 4:19 AM, Johan Brichau <[hidden email]> wrote:
I also responded this on stack overflow.

Depending on how you want your website to behave, I guess there are multiple ways of doing it. Here is the raw sample of one possibility I can think of using a jQuery ajax callback:

html jQuery ajax 
callback: [:value | (FileStream newFileNamed: 'test.png') nextPutAll: value base64Decoded ] 
value: (JSStream on: 'canvas.toDataURL()')

I did not test this myself. Maybe the filestream needs to be sent the #binary message to make a correct png file. Let me know if there are troubles.

Hope it helps.

On 26 Jul 2011, at 22:01, Bob N. wrote:

(I also posted this in stack overflow)

I have an image that users can annotate on the browser. I can access the image using
    canvas.toDataURL() 
...I'd like to add a 'save' option for the user to save the image on the server.

This question has been answered for php...
    file_put_contents('test.png', base64_decode(substr($data, strpos($data, ",")+1))); 
...what I need is a Seaside callback with the PNG file contents.

Is there a way to do this in Seaside?

Thanks,
Bob 
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside


_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside



_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Bob Nemec
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Philippe Marschall
2011/7/27 Bob N. <[hidden email]>:
> Thanks Johan, feels like I almost have it.
> I'm doing this work in VW. Could someone show the VW equivalent of
> #base64Decoded? Or is it in some Seaside compatibility library? I'm using
> 'Seaside 3.0 - 87' from the Cincom public repository.

GRPlatform current base64Decode:

Cheers
Philippe
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Bob Nemec
Thanks. Here is what I'm now using... 

html jQuery ajax 
callback: [:value | 
| writestream |
writestream := (('c:\data\sketchpad_', Time now asSeconds printString ,'.png') asFilename withEncoding:  #binary) writeStream.
[writestream nextPutAll: (Seaside.GRPlatform current base64Decode: value) asByteArray] ensure: [writestream close]] 
value: (Javascript.JSStream on: 'sketchpadCanvas.toDataURL()')

...but I got an exception in Net.MimeScanner class>>decodeBase64From:to:in:on: 

aString size is 17074 and the code iterates over the string, checking a #limit which is set to the string size. But the code checks for index + 3 which exceeds the string size.  Hacking the code so the limit is set to size - 3 works, but the resulting image is not a valid PNG file.

Is there is way to test the decoded content to see if it is a valid PNG file?

I also tried toDataURL("image/jpeg") which created an output starting with 'data:image/jpeg;base64' but that also saved an invalid image file.

Bob 

On Wed, Jul 27, 2011 at 10:23 AM, Philippe Marschall <[hidden email]> wrote:
2011/7/27 Bob N. <[hidden email]>:
> Thanks Johan, feels like I almost have it.
> I'm doing this work in VW. Could someone show the VW equivalent of
> #base64Decoded? Or is it in some Seaside compatibility library? I'm using
> 'Seaside 3.0 - 87' from the Cincom public repository.

GRPlatform current base64Decode:

Cheers
Philippe
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside


_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Bob Nemec
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Bob Nemec
In reply to this post by Johan Brichau-2
FWIW: I tried saving the contents of the JSStream string directly in Pharo and I get an invalid PNG file.

| string |
string := 'data:image/png;base64... '. "long string from toDataURL()"
(FileStream newFileNamed: ('c:\data\sketchpad_test.png')) binary nextPutAll: string base64Decoded 

Bob

On Wed, Jul 27, 2011 at 4:19 AM, Johan Brichau <[hidden email]> wrote:
I also responded this on stack overflow.

Depending on how you want your website to behave, I guess there are multiple ways of doing it. Here is the raw sample of one possibility I can think of using a jQuery ajax callback:

html jQuery ajax 
callback: [:value | (FileStream newFileNamed: 'test.png') nextPutAll: value base64Decoded ] 
value: (JSStream on: 'canvas.toDataURL()')

I did not test this myself. Maybe the filestream needs to be sent the #binary message to make a correct png file. Let me know if there are troubles.

Hope it helps.

On 26 Jul 2011, at 22:01, Bob N. wrote:

(I also posted this in stack overflow)

I have an image that users can annotate on the browser. I can access the image using
    canvas.toDataURL() 
...I'd like to add a 'save' option for the user to save the image on the server.

This question has been answered for php...
    file_put_contents('test.png', base64_decode(substr($data, strpos($data, ",")+1))); 
...what I need is a Seaside callback with the PNG file contents.

Is there a way to do this in Seaside?

Thanks,
Bob 
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside


_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside



_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Bob Nemec
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Johan Brichau-2
In reply to this post by Bob Nemec
I don't have access to a smalltalk image right now, but my guess is you need to strip the string of the mine type declaration first. The php example does the same thing: it takes the substring after the comma before decoding and writing to the file.

--
Johan

On 27 Jul 2011, at 17:43, "Bob N." <[hidden email]> wrote:

Thanks. Here is what I'm now using... 

html jQuery ajax 
callback: [:value | 
| writestream |
writestream := (('c:\data\sketchpad_', Time now asSeconds printString ,'.png') asFilename withEncoding:  #binary) writeStream.
[writestream nextPutAll: (Seaside.GRPlatform current base64Decode: value) asByteArray] ensure: [writestream close]] 
value: (Javascript.JSStream on: 'sketchpadCanvas.toDataURL()')

...but I got an exception in Net.MimeScanner class>>decodeBase64From:to:in:on: 

aString size is 17074 and the code iterates over the string, checking a #limit which is set to the string size. But the code checks for index + 3 which exceeds the string size.  Hacking the code so the limit is set to size - 3 works, but the resulting image is not a valid PNG file.

Is there is way to test the decoded content to see if it is a valid PNG file?

I also tried toDataURL("image/jpeg") which created an output starting with 'data:image/jpeg;base64' but that also saved an invalid image file.

Bob 

On Wed, Jul 27, 2011 at 10:23 AM, Philippe Marschall <[hidden email]> wrote:
2011/7/27 Bob N. <[hidden email]>:
> Thanks Johan, feels like I almost have it.
> I'm doing this work in VW. Could someone show the VW equivalent of
> #base64Decoded? Or is it in some Seaside compatibility library? I'm using
> 'Seaside 3.0 - 87' from the Cincom public repository.

GRPlatform current base64Decode:

Cheers
Philippe
_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside

_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside

_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Reply | Threaded
Open this post in threaded view
|

Re: How to save a html5 canvas.toDataURL as a png file on the server

Bob Nemec
Thanks. Nice catch. 
Adjusting the string also avoids the VW index range error in Net.MimeScanner class>>decodeBase64From:to:in:on:

This code works in VW (with string copy hack).

html button
onClick: (html jQuery ajax 
callback: [:value | 
| writestream string |
writestream := ('c:\data\sketchpad_image.png' asFilename withEncoding:  #binary) writeStream.
string := value copyFrom: 23 to: value size.
[writestream nextPutAll: (Seaside.GRPlatform current base64Decode: string) asByteArray] 
                                       ensure: [writestream close] ] 
value: (Javascript.JSStream on: 'sketchpadCanvas.toDataURL()'));
with: 'Save'.

Bob

On Wed, Jul 27, 2011 at 3:16 PM, Johan Brichau <[hidden email]> wrote:
I don't have access to a smalltalk image right now, but my guess is you need to strip the string of the mine type declaration first. The php example does the same thing: it takes the substring after the comma before decoding and writing to the file.

--
Johan

On 27 Jul 2011, at 17:43, "Bob N." <[hidden email]> wrote:

Thanks. Here is what I'm now using... 

html jQuery ajax 
callback: [:value | 
| writestream |
writestream := (('c:\data\sketchpad_', Time now asSeconds printString ,'.png') asFilename withEncoding:  #binary) writeStream.
[writestream nextPutAll: (Seaside.GRPlatform current base64Decode: value) asByteArray] ensure: [writestream close]] 
value: (Javascript.JSStream on: 'sketchpadCanvas.toDataURL()')

...but I got an exception in Net.MimeScanner class>>decodeBase64From:to:in:on: 

aString size is 17074 and the code iterates over the string, checking a #limit which is set to the string size. But the code checks for index + 3 which exceeds the string size.  Hacking the code so the limit is set to size - 3 works, but the resulting image is not a valid PNG file.

Is there is way to test the decoded content to see if it is a valid PNG file?

I also tried toDataURL("image/jpeg") which created an output starting with 'data:image/jpeg;base64' but that also saved an invalid image file.

Bob 

On Wed, Jul 27, 2011 at 10:23 AM, Philippe Marschall <[hidden email][hidden email]> wrote:
2011/7/27 Bob N. <[hidden email][hidden email]>:
> Thanks Johan, feels like I almost have it.
> I'm doing this work in VW. Could someone show the VW equivalent of
> #base64Decoded? Or is it in some Seaside compatibility library? I'm using
> 'Seaside 3.0 - 87' from the Cincom public repository.

GRPlatform current base64Decode:

Cheers
Philippe
_______________________________________________
seaside mailing list
[hidden email][hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside

_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside

_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside



_______________________________________________
seaside mailing list
[hidden email]
http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside
Bob Nemec