ruby picture download verification - ruby

I would like to know if it is possible to check if a picture downloaded using open-uri () was downloaded correctly?
There are 2 cases I would like to manage:
1. the picture is at least 80% black (in this case, it is an error)
2. the picture is simply unreadable by picture reader (ex: Ephoto on Linux)
Ideally, the code would look somewhat like this
pic_buffer = open(my_link, "User-Agent" => "Ruby/#{RUBY_VERSION}")
if functionCheckPictureDownloadedCorrectly(pic_buffer) == false
abort("file is unreadable")
end
puts "file is good, saving it"
File.open(name_buffer + ".jpg", 'wb') do |pic|
pic << pic_buffer.read
end
Note : I am only downloading .jpeg pictures

Related

Pillow: converting a TIFF from greyscale 16 bit to 8 bit results in fully white image

I know that there are multiple similar questions on SO, but I have tried multiple proposed solutions to no avail.
I have the following TIFF image that opens in Pillow as type='I;16'.
Google Drive link
Based on this SO question, I wrote this code to convert it:
def tiff_force_8bit(image, **kwargs):
if image.format == 'TIFF' and image.mode == 'I;16':
array = np.array(image)
normalized = (array.astype(np.uint16) - array.min()) * 255.0 / (array.max() - array.min())
image = Image.fromarray(normalized.astype(np.uint8))
return image
However, the result is a completely white image.
I have tried other solutions too, such as this:
table = [i/256 for i in range(65536)]
image = image.point(table, 'L')
with the same result: full white out.
Can anyone shed some light?
Thanks!
There's nothing wrong with your code. If you run:
# Open image
im = Image.open('NGC 281 11-01-2021 Ha 1.15.tif')
# Force to 8-bit
res = tiff_force_8bit(im)
# Check min and max of result
res.getextrema() # prints (0,255) as expected
# Save as PNG
res.save('result.png')
# Display it
res.show()
I can only guess there is a problem with your installation or the way you display the result.

ruby base64 decode function limited 4KB in Windows

I want to write png file from A xml including encoded png image by base64. First I tried like this
if (captureImageB64.length > 1)
pngFile = File.new("xxx.png", "wb")
captureImageB64.unpack('m').first
pngFile.close
end
but this code makes 4KB png image. captureImageB64.unpack('m').first.length is 4096. so.. next version is
if (captureImageB64.length > 1)
pngFile = File.new("xxx.png", "wb")
i = 0
while i < captureImageB64.length
pngFile.write(captureImageB64.slice(i, 12).unpack('m').first)
i += 12
end
pngFile.close
end
it makes broken png file. until 4096 is fine. How can I write the right file ?
I'm working on Windows7, ruby 2.0(x86).
Update:
I found padding string(==) in image file encoded base64. So it was encoded each 4096 byte! No one told me about that... I'll make a new encoder component.

How to remove link tag from image using Nokogiri

I'm parsing an HTML document using Nokogiri. The code contain several images like this:
<img alt="alternative-text" border="0" height="427" src="http://url_to_my_photo.jpg?" title="Image Title" width="640">
I'm trying to save that image to my S3 storage, change the style and remove the link. All the images have the css tag ".post-body img".
So far, the closest I got is this:
#doc.css(".post-body img").each do |image|
#new_photo = Photo.create!(
#Params required to save and upload the photo to S3.
...
...
)
# The url of the photo upload to S3 is #new_photo.photo.url
image['src']= #new_photo.photo.url
image['class'] = "my-picture-class"
image.parent['src] = '#'
puts image.parent.content
#doc.to_html
end
This removes the link to the big photo but obviously it isn't a good solution.
I've tried to replace the parent using image.parent << image as suggested on http://rubyforge.org/pipermail/nokogiri-talk/2009-June/000333.html but doesn't do anything and image.parent = image returns "Could not reparent node (RuntimeError)"
To convert that mailing list example over to apply to your situation, you have to remember that node is the node they are trying to get rid of, which in your case is image.parent.
So instead of image.parent['src] = '#' you should try:
link = image.parent
link.parent << image
link.remove
Edit:
Actually, the above code would probably move all the images to the bottom of whatever element contains the link, so try this instead:
link = image.parent
link.replace(image)

Group text and images as a block with Prawn?

I'm trying to build a PDF from user-generated content and I have a chunk of information that should be grouped together. I know of the group method to make sure text all gets rendered together, but this doesn't seem to work with a mix of text and images. Is there something that can do this with Prawn, or do I need to try to calculate cursor position and manually linebreak?
Edit: For illustration of what I'm looking to do:
pdf = PDF::Document.new
20.times do
pdf.group do
pdf.text "Something"
pdf.image "path/to/image.jpg"
pdf.text Time.now.to_s
end
end
And I would expect to not ever have "Something" on one page and the image on the next, but that is what I see. Is there some way I can achieve what I want?
Okay, I've figured it out. Prawn does not seem to take the image height into account when grouping, but you can hack your way around it:
pdf.group do
pdf.text "Best regards, (...)"
pdf.image "#{Rails.root}/vendor/signature.jpg", {
:height => 30,
:at => [0, pdf.y.to_i - #bottom_margin]
}
pdf.move_down(35)
pdf.text " "
end
The trick is to use absolute positioning for the image, and move the text cursor down manually.

How to create a multi-page PDF-file with Gnuplot?

I make a dozen of plots with Gnuplot on Mac via ruby-gnuplot. If I re-run my ruby script, then the number of open windows with the plots doubles. If I could just output all these plots in a PDF opened in Preview, then the file would be automatically updated after every re-run and I don't need to bother closing the numerous windows.
Currently I can achieve this only with one plot per PDF-file:
Gnuplot.open do |gp|
Gnuplot::Plot.new(gp) do |plot|
plot.arbitrary_lines << "set terminal pdf \n set output 'figures.pdf'"
# ...
end
end
How can I make a single PDF with all my figures by Gnuplot?
Hmm, at least on gnuplot for UN*x, multipage output for postscript and PDF always was the default - as long as you don't either change the terminal type nor reassign the output file, everything you plot ends up on a new page.
I.e. you do:
set terminal pdf
set output "multipageplot.pdf"
plot x, x*x
plot sin(x), cos(x)
set output ""
and you end up with two pages in the PDF file, one containing line/parabola, the other sine/cosine.
To clarify: The important thing is to issue all the plot commands in sequence, without changing the output file nor changing the terminal type. Gnuplot won't append to an existing PDF file.
I make thousands of plots with ruby-gnuplot and use a gem called prawn to compile them into a pdf. The following is a code snippet using prawn, that includes some useful features:
require 'prawn'
def create_pdf
toy_catalogue = #toy_catalogue
full_output_filename ||= "#{output_path}/#{pre-specified_filename_string}"
Prawn::Document.generate(full_output_filename, :page_layout => :portrait, :margin => 5, :skip_page_creation => false, :page_size => [595, 1000]) do
toy_catalogue.each do |toy|
start_new_page
image toy[:plan_view], :at => [0,900], :width => 580
image toy[:front_view], :at => [0, 500], :width => 585
font_size(20) { draw_text toy[:name], :at => [5, 920] }
draw_text "production_date = #{toy[:date]}", :at => [420, 930]
end
end
end
That should be easy enough to adapt to your purposes.

Resources