KnigaRead.com/
KnigaRead.com » Компьютеры и Интернет » Программирование » Хэл Фултон - Программирование на языке Ruby

Хэл Фултон - Программирование на языке Ruby

На нашем сайте KnigaRead.com Вы можете абсолютно бесплатно читать книгу онлайн Хэл Фултон, "Программирование на языке Ruby" бесплатно, без регистрации.
Перейти на страницу:

Разрешение: 72.0/72.0 пикселей на дюйм

2.0 pixels per inch

Посмотрим, как именно работает эта программа. Для чтения файла мы вызываем метод Magick::Image::read. Поскольку один файл (например, анимированный GIF) может содержать несколько изображений, эта операция возвращает массив изображений (мы получаем лишь первое, вызывая метод first). Для чтения файла можно также воспользоваться методом Magick::ImageList.new.

У объекта, представляющего изображение, есть ряд методов чтения: format (название формата изображения), filesize, depth и другие. Не так очевидно, что для получения ширины и высоты изображения служат методы columns и rows соответственно (поскольку изображение представляется в виде прямоугольной таблицы пикселей). Разрешение представляется двумя числами, так как может быть разным по вертикали и горизонтали.

Можно получить и другие метаданные об изображении. Подробнее об этом вы можете прочитать в онлайновой документации по RMagick.

Часто возникает необходимость перевести изображение из одного формата в другой. В RMagick это проще всего сделать, прочитав изображение из файла в одном из поддерживаемых форматов и записав его в другой файл. Новый формат определяется расширением имени файла. Понятно, что «за кулисами» при этом происходит преобразование данных. Пример:

img = Magick::Image.read("smallpic.jpg")

img.write("smallpic.gif") # Преобразовать в формат GIF.

Иногда нужно изменить размер изображения (сделать его больше или меньше). Для этого обычно применяется один из четырех методов: thumbnail, resize, sample и scale. Все они принимают либо число с плавающей точкой (коэффициент масштабирования), либо два числа (новые размеры в пикселях). Различия между этими методами продемонстрированы в листинге 15.7. Если вас волнует быстродействие, рекомендую провести тесты на своем компьютере, используя собственные данные.

Листинг 15.7. Четыре способа масштабирования изображения

require 'RMagick'


img = Magick::ImageList.new("vw.jpg")


# Все эти методы могут принимать либо один параметр - коэффициент

# масштабирования, либо два - ширину и высоту.


# Метод thumbnail самый быстрый, особенно если нужно получить очень

# маленькое изображение.

pic1 = img.thumbnail(0.2)   # Уменьшить до 20%.

pic2 = img.thumbnail(64,48) # Новый размер - 64x48 пикселей.


# resize работает со средней скоростью. Если заданы третий и четвертый

# параметры, то они интерпретируются как фильтр и размывание

# соответственно. По умолчанию подразумевается фильтр LanczosFilter

# и коэффициент размывания 1.0.


pic3 = img.resize(0.40)     # Уменьшить до 40%.

pic4 = img.resize(320,240)  # Новый размер - 320x240.

pic5 = img.resize(300,200,Magick::LanczosFilter,0.92)


# Метод sample также имеет среднее быстродействие (и не выполняет

# интерполяцию цветов).


pic6 = img.sample(0.35)     # Уменьшить до 35%.

pic7 = img.sample(320,240)  # Новый размер - 320x240.


# Метод scale в моих тестах оказался самым медленным.


pic8 = img.scale(0.60)      # Уменьшить до 60%.

pic9 = img.scale(400,300)   # Новый размер - 400x300.

Изображения можно подвергать и многим другим трансформациям. Некоторые просты и понятны, другие гораздо сложнее. В следующем разделе мы рассмотрим несколько интересных трансформаций и специальных эффектов.

15.3.2. Специальные эффекты и трансформации

Над изображением можно выполнять следующие операции: зеркально отражать, инвертировать цвета, поворачивать, растягивать, перекрашивать и т.д. В RMagick есть десятки методов для выполнения подобных операций, причем многие из них еще и настраиваются путем указания параметров.

В листинге 15.8 показано 12 различных эффектов. Метод example принимает имя файла, символ, соответствующий методу, и имя нового файла; он читает файл, вызывает метод и записывает результат в новый файл. Сами методы (скажем, do_rotate) по большей части просты — они получают изображение и вызывают его метод экземпляра (а возвращают результат трансформации).

Листинг 15.8. Двенадцать специальных эффектов и трансформаций

require 'Rmagick'


def do_flip(img)

 img.flip

end


def do_rotate(img)

 img.rotate(45)

end


def do_implode(img)

 img = img.implode(0.65)

end


def do_resize(img)

 img.resize(120,240)

end


def do_text(img)

 text = Magick::Draw.new

 text.annotate(img, 0, 0, 0, 100, "HELLO") do

  self.gravity = Magick::SouthGravity

  self.pointsize = 72

  self.stroke = 'black'

  self.fill = '#FAFAFA'

  self.font_weight = Magick::BoldWeight

  self.font_stretch = Magick::UltraCondensedStretch

 end

 img

end


def do_emboss(img)

 img.emboss

end


def do_spread(img)

 img.spread(10)

end


def do_motion(img)

 img.motion_blur(0,30,170)

end


def do_oil(img)

 img.oil_paint(10)

end


def do_charcoal(img)

 img.charcoal

end


def do_vignette(img)

 img.vignette

end


def do_affine(img)

 spin_xform = Magick::AffineMatrix.new(1, Math::PI/6, Math::PI/6, 1, 0, 0)

 img.affine_transform(spin_xform) # Применить преобразование.

end


###


def example(old_file, meth, new_file)

 img = Magick::ImageList.new(old_file)

 new_img = send(meth, img)

 new_img.write(new_file)

end


example("smallpic.jpg", :do_flip,    "flipped.jpg")

example("smallpic.jpg", :do_rotate,  "rotated.jpg")

example("smallpic.jpg", :do_resize,  "resized.jpg")

example("smallpic.jpg", :do_implode, "imploded.jpg")

example("smallpic.jpg", :do_text,    "withtext.jpg")

example("smallpic.jpg", :do_emboss,  "embossed.jpg")


example("vw.jpg", :do_spread,   "vw_spread.jpg")

example("vw.jpg", :do_motion,   "vw_motion.jpg")

example("vw.jpg", :do_oil,      "vw_oil.jpg")

example("vw.jpg", :do_charcoal, "vw_char.jpg")

example("vw.jpg", :do_vignette, "vw_vig.jpg")

example("vw.jpg", :do_affine,   "vw_spin.jpg")

Мы продемонстрировали методы flip, rotate, implode, resize, annotate и др. Результаты представлены на рис. 15.2.

Рис. 15.2. Двенадцать специальных эффектов и трансформаций

О том, какие еще существуют трансформации изображений, читайте в онлайновой документации.

15.3.3. API рисования

В RMagick имеется развитый API для рисования линий, многоугольников и различных кривых. Он поддерживает заливку, полупрозрачность, выбор цвета, шрифтов, вращение, растяжение и другие операции.

Чтобы получить представление об имеющихся возможностях, рассмотрим простой пример.

В листинге 15.9 приведена программа, которая рисует на заданном фоне сетку, а поверх нее несколько закрашенных геометрических фигур. Черно-белое изображение, получившееся в результате, показано на рис. 15.3.

Листинг 15.9. Простая программа рисования

require 'RMagick'


img = Magick::ImageList.new

img.new_image(500, 500)


purplish = "#ff55ff"

yuck = "#5fff62"

bleah = "#3333ff"


line = Magick::Draw.new

50.step(450,50) do |n|

 line.line(n,50, n,450) # Вертикальная прямая.

 line.draw(img)

 line.line(50,n, 450,n) # Горизонтальная прямая.

 line.draw(img)

end


# Нарисовать круг.

cir = Magick::Draw.new

cir.fill(purplish)

cir.stroke('black').stroke_width(1)

cir.circle(250,200, 250,310)

cir.draw(img)


rect = Magick::Draw.new

rect.stroke('black').stroke_width(1)

rect.fill(yuck)

rect.rectangle(340,380,237,110)

rect.draw(img)


tri = Magick::Draw.new

tri.stroke('black').stroke_width(1)

tri.fill(bleah)

tri.polygon(90,320,160,370,390,120)

tri.draw(img)


img = img.quantize(256,Magick::GRAYColorspace)


img.write("drawing.gif")

Рис. 15.3. Простая программа рисования

Рассмотрим эту программу подробнее. Сначала мы создаем «пустое» изображение методом ImageList.new, а потом вызываем для возвращенного объекта метод new_image. Можно считать, что мы получили «чистый холст» заданного размера (500×500 пикселей).

Для удобства определим несколько цветов с понятными именами, например purplish и yuck. Цвета определяются так же, как в HTML. Базовая библиотека xMagick сама распознает много названий цветов, например, red и black; если сомневаетесь, пробуйте или задавайте цвета в шестнадцатеричном виде.

Перейти на страницу:
Прокомментировать
Подтвердите что вы не робот:*