Ruby 的快樂 - CGI 上的圖片處理成功!


花了差不多 72 小時,終於解決了一直想不通的東西,今天終於在回家後,得到了一個進展,原來網上抓下的代碼有兩個地方錯了,意想不到,昨天試了很久都沒有發現,可能是處理都是輸出 500 吧..

當問題修正後,一直都想不通,為何會輸出不是亂碼的(圖片的碼),當離開電腦後,再回望一下代碼,人清醒了看的果然就不同了,原來是程式部份將原來的 “puts” 打成了 “p” ..真的汗字一大個..

雖然問題修正了,可是另一個問題又出現了,發現輸出的圖片顯示的不清析,不知道為什麼的,圖片倒是圖片,可是為何人家的網上系統都正常清楚,而我的卻不像樣,而在 SR 大的回應和閒談後,才發現原來是輸出時沒將輸出檔頭設為 binmode …真的又汗了..

都只怪 PHP 放縱了我 = = ..我太依賴 PHP …

基本上測試顯示圖片的代碼只要如下 :

1
2
3
4
5
6
7
8
9
10
11
12
13
#!/ruby/bin/ruby

require "image.rb" #此檔案為生成圖片的類
captcha = Captcha.new(4)

$stdout.binmode
puts "Content-type: image/jpeg\n"
puts "Content-Disposition: inline; filename=callimage.jpg\n\n"
begin
puts captcha.code_image
rescue => e
p e.message
end

關於安裝方面,請看下一頁

以下為在 Window 上安裝 RMagick 的方法

1
2
3
4
5
6
1. 先到 http://rubyforge.org/frs/?group_id=12&release_id=8170
2. 下載 RMagick 1.14.1 binary gem for Ruby 1.8.5 > RMagick-1.14.1_IM-6.3.0-7-Q8.zip
3. 解壓縮得到 rmagick-1.14.1-win32.gem
4. 打開 cmd
5. 執行 gem rmagick-1.14.1-win32.gem
6. 安裝那個 ImageMagick.exe 就可以

至於 Linux 的方法如下吧 (CentOS, 都用 Yum, 不 tar 啦 = =) :

1
2
3
4
5
6
7
8
9
10
11
12
13
14
安裝 ImageMagick
>> yum install ImageMagick-devel
>> 大大力的拍下 Enter 鍵

安裝 Freetype
>> yum install freetype-devel
>> 大大力的拍下 Enter 鍵

安裝 ghostscript
>> yum -y install ghostscript
>> 大大力的拍下 Enter 鍵

安裝 RMagick
>> gem install rmagick

而下一頁為第 1 頁的程式碼 (PS. 這是從網上抓回來,但是經過了我的修改後才可以正常使用,最起碼我是這樣啦 = =)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
require 'rubygems'
require 'RMagick'

class Captcha
# 2 個類的屬性
attr_reader :code, :code_image

def initialize(len)
begin
#chars = ('a'..'z').to_a-['a','e','i','o','u']
code_array =[]
codex =""
rr =0
normalweight=100
boldweight =100

# 隨機生成 5 個大寫字母
1.upto(5) {
rr = 65+rand(25)
code_array << rr
}

#code_array=[rand(rr).chr,rand(rr).chr,rand(rr).chr,rand(rr).chr]
#1.upto(len) {code_array << chars[rand(chars.length)]}

# 生成 granite 樣式的背景
granite = Magick::ImageList.new('granite:')

# 定義一個畫布
canvas = Magick::ImageList.new

# granite 放在畫布上
canvas.new_image(24*4,50, Magick::TextureFill.new(granite))

# 文字
text = Magick::Draw.new

#text.font_family = 'times'

# 文字大小
text.pointsize = 20
cur = 10

code_array.each{|c|
c = c.to_i
c = c.chr

# ACS 碼(數字)轉為字母
codex=codex+c

#rand(10) > 5 ? rot=rand(Wobble) : rot = -rand(Wobble)
rand(10) > 5 ? weight = normalweight : weight = boldweight

ra=1000

while ra<100000
ra=rand(999999)
end

rn = '#'+ra.to_s

# text 對象放在 canvas 上
text.annotate(canvas,20,20, cur,18,c){
self.rotation = rand(30) # 旋轉角度
self.font_weight = weight
self.fill = rn # text 文字顏色
}

cur += 15
}

@code = codex

# 生成文字(字符串格式)
@code_image = canvas.to_blob{
# 生成圖片 (二進制格式)
self.format="jpg"
}
rescue => e
p e.message
end
end
end