Inlining images for people page

pull/1/head
Oliver Kennedy 2018-04-27 20:25:43 -04:00
parent 49636951d2
commit 7b3382fa9d
7 changed files with 101 additions and 21 deletions

View File

@ -264,4 +264,8 @@ task "email-lab" do
"#{name} <#{data["ubit"]}@buffalo.edu>"
end
(system("open", "-a", "Mail", "mailto://#{members.join(", ")}"))
end
task :test do
puts ImageSmith::img("assets/people/oliver.jpg", bounding_box: [50,50], inline: true)
end

View File

@ -3,6 +3,7 @@ require 'redcarpet'
require 'erb'
require 'pipeline.rb'
require 'date'
require 'image'
class Array
def where

82
lib/image.rb Normal file
View File

@ -0,0 +1,82 @@
require "base64"
require "tempfile"
require "open-uri"
module ImageSmith
def ImageSmith::img(source, params = {})
puts "Render #{source}"
temp_file = nil
if source.start_with?("http") then
temp_file = Tempfile.new("img")
open(source) do |f|
temp_file.write(f.read)
end
temp_file.flush
puts "Downloading to #{temp_file.path}"
source = temp_file.path
end
padding = { left: 0, right: 0, top: 0, bottom: 0 }
metadata = identify(source)
size = metadata[:size].clone
conversion_params = []
uri = source
if params.has_key? :bounding_box
box = params[:bounding_box]
scale = size.zip(params[:bounding_box])
.map { |base, target| target.to_f / base.to_f }
.min
size.map!{ |dim| (dim * scale).to_i }
conversion_params = ["-resize", size.join("x")]
errors = box.zip(size).map { |target, actual| target - actual }
padding[:left] += errors[0]/2
padding[:right] += errors[0]/2
padding[:top] += errors[1]/2
padding[:bottom] += errors[1]/2
end
if params.fetch(:inline, false)
# fmt = case metadata[:format]
# when :JPEG then "image/jpeg"
# when :GIF then "image/gif"
# when :PNG then "image/png"
# else raise "Unknown format #{metadata[:format]}"
# end
fmt = "image/png"
data = IO.popen(["convert", source]+conversion_params+["-strip", "png:-"]) do |c|
Base64.encode64(c.read)
end
uri = "data:#{fmt};base64,#{data}"
p uri.length
end
style = {
padding: [:top, :right, :bottom, :left].map { |dir| padding[dir].to_s+"px" }.join(" ")
}
fields = {
src: uri,
width: size[0],
height: size[1],
style: style.map { |k, v| "#{k}:#{v}" }.join(';')
}
return "<img #{fields.map { |k, v| "#{k}=\"#{v}\"" }.join(" ") } />"
end
def ImageSmith::identify(path)
IO.popen(["identify", path]) do |i|
raw = i.read.chomp.split(/ +/)
metadata = {
path: raw[0],
format: raw[1].to_sym,
size: raw[2].split(/x/).map { |x| x.to_i },
raw: raw
}
return metadata
end
end
end

View File

@ -1,4 +1,3 @@
require "rubygems"
require "prawn"
require "prawn/measurement_extensions"
require "util.rb"

View File

@ -118,7 +118,7 @@ class Array
Math.sqrt((avg ** 2 - (map{|i| i.to_f ** 2}.avg)).abs)
end
def reduce(&reducer)
def my_reduce(&reducer)
ret = Hash.new;
each do |k,v|
ret[k] = Array.new unless ret.has_key? k;
@ -289,7 +289,7 @@ class Array
map { |x| [x, 0] }.
to_h.
join(map { |x| (x.to_f / bin_width).to_i * bin_width }.
reduce { |k,v| v.count },
my_reduce { |k,v| v.count },
:left
).
map { |bin, cnt| [bin, cnt.compact.sum] }.

View File

@ -4,7 +4,7 @@ title: Publications
<div style="height: 20px">&nbsp;</div>
<div class="paper_list">
<% $db["publications"].map { |pub| [pub["year"].to_i, pub] }.reduce.each do |year, pubs| %>
<% $db["publications"].map { |pub| [pub["year"].to_i, pub] }.my_reduce.each do |year, pubs| %>
<div class="panel">
<div class="panel-heading">
<center><h2><%= year %></h2></center>

View File

@ -5,24 +5,18 @@ title: Members and Affiliates
<h1>Lab Members</h1>
<% $db["lab/members"].each do |member, data| %>
<div class="person" style="vertical-align: middle;">
<%
pic = data.fetch("pic", { "file" => "../assets/people/missing.png", "width" => 275, "height" => 438 })
pic_scale = 50.0 / [ pic["width"].to_i, pic["height"].to_i ].max
padding_width = [ (50.0 - pic["width"].to_i * pic_scale) / 2, 0 ].max
padding_height = [ (50.0 - pic["height"].to_i * pic_scale) / 2, 0 ].max
<%=
img = "../assets/people/missing.png"
if data.has_key? "pic"
img = data["pic"]
img = img["file"] if img.is_a? Hash
img = img.gsub(/https:\/\/odin\.cse\.buffalo\.edu\//, "")
end
ImageSmith.img(img,
bounding_box: [50,50],
inline: true
)
%>
<img
src="<%= pic["file"] %>"
width="<%= pic["width"].to_i * pic_scale %>"
height="<%= pic["height"].to_i * pic_scale %>"
style="
margin-left: <%= padding_width %>px;
margin-right: <%= padding_width + 20 %>px;
margin-top: <%= padding_height %>px;
margin-bottom: <%= padding_height %>px;
"
/>
<a href="<%= if data["link_relative"] then File.join(root_path, data["link"]) else data["link"] end %>"><%= member %></a>
<span class="status" style="padding-top: 15px;">
<%= data["status"] %>