每周源代码29 – Ruby,Shoes和第一个Ruby病毒
[原文发表地址] The Weekly Source Code 29 - Ruby and Shoes and the First Ruby Virus
[原文发表时间] 2008-06-24 07:47
上周我在挪威参加挪威开发者会议,所以恐怕这个月的每周源代码要变成双周源代码了。一次国外旅行能让人放松下来,感觉太棒了。这次旅行让我完全沉浸其中。不过我还是在慢慢地回归到现实的生活中来。
我最近对运用插件和其他工具扩展应用程序这类越来越有兴趣了。秉持着我一贯的信念——勤读代码,有助于成为更高水准的程序开发者——亲爱的读者们,这里我为你们奉上第29篇“每周源代码”,之后也会不断继续。
本周的源是为Ruby设计的“一点”式外挂。这非常酷,因为它集结了许多技术,形成了十分清晰的终极用户体验。其目的是使Ruby的GUI应用程序轻松运行,这的确有效可行,而且在各个层面的表现都非常突出。感谢Sam Saffron告诉我这个!
最开始,是名叫“为什么是幸运的僵硬”(或者简称"_why")的黑客提到的,所以这起源很早,而且有错误。你可以在GitHub上查看代码:https://github.com/why/shoes/tree/master 或通过“git clone git://github.com/why/shoes.git”克隆整个结构。
Shoes
在我看来,Ruby是一种非常美观,赏心悦目而且灵活的语言。Shoes则是使用Ruby制作窗口应用程序的GUI工具包。我在每周源代码12中曾提及过。Shoes是一个传奇,原因有很多,不过最重要的是因为它具有在所有软件文档历史上最伟大的API文档。在Shoes开发中最主要的著作叫做《没人知道Shoes》,这本书非常棒,连Chris Sells都对它爱不释手。
这是用Ruby和Shoes写成的通讯录程序样本的一部分:
1: Shoes.app :width => 320, :height => 350 do
2:
3: stack :margin => 40 do
4: stack :margin => 10 do
5: para "Name"
6: @name = list_box :items => ["Yes, please!", "NO. No thankyou."]
7: end
8: stack :margin => 10 do
9: para "Address"
10: @address = edit_line
11: end
12: stack :margin => 10 do
13: para "Phone"
14: @phone = edit_line
15: end
16: stack :margin => 10 do
17: button "Save" do
18: Shoes.p [@name.text, @address.text, @phone.text]
19: end
20: end
21: end
22: end
感觉上和Tcl/Tk或者Rebol很像。如果有人写了一个非凡的主流程序,那一定很有趣。Shoes可以在XP,Vista,MacOSX和Linux上运行。注意你在Vista上必须点击右键,以管理者身份运行,因为_why还没有写入权限
提升提示。你得通过管理者进行初始引导安装。
不过,为了让Shoes正常运行,在今天之前,你必须安装Ruby,然后安装Shoes库,通常通过gem来实现。然后你需要通过ruby.exe,yourapp.rb或者你设置的快捷来运行程序。_why的博文发布的第二个评论就说了这些:
哇,这太棒了,我们现在可以把我们的应用程序给别人了。
Shoes的“引导程序”(我这样表述)是怎么运行的呢?_why给出的解释是:
如果你摆弄一下Windows PE二进制格式中的十六进制编辑器,你会在包含图标,对话框的文件末尾找到.rsrc部分。我把Ruby脚本添加进去:
binj = Binject::EXE.new("blank.exe")
binj.inject("SHOES_FILENAME", "simple-accordion.rb")
File.open("simple-accordion.rb") do |f|
binj.inject("SHOES_PAYLOAD", f)
end
binj.save("accordion.exe")
超棒的黑客。他把Ruby脚本升级成了Windows资源!他还为Mac OSX上的DMG(Disk Images)做了同样的升级。所以现在你可以创建移植到这两个运行平台上的Ruby脚本了。
运行时,它会查询Shoes是否存在于你的系统中。它在C:\Program Files (x86)\Common Files\Shoes\中。如果Shoes(包含Ruby的私有拷贝)不在其中,那就下载安装,然后程序就运行了。多棒啊,一点式跨平台GUI。
我也不清楚什么是安全分歧。好吧。我很清楚。我怀疑没有不被主机操作系统认证的安全性。你一旦运行,Ruby脚本就有完全的自由做任何它想做的事情。所以我在想有没有人可以写一个恶意的程序,就像如果他们愿意,可以给.NET程序写恶意程序一样。
你运行shoes –package就可以实现打包程序。点击打包,然后就会出现这样的对话框。如果你愿意你可以选在把Shoes和Ruby包括在最终EXE中。
Shoes还支持自定义"Widgets"。比如,下面就是一个自定义里程表控制。
程序的完整代码,包括自定义控制代码如下:
1: class Speedometer < Widget
2: attr_accessor :range, :tick, :position
3: def initialize opts = {}
4: @range = opts[:range] || 200
5: @tick = opts[:tick] || 10
6: @position = opts[:position] || 0
7: @cx, @cy = self.left + 110, self.top + 100
8:
9: nostroke
10: rect :top => self.top, :left => self.left,
11: :width => 220, :height => 200
12: nofill
13: stroke white
14: oval :left => @cx - 50, :top => @cy - 50, :radius => 100
15: (ticks + 1).times do |i|
16: radial_line 225 + ((270.0 / ticks) * i), 70..80
17: radial_line 225 + ((270.0 / ticks) * i), 45..49
18: end
19: strokewidth 2
20: oval :left => @cx - 70, :top => @cy - 70, :radius => 140
21: stroke lightgreen
22: oval :left => @cx - 5, :top => @cy - 5, :radius => 10
23: @needle = radial_line 225 + ((270.0 / @range) * @position), 0..90
24: end
25: def ticks; @range / @tick end
26: def radial_line deg, r
27: pos = ((deg / 360.0) * (2.0 * Math::PI)) - (Math::PI / 2.0)
28: line (Math.cos(pos) * r.begin) + @cx, (Math.sin(pos) * r.begin) + @cy,
29: (Math.cos(pos) * r.end) + @cx, (Math.sin(pos) * r.end) + @cy
30: end
31: def position= pos
32: @position = pos
33: @needle.remove
34: append do
35: @needle = radial_line 225 + ((270.0 / @range) * @position), 0..90
36: end
37: end
38: end
39:
40: Shoes.app do
41: stack do
42: para "Enter a number between 0 and 100"
43: flow do
44: @p = edit_line
45: button "OK" do
46: @s.position = @p.text.to_i
47: end
48: end
49:
50: @s = speedometer :range => 100, :ticks => 10
51: end
52: end
完成后,大概占磁盘库的24兆,但你因此拥有了多媒体支持以及在那个范围内的许多库的支持,更不用说Ruby本身的拷贝。裸下载只需2.5M,带视频支持的版本下载也只需6.8M。
我觉得建立一个用Shoes的Twitter客户端也很棒。比赛已经开始!希望我们赶在一些写Ruby Shoes病毒的坏人之前做好Twitter客户端。我会把自己写的Ruby Shoes病毒亲自保管好。好吧,这不算是真正的病毒,只是自寻烦恼的源头罢了。不过我还是会保管好的。
追踪它演变的过程一定会非常有趣的。我希望会有更清晰的升级过程。如果你想试试运行你的第一个Ruby/Shoes程序,那就运行这个EXE,只要你有Windows,或者这个DMG如果你是Mac用户,那就看看简单的demo程序,不过最重要的是,体验一下安装/引导过程。