rucola 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/ChangeLog +628 -0
- data/History.txt +4 -0
- data/License.txt +20 -0
- data/Manifest.txt +106 -0
- data/README.txt +126 -0
- data/Rakefile +32 -0
- data/TODO +28 -0
- data/app_generators/rucola/USAGE +6 -0
- data/app_generators/rucola/rucola_generator.rb +112 -0
- data/app_generators/rucola/templates/Rakefile.erb +12 -0
- data/app_generators/rucola/templates/Rakefile.erb.old +156 -0
- data/app_generators/rucola/templates/app/controllers/application_controller.rb +22 -0
- data/app_generators/rucola/templates/config/Info.plist.erb +28 -0
- data/app_generators/rucola/templates/config/boot.rb +2 -0
- data/app_generators/rucola/templates/config/environment.rb +11 -0
- data/app_generators/rucola/templates/config/environments/debug.rb +3 -0
- data/app_generators/rucola/templates/config/environments/release.rb +3 -0
- data/app_generators/rucola/templates/config/environments/test.rb +3 -0
- data/app_generators/rucola/templates/config/ib_external_class_defs.yml +13 -0
- data/app_generators/rucola/templates/misc/English.lproj/InfoPlist.strings.erb +3 -0
- data/app_generators/rucola/templates/misc/English.lproj/MainMenu.nib/classes.nib +40 -0
- data/app_generators/rucola/templates/misc/English.lproj/MainMenu.nib/info.nib +18 -0
- data/app_generators/rucola/templates/misc/English.lproj/MainMenu.nib/keyedobjects.nib +0 -0
- data/app_generators/rucola/templates/misc/main.m.erb +15 -0
- data/app_generators/rucola/templates/misc/rb_main.rb.erb +13 -0
- data/app_generators/rucola/templates/project.pbxproj.erb +299 -0
- data/app_generators/rucola/templates/script/plugin +84 -0
- data/app_generators/rucola/templates/test/controllers/test_application_controller.rb +10 -0
- data/app_generators/rucola/templates/test/test_helper.rb +10 -0
- data/bin/rucola +12 -0
- data/config/hoe.rb +71 -0
- data/config/requirements.rb +17 -0
- data/lib/rucola.rb +3 -0
- data/lib/rucola/info_plist.rb +37 -0
- data/lib/rucola/initializer.rb +313 -0
- data/lib/rucola/nib.rb +99 -0
- data/lib/rucola/rucola_support.rb +9 -0
- data/lib/rucola/rucola_support/controllers.rb +2 -0
- data/lib/rucola/rucola_support/controllers/rc_controller.rb +7 -0
- data/lib/rucola/rucola_support/controllers/rc_window_controller.rb +12 -0
- data/lib/rucola/rucola_support/core_ext.rb +2 -0
- data/lib/rucola/rucola_support/core_ext/objc.rb +4 -0
- data/lib/rucola/rucola_support/core_ext/objc/nsobject.rb +22 -0
- data/lib/rucola/rucola_support/core_ext/ruby.rb +4 -0
- data/lib/rucola/rucola_support/core_ext/ruby/string.rb +21 -0
- data/lib/rucola/rucola_support/initialize_hooks.rb +21 -0
- data/lib/rucola/rucola_support/models.rb +1 -0
- data/lib/rucola/rucola_support/models/rc_document.rb +10 -0
- data/lib/rucola/rucola_support/notifications.rb +1 -0
- data/lib/rucola/rucola_support/notifications/notifications.rb +146 -0
- data/lib/rucola/rucola_support/rc_app.rb +101 -0
- data/lib/rucola/tasks/freeze.rake +44 -0
- data/lib/rucola/tasks/interface_builder.rake +80 -0
- data/lib/rucola/tasks/main.rake +29 -0
- data/lib/rucola/tasks/xcode.rake +43 -0
- data/lib/rucola/test_helper.rb +57 -0
- data/lib/rucola/version.rb +9 -0
- data/lib/rucola/xcode.rb +148 -0
- data/log/debug.log +0 -0
- data/rucola_generators/controller/USAGE +5 -0
- data/rucola_generators/controller/controller_generator.rb +84 -0
- data/rucola_generators/controller/templates/controller_template.rb.erb +5 -0
- data/rucola_generators/controller/templates/test_controller_template.rb.erb +10 -0
- data/rucola_generators/document_model/USAGE +5 -0
- data/rucola_generators/document_model/document_model_generator.rb +67 -0
- data/rucola_generators/document_model/templates/document_model_template.rb.erb +27 -0
- data/rucola_generators/document_model/templates/test_document_model_template.rb.erb +10 -0
- data/rucola_generators/window_controller/USAGE +6 -0
- data/rucola_generators/window_controller/templates/Window.nib/classes.nib.erb +35 -0
- data/rucola_generators/window_controller/templates/Window.nib/info.nib +16 -0
- data/rucola_generators/window_controller/templates/Window.nib/keyedobjects.nib +0 -0
- data/rucola_generators/window_controller/templates/test_window_controller_template.rb.erb +10 -0
- data/rucola_generators/window_controller/templates/window_controller_template.rb.erb +19 -0
- data/rucola_generators/window_controller/window_controller_generator.rb +74 -0
- data/script/destroy +14 -0
- data/script/generate +14 -0
- data/script/txt2html +74 -0
- data/setup.rb +1585 -0
- data/tasks/deployment.rake +27 -0
- data/tasks/environment.rake +7 -0
- data/tasks/website.rake +17 -0
- data/test/fixtures/Info.plist +28 -0
- data/test/fixtures/MainMenu.nib/classes.nib +32 -0
- data/test/fixtures/MainMenu.nib/info.nib +18 -0
- data/test/fixtures/MainMenu.nib/keyedobjects.nib +0 -0
- data/test/test_controller_generator.rb +75 -0
- data/test/test_core_ext.rb +15 -0
- data/test/test_document_model_generator.rb +64 -0
- data/test/test_generator_helper.rb +20 -0
- data/test/test_helper.rb +13 -0
- data/test/test_info_plist.rb +31 -0
- data/test/test_nib.rb +73 -0
- data/test/test_notifications.rb +75 -0
- data/test/test_objc_core_ext.rb +37 -0
- data/test/test_rc_app.rb +63 -0
- data/test/test_rc_document.rb +18 -0
- data/test/test_rc_window_controller.rb +13 -0
- data/test/test_rucola.rb +11 -0
- data/test/test_rucola_generator.rb +87 -0
- data/test/test_window_controller_generator.rb +50 -0
- data/test/test_xcode.rb +128 -0
- data/website/index.html +199 -0
- data/website/index.txt +126 -0
- data/website/javascripts/rounded_corners_lite.inc.js +285 -0
- data/website/stylesheets/screen.css +138 -0
- data/website/template.rhtml +48 -0
- metadata +189 -0
@@ -0,0 +1,37 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
|
3
|
+
# FIXME: Actually these are not only objc_core_ext tests but also initialize_hooks tests...
|
4
|
+
|
5
|
+
class FooAfterHook < Rucola::RCController; end
|
6
|
+
|
7
|
+
describe 'A RCController subclass with Rucola initialize hooks' do
|
8
|
+
|
9
|
+
it "should register rucola initialization hooks" do
|
10
|
+
hook = Proc.new { 'foo' }
|
11
|
+
FooAfterHook._rucola_register_initialize_hook(hook)
|
12
|
+
hooks = FooAfterHook.instance_variable_get(:@_rucola_initialize_hooks)
|
13
|
+
hooks.should.include hook
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should run the hooks after initialization" do
|
17
|
+
hook = Proc.new { FooAfterHook.some_class_method }
|
18
|
+
FooAfterHook._rucola_register_initialize_hook(hook)
|
19
|
+
FooAfterHook.expects(:some_class_method).once
|
20
|
+
FooAfterHook.alloc.init
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
class Rucola::RCMockClass < OSX::NSObject; end
|
25
|
+
class BarAfterHook < Rucola::RCMockClass; end
|
26
|
+
|
27
|
+
class NotSubClassOfRC < OSX::NSObject; end
|
28
|
+
|
29
|
+
describe "NSObject default mixins" do
|
30
|
+
it "should automatically mixin the Rucola initialize hooks if it's a subclass of a class that starts with 'Rucola::RC'" do
|
31
|
+
BarAfterHook.methods.should.include '_rucola_register_initialize_hook'
|
32
|
+
end
|
33
|
+
|
34
|
+
it "should not mixin the initialize hooks if it's a subclass of a class that starts with anything else but 'Rucola::RC'" do
|
35
|
+
NotSubClassOfRC.methods.should.not.include '_rucola_register_initialize_hook'
|
36
|
+
end
|
37
|
+
end
|
data/test/test_rc_app.rb
ADDED
@@ -0,0 +1,63 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
require 'pathname'
|
3
|
+
include Rucola
|
4
|
+
|
5
|
+
class FooController; end
|
6
|
+
class Person; end
|
7
|
+
class PreferencesController; end
|
8
|
+
|
9
|
+
describe 'Rucola::RCApp' do
|
10
|
+
before do
|
11
|
+
@root_path = '/some/path/to/root'
|
12
|
+
::RUBYCOCOA_ROOT = Pathname.new(@root_path)
|
13
|
+
end
|
14
|
+
|
15
|
+
it "should return the path to the current root dir" do
|
16
|
+
RCApp.root_path.should == @root_path
|
17
|
+
end
|
18
|
+
|
19
|
+
it "should return the path to the current controllers dir" do
|
20
|
+
RCApp.controllers_path.should == "#{@root_path}/app/controllers"
|
21
|
+
end
|
22
|
+
|
23
|
+
it "should return the path to the current models dir" do
|
24
|
+
RCApp.models_path.should == "#{@root_path}/app/models"
|
25
|
+
end
|
26
|
+
|
27
|
+
it "should return the path to the current views dir" do
|
28
|
+
RCApp.views_path.should == "#{@root_path}/app/views"
|
29
|
+
end
|
30
|
+
|
31
|
+
it "should return the path to the current assets dir" do
|
32
|
+
RCApp.assets_path.should == "#{@root_path}/app/assets"
|
33
|
+
end
|
34
|
+
|
35
|
+
it "should return the path for a given controller" do
|
36
|
+
RCApp.path_for_controller(FooController).should == "#{@root_path}/app/controllers/foo_controller.rb"
|
37
|
+
end
|
38
|
+
|
39
|
+
it "should return the path for a given model" do
|
40
|
+
RCApp.path_for_model(Person).should == "#{@root_path}/app/models/person.rb"
|
41
|
+
end
|
42
|
+
|
43
|
+
it "should return the path for a given view" do
|
44
|
+
view_path = "#{@root_path}/app/views/Preferences.nib"
|
45
|
+
RCApp.path_for_view('Preferences').should == view_path
|
46
|
+
RCApp.path_for_view('preferences').should == view_path
|
47
|
+
RCApp.path_for_view(PreferencesController).should == view_path
|
48
|
+
RCApp.path_for_view(PreferencesController.new).should == view_path
|
49
|
+
end
|
50
|
+
|
51
|
+
it "should return the path for a given asset" do
|
52
|
+
asset_path = "#{@root_path}/app/assets/somefile.png"
|
53
|
+
RCApp.path_for_asset('somefile.png').should == asset_path
|
54
|
+
RCApp.path_for_view('SomeFile.png').should.not == asset_path
|
55
|
+
end
|
56
|
+
|
57
|
+
it "should be included by default in the RCController class" do
|
58
|
+
RCController.include?(RCApp).should.be true
|
59
|
+
RCController.alloc.init.send(:root_path).should == @root_path
|
60
|
+
|
61
|
+
RCWindowController.include?(RCApp).should.not.be true
|
62
|
+
end
|
63
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require File.expand_path('../test_helper', __FILE__)
|
2
|
+
|
3
|
+
class SomeDocController < Rucola::RCWindowController; end
|
4
|
+
class SomeDoc < Rucola::RCDocument; end
|
5
|
+
|
6
|
+
describe "RCDocument" do
|
7
|
+
it "should initialize a window controller corresponding to itself" do
|
8
|
+
# doc = SomeDoc.alloc
|
9
|
+
# doc.expects(:addWindowController).with(SomeDocController)
|
10
|
+
# doc.init
|
11
|
+
|
12
|
+
doc = SomeDoc.alloc.init
|
13
|
+
controller_mock = mock("SomeDocController mock")
|
14
|
+
SomeDocController.expects_alloc_init_returns(controller_mock)
|
15
|
+
doc.expects(:addWindowController).with(controller_mock)
|
16
|
+
doc.makeWindowControllers
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
|
3
|
+
class FooBarController < Rucola::RCWindowController; end
|
4
|
+
|
5
|
+
describe 'A subclassed WindowController' do
|
6
|
+
it "should know at initialization which nib belongs to it" do
|
7
|
+
RUBYCOCOA_ROOT = ''
|
8
|
+
|
9
|
+
FooBarController.during_init do |obj|
|
10
|
+
obj.expects(:initWithWindowNibPath_owner).with('app/views/FooBar.nib', obj).returns(true)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
data/test/test_rucola.rb
ADDED
@@ -0,0 +1,87 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), "test_generator_helper.rb")
|
2
|
+
|
3
|
+
module RubiGen::GeneratorTestHelper
|
4
|
+
def assert_generated_symlink(path)
|
5
|
+
# For some reason File.exists? doesn't work with symlinks generated with File.symlink(),
|
6
|
+
# it does work if the symlink was created with: ln -s
|
7
|
+
assert Dir.entries(File.dirname("#{APP_ROOT}/#{path}")).include?(File.basename(path)),"The symbolic link '#{path}' should exist"
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
class TestRucolaGenerator < Test::Unit::TestCase
|
12
|
+
include RubiGen::GeneratorTestHelper
|
13
|
+
|
14
|
+
def setup
|
15
|
+
bare_setup
|
16
|
+
end
|
17
|
+
|
18
|
+
def teardown
|
19
|
+
bare_teardown
|
20
|
+
end
|
21
|
+
|
22
|
+
# Some generator-related assertions:
|
23
|
+
# assert_generated_file(name, &block) # block passed the file contents
|
24
|
+
# assert_directory_exists(name)
|
25
|
+
# assert_generated_class(name, &block)
|
26
|
+
# assert_generated_module(name, &block)
|
27
|
+
# assert_generated_test_for(name, &block)
|
28
|
+
# The assert_generated_(class|module|test_for) &block is passed the body of the class/module within the file
|
29
|
+
# assert_has_method(body, *methods) # check that the body has a list of methods (methods with parentheses not supported yet)
|
30
|
+
#
|
31
|
+
# Other helper methods are:
|
32
|
+
# app_root_files - put this in teardown to show files generated by the test method (e.g. p app_root_files)
|
33
|
+
# bare_setup - place this in setup method to create the APP_ROOT folder for each test
|
34
|
+
# bare_teardown - place this in teardown method to destroy the TMP_ROOT or APP_ROOT folder after each test
|
35
|
+
|
36
|
+
def test_generator_without_options
|
37
|
+
run_generator('rucola', [APP_ROOT], sources)
|
38
|
+
|
39
|
+
assert_directory_exists "app/controllers"
|
40
|
+
assert_directory_exists "app/models"
|
41
|
+
assert_directory_exists "app/views"
|
42
|
+
assert_directory_exists "config/environments"
|
43
|
+
assert_directory_exists "misc/English.lproj/MainMenu.nib"
|
44
|
+
assert_directory_exists "test/controllers"
|
45
|
+
assert_directory_exists "test/models"
|
46
|
+
assert_directory_exists "vendor"
|
47
|
+
|
48
|
+
assert_generated_file "Rakefile"
|
49
|
+
|
50
|
+
assert_generated_file "app/controllers/application_controller.rb"
|
51
|
+
assert_generated_file "config/boot.rb"
|
52
|
+
assert_generated_file "config/environment.rb"
|
53
|
+
assert_generated_file "config/environments/debug.rb"
|
54
|
+
assert_generated_file "config/environments/release.rb"
|
55
|
+
assert_generated_file "config/environments/test.rb"
|
56
|
+
assert_generated_file "config/Info.plist"
|
57
|
+
assert_generated_file "config/ib_external_class_defs.yml"
|
58
|
+
assert_generated_symlink "Info.plist"
|
59
|
+
|
60
|
+
assert_generated_file "misc/main.m"
|
61
|
+
assert_generated_file "misc/rb_main.rb"
|
62
|
+
assert_generated_file "misc/English.lproj/InfoPlist.strings"
|
63
|
+
assert_generated_file "misc/English.lproj/MainMenu.nib/classes.nib"
|
64
|
+
assert_generated_file "misc/English.lproj/MainMenu.nib/info.nib"
|
65
|
+
assert_generated_file "misc/English.lproj/MainMenu.nib/keyedobjects.nib"
|
66
|
+
|
67
|
+
assert_directory_exists "myproject.xcodeproj"
|
68
|
+
assert_generated_file "myproject.xcodeproj/project.pbxproj"
|
69
|
+
|
70
|
+
assert_generated_file "test/test_helper.rb"
|
71
|
+
assert_generated_file "test/controllers/test_application_controller.rb"
|
72
|
+
|
73
|
+
assert_directory_exists "script"
|
74
|
+
assert_generated_file "script/plugin"
|
75
|
+
assert `ls -l #{File.expand_path('../tmp/myproject/script/plugin', __FILE__)}`[0..9] == '-rwxr-xr-x'
|
76
|
+
end
|
77
|
+
|
78
|
+
private
|
79
|
+
def sources
|
80
|
+
[RubiGen::PathSource.new(:test, File.join(File.dirname(__FILE__),"..", generator_path))
|
81
|
+
]
|
82
|
+
end
|
83
|
+
|
84
|
+
def generator_path
|
85
|
+
"app_generators"
|
86
|
+
end
|
87
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), "test_generator_helper.rb")
|
2
|
+
|
3
|
+
class TestWindowControllerGenerator < Test::Unit::TestCase
|
4
|
+
include RubiGen::GeneratorTestHelper
|
5
|
+
|
6
|
+
def setup
|
7
|
+
bare_setup
|
8
|
+
end
|
9
|
+
|
10
|
+
def teardown
|
11
|
+
bare_teardown
|
12
|
+
end
|
13
|
+
|
14
|
+
# Some generator-related assertions:
|
15
|
+
# assert_generated_file(name, &block) # block passed the file contents
|
16
|
+
# assert_directory_exists(name)
|
17
|
+
# assert_generated_class(name, &block)
|
18
|
+
# assert_generated_module(name, &block)
|
19
|
+
# assert_generated_test_for(name, &block)
|
20
|
+
# The assert_generated_(class|module|test_for) &block is passed the body of the class/module within the file
|
21
|
+
# assert_has_method(body, *methods) # check that the body has a list of methods (methods with parentheses not supported yet)
|
22
|
+
#
|
23
|
+
# Other helper methods are:
|
24
|
+
# app_root_files - put this in teardown to show files generated by the test method (e.g. p app_root_files)
|
25
|
+
# bare_setup - place this in setup method to create the APP_ROOT folder for each test
|
26
|
+
# bare_teardown - place this in teardown method to destroy the TMP_ROOT or APP_ROOT folder after each test
|
27
|
+
|
28
|
+
def test_generator_without_options
|
29
|
+
name = "FooBar"
|
30
|
+
run_generator('window_controller', [name], sources)
|
31
|
+
|
32
|
+
assert_generated_file 'app/controllers/foo_bar_controller.rb'
|
33
|
+
assert_generated_file 'test/controllers/test_foo_bar_controller.rb'
|
34
|
+
|
35
|
+
assert_directory_exists 'app/views/FooBar.nib'
|
36
|
+
assert_generated_file 'app/views/FooBar.nib/classes.nib'
|
37
|
+
assert_generated_file 'app/views/FooBar.nib/info.nib'
|
38
|
+
assert_generated_file 'app/views/FooBar.nib/keyedobjects.nib'
|
39
|
+
end
|
40
|
+
|
41
|
+
private
|
42
|
+
def sources
|
43
|
+
[RubiGen::PathSource.new(:test, File.join(File.dirname(__FILE__),"..", generator_path))
|
44
|
+
]
|
45
|
+
end
|
46
|
+
|
47
|
+
def generator_path
|
48
|
+
"rucola_generators"
|
49
|
+
end
|
50
|
+
end
|
data/test/test_xcode.rb
ADDED
@@ -0,0 +1,128 @@
|
|
1
|
+
require "rubygems"
|
2
|
+
require "test/unit"
|
3
|
+
require "test/spec"
|
4
|
+
require 'mocha'
|
5
|
+
|
6
|
+
require File.expand_path('../../lib/rucola/xcode', __FILE__)
|
7
|
+
include Rucola
|
8
|
+
|
9
|
+
describe 'Xcode' do
|
10
|
+
before do
|
11
|
+
@name = 'Baz'
|
12
|
+
@project_path = "/foo/bar/#{@name}.xcodeproj"
|
13
|
+
@data_path = "#{@project_path}/project.pbxproj"
|
14
|
+
|
15
|
+
@object_id = '519A79DB0CC8AE6B00CBE85E'.to_ns
|
16
|
+
@object_values = { 'isa' => 'PBXNativeTarget', 'name' => @name, 'buildPhases' => [] }.to_ns
|
17
|
+
@object = [@object_id, @object_values]
|
18
|
+
@data = { 'objects' => { @object_id => @object_values } }.to_ns
|
19
|
+
OSX::NSDictionary.stubs(:dictionaryWithContentsOfFile).with(@data_path).returns(@data)
|
20
|
+
|
21
|
+
@project = Xcode.new(@project_path)
|
22
|
+
end
|
23
|
+
|
24
|
+
it "should initialize" do
|
25
|
+
OSX::NSDictionary.expects(:dictionaryWithContentsOfFile).with(@data_path).returns(@data)
|
26
|
+
|
27
|
+
project = Xcode.new(@project_path)
|
28
|
+
project.project_path.to_s.should == @project_path
|
29
|
+
project.project.should == @name
|
30
|
+
project.project_data.should == @data
|
31
|
+
end
|
32
|
+
|
33
|
+
it "should save the data back as a plist" do
|
34
|
+
# atm we don't generate id's, so let's at least make a backup
|
35
|
+
backup = "/tmp/#{@name}.xcodeproj.bak"
|
36
|
+
File.expects(:exists?).with(backup).returns(true)
|
37
|
+
Kernel.expects(:system).with("rm -rf #{backup}")
|
38
|
+
Kernel.expects(:system).with("cp -R #{@project_path} #{backup}")
|
39
|
+
@project.project_data.expects(:writeToFile_atomically).with(@data_path, true)
|
40
|
+
@project.save
|
41
|
+
end
|
42
|
+
|
43
|
+
it "should return an object for a given name" do
|
44
|
+
@project.object_for_name('Baz').should == @object
|
45
|
+
@project.object_for_name('foo').should.be nil
|
46
|
+
end
|
47
|
+
|
48
|
+
it "should return an object for a given type and name" do
|
49
|
+
@project.object_for_type_and_name('PBXNativeTarget', 'Baz').should == @object
|
50
|
+
@project.object_for_type_and_name('PBXBuildPhase', 'Baz').should.be nil
|
51
|
+
end
|
52
|
+
|
53
|
+
it "should return an object for the main target" do
|
54
|
+
@project.object_for_project_target.should == @object
|
55
|
+
end
|
56
|
+
|
57
|
+
it "should return an object for a given id" do
|
58
|
+
@project.object_for_id(@object_id).should == @object
|
59
|
+
@project.object_for_id('DOES_NOT_EXIST').should.be nil
|
60
|
+
end
|
61
|
+
|
62
|
+
it "should add an object to the objects" do
|
63
|
+
id, values = 'SOME_ID'.to_ns, { 'name' => 'some blah' }.to_ns
|
64
|
+
@project.add_object(id, values)
|
65
|
+
@project.object_for_id(id).should == [id, values]
|
66
|
+
end
|
67
|
+
|
68
|
+
it "should add a build phase to the project target only once" do
|
69
|
+
id, values = 'BUILD_PHASE_ID'.to_ns, { 'name' => 'some blah' }.to_ns
|
70
|
+
@project.add_object(id, values)
|
71
|
+
@project.add_build_phase_to_project_target(id)
|
72
|
+
@project.object_for_project_target.last['buildPhases'].should == [id]
|
73
|
+
|
74
|
+
@project.add_build_phase_to_project_target(id)
|
75
|
+
@project.object_for_project_target.last['buildPhases'].length.should.be 1
|
76
|
+
end
|
77
|
+
|
78
|
+
it "should add an object to a copy build phase" do
|
79
|
+
id, values = 'BUILD_PHASE_ID'.to_ns, { 'name' => 'some blah', 'files' => [] }.to_ns
|
80
|
+
@project.add_object(id, values)
|
81
|
+
@project.add_build_phase_to_project_target(id)
|
82
|
+
|
83
|
+
@project.add_object_to_build_phase(@object_id, id)
|
84
|
+
@project.object_for_id(id).last['files'].should == [@object_id]
|
85
|
+
end
|
86
|
+
|
87
|
+
# it "should create a new framework copy build phase" do
|
88
|
+
# # FIXME: until we generate id's this is just a lame test
|
89
|
+
# Xcode::NEW_COPY_FRAMEWORKS_BUILD_PHASE = @object
|
90
|
+
# @project.new_framework_copy_build_phase.should == @object
|
91
|
+
# end
|
92
|
+
|
93
|
+
it "should change the path of a framework used in the project" do
|
94
|
+
id, values = 'FRAMEWORK_ID'.to_ns, { 'name' => 'RubyCocoa.framework', 'path' => '/foo/RubyCocoa.framework', 'sourceTree' => '<absolute>' }.to_ns
|
95
|
+
@project.add_object(id, values)
|
96
|
+
framework_path = 'vendor/RubyCocoa.framework'
|
97
|
+
@project.change_framework_location('RubyCocoa.framework', framework_path)
|
98
|
+
|
99
|
+
@project.object_for_id(id).last['path'].should == framework_path
|
100
|
+
@project.object_for_id(id).last['sourceTree'].should == '<group>'
|
101
|
+
end
|
102
|
+
|
103
|
+
it "should change the path of the RubyCocoa framework" do
|
104
|
+
framework_path = 'vendor/RubyCocoa.framework'
|
105
|
+
@project.expects(:change_framework_location).with('RubyCocoa.framework', framework_path)
|
106
|
+
@project.change_rubycocoa_framework_location(framework_path)
|
107
|
+
end
|
108
|
+
|
109
|
+
it "should bundle a framework with the application" do
|
110
|
+
id, values = 'FRAMEWORK_ID'.to_ns, { 'name' => 'BlaBla.framework', 'path' => '/foo/BlaBla.framework', 'sourceTree' => '<absolute>' }.to_ns
|
111
|
+
@project.add_object(id, values)
|
112
|
+
|
113
|
+
@project.bundle_framework('BlaBla.framework')
|
114
|
+
|
115
|
+
build_phases = @project.object_for_project_target.last['buildPhases']
|
116
|
+
build_phases.length.should.be 1
|
117
|
+
@project.object_for_id(build_phases.first).last['name'].should == 'Copy Frameworks'
|
118
|
+
|
119
|
+
build_phase_id = @project.object_for_id(build_phases.first).last['files'].first
|
120
|
+
build_phase_id, build_phase = @project.object_for_id(build_phase_id)
|
121
|
+
build_phase['fileRef'].should == 'FRAMEWORK_ID'
|
122
|
+
end
|
123
|
+
|
124
|
+
it "should bundle the RubyCocoa framework with the application" do
|
125
|
+
@project.expects(:bundle_framework).with('RubyCocoa.framework')
|
126
|
+
@project.bundle_rubycocoa_framework
|
127
|
+
end
|
128
|
+
end
|
data/website/index.html
ADDED
@@ -0,0 +1,199 @@
|
|
1
|
+
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
|
2
|
+
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
|
3
|
+
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
4
|
+
<head>
|
5
|
+
<link rel="stylesheet" href="stylesheets/screen.css" type="text/css" media="screen" />
|
6
|
+
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
7
|
+
<title>
|
8
|
+
rucola
|
9
|
+
</title>
|
10
|
+
<script src="javascripts/rounded_corners_lite.inc.js" type="text/javascript"></script>
|
11
|
+
<style>
|
12
|
+
|
13
|
+
</style>
|
14
|
+
<script type="text/javascript">
|
15
|
+
window.onload = function() {
|
16
|
+
settings = {
|
17
|
+
tl: { radius: 10 },
|
18
|
+
tr: { radius: 10 },
|
19
|
+
bl: { radius: 10 },
|
20
|
+
br: { radius: 10 },
|
21
|
+
antiAlias: true,
|
22
|
+
autoPad: true,
|
23
|
+
validTags: ["div"]
|
24
|
+
}
|
25
|
+
var versionBox = new curvyCorners(settings, document.getElementById("version"));
|
26
|
+
versionBox.applyCornersToAll();
|
27
|
+
}
|
28
|
+
</script>
|
29
|
+
</head>
|
30
|
+
<body>
|
31
|
+
<div id="main">
|
32
|
+
|
33
|
+
<h1>rucola</h1>
|
34
|
+
<div id="version" class="clickable" onclick='document.location = "http://rubyforge.org/projects/rucola"; return false'>
|
35
|
+
<p>Get Version</p>
|
36
|
+
<a href="http://rubyforge.org/projects/rucola" class="numbers">0.0.1</a>
|
37
|
+
</div>
|
38
|
+
<h1>→ ‘rucola’</h1>
|
39
|
+
|
40
|
+
|
41
|
+
<h3><span class="caps">SUPER DUPER PRE ALPHA VERSION</span> (expect things to break kinda alpha…)</h3>
|
42
|
+
|
43
|
+
|
44
|
+
<h2>What</h2>
|
45
|
+
|
46
|
+
|
47
|
+
<p>A Framework for building Cocoa applications in Ruby</p>
|
48
|
+
|
49
|
+
|
50
|
+
<p>Rucola is a light weight framework that helps you write RubyCocoa apps.
|
51
|
+
It allows you to build, test, and deploy applications using rake commands,
|
52
|
+
eliminating the need to use XCode, however you can use XCode if you wish.</p>
|
53
|
+
|
54
|
+
|
55
|
+
<p>Rucola provides a set of generators to help you generate controllers, window controllers,
|
56
|
+
and document-based applications. It also provides APIs for simplifying some of Objective-C’s
|
57
|
+
ways of doing things.</p>
|
58
|
+
|
59
|
+
|
60
|
+
<h2>Installing</h2>
|
61
|
+
|
62
|
+
|
63
|
+
<p><pre class='syntax'><span class="ident">sudo</span> <span class="ident">gem</span> <span class="ident">install</span> <span class="ident">rucola</span></pre></p>
|
64
|
+
|
65
|
+
|
66
|
+
<h2>Demonstration of usage</h2>
|
67
|
+
|
68
|
+
|
69
|
+
<h4>Generating an application skeleton</h4>
|
70
|
+
|
71
|
+
|
72
|
+
<pre><code>rucola MyApp -a "Your Name"</code></pre>
|
73
|
+
|
74
|
+
|
75
|
+
<p>Running this command will give you a complete, working application with a single window already
|
76
|
+
bound to your application controller.</p>
|
77
|
+
|
78
|
+
|
79
|
+
<h3>Using Notifications</h3>
|
80
|
+
|
81
|
+
|
82
|
+
<h4>Rucola
|
83
|
+
<pre class='syntax'>
|
84
|
+
<span class="keyword">class </span><span class="class">Foo</span> <span class="punct"><</span> <span class="constant">Rucola</span><span class="punct">::</span><span class="constant">RCController</span>
|
85
|
+
<span class="ident">notify</span> <span class="symbol">:some_method</span><span class="punct">,</span> <span class="symbol">:when</span> <span class="punct">=></span> <span class="symbol">:something_happens</span>
|
86
|
+
|
87
|
+
<span class="keyword">def </span><span class="method">some_method</span><span class="punct">(</span><span class="ident">notification</span><span class="punct">)</span>
|
88
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string">w00t!</span><span class="punct">"</span>
|
89
|
+
<span class="keyword">end</span>
|
90
|
+
<span class="keyword">end</span>
|
91
|
+
</pre></h4>
|
92
|
+
|
93
|
+
|
94
|
+
<h4>Objective C (Excluding header file)
|
95
|
+
<pre class='syntax'>
|
96
|
+
@implementation Foo
|
97
|
+
-(id)init {
|
98
|
+
if(self = [super init]) {
|
99
|
+
NSNotificationCenter *center = [NSNotificationCenter defaultCenter];
|
100
|
+
[center addObserver:self selector:(some_method:) name:@"SomethingHappensNotification" object:nil];
|
101
|
+
}
|
102
|
+
return self;
|
103
|
+
}
|
104
|
+
|
105
|
+
-(void)some_method:(NSNotification *) notification {
|
106
|
+
NSLog("w00t!");
|
107
|
+
}
|
108
|
+
@end
|
109
|
+
</pre></h4>
|
110
|
+
|
111
|
+
|
112
|
+
<h3>Alternative Way Of Using Notifications</h3>
|
113
|
+
|
114
|
+
|
115
|
+
<pre class='syntax'>
|
116
|
+
<span class="keyword">class </span><span class="class">Foo</span> <span class="punct"><</span> <span class="constant">Rucola</span><span class="punct">::</span><span class="constant">RCController</span>
|
117
|
+
<span class="ident">notify_on</span> <span class="symbol">:something_happens</span> <span class="keyword">do</span> <span class="punct">|</span><span class="ident">notification</span><span class="punct">|</span>
|
118
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string">w0t0!</span><span class="punct">"</span>
|
119
|
+
<span class="keyword">end</span>
|
120
|
+
<span class="keyword">end</span>
|
121
|
+
</pre>
|
122
|
+
|
123
|
+
|
124
|
+
<h3>Working with Interface Builder</h3>
|
125
|
+
|
126
|
+
|
127
|
+
<p>A Cocoa application contains `outlets`. Outlets allow you to bind variable names to objects.
|
128
|
+
An object can be a user interface element or an instance of a class.</p>
|
129
|
+
|
130
|
+
|
131
|
+
<pre class='syntax'>
|
132
|
+
<span class="keyword">class </span><span class="class">ApplicationController</span> <span class="punct"><</span> <span class="constant">Rucola</span><span class="punct">::</span><span class="constant">RCController</span>
|
133
|
+
<span class="ident">ib_outlet</span> <span class="symbol">:main_window</span>
|
134
|
+
|
135
|
+
<span class="keyword">def </span><span class="method">awakeFromNib</span>
|
136
|
+
<span class="comment"># All the application delegate methods will be called on this object.</span>
|
137
|
+
<span class="constant">OSX</span><span class="punct">::</span><span class="constant">NSApp</span><span class="punct">.</span><span class="ident">delegate</span> <span class="punct">=</span> <span class="constant">self</span>
|
138
|
+
|
139
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string">ApplicationController awoke.</span><span class="punct">"</span>
|
140
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string">Edit: app/controllers/application_controller.rb</span><span class="punct">"</span>
|
141
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string"><span class="escape">\n</span>It's window is: <span class="expr">#{@main_window.inspect}</span></span><span class="punct">"</span>
|
142
|
+
<span class="keyword">end</span>
|
143
|
+
|
144
|
+
<span class="comment"># NSApplication delegate methods</span>
|
145
|
+
<span class="keyword">def </span><span class="method">applicationDidFinishLaunching</span><span class="punct">(</span><span class="ident">notification</span><span class="punct">)</span>
|
146
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string"><span class="escape">\n</span>Application finished launching.</span><span class="punct">"</span>
|
147
|
+
<span class="keyword">end</span>
|
148
|
+
|
149
|
+
<span class="keyword">def </span><span class="method">applicationWillTerminate</span><span class="punct">(</span><span class="ident">notification</span><span class="punct">)</span>
|
150
|
+
<span class="ident">puts</span> <span class="punct">"</span><span class="string"><span class="escape">\n</span>Application will terminate.</span><span class="punct">"</span>
|
151
|
+
<span class="keyword">end</span>
|
152
|
+
<span class="keyword">end</span>
|
153
|
+
</pre>
|
154
|
+
|
155
|
+
|
156
|
+
<p>The `@main_window` variable now points to the user interface window. You can invoke any methods of NSWindow.</p>
|
157
|
+
|
158
|
+
|
159
|
+
<p>There is also a `rake ib:update` that will update your nib files with the outlets you specify in your code.
|
160
|
+
For example, if we wanted to add a button to the application controller above, we could add `ib_outlet :my_button`.
|
161
|
+
After you’ve added this, you can run `rake ib:update` and your outlet will be available in interface builder that
|
162
|
+
you can now hook up to your UI button.</p>
|
163
|
+
|
164
|
+
|
165
|
+
<h2>Forum</h2>
|
166
|
+
|
167
|
+
|
168
|
+
<p><a href="http://groups.google.com/group/rucola">http://groups.google.com/group/rucola</a></p>
|
169
|
+
|
170
|
+
|
171
|
+
<h2>How to submit patches</h2>
|
172
|
+
|
173
|
+
|
174
|
+
<p>Read the <a href="http://drnicwilliams.com/2007/06/01/8-steps-for-fixing-other-peoples-code/">8 steps for fixing other people’s code</a> and for section <a href="http://drnicwilliams.com/2007/06/01/8-steps-for-fixing-other-peoples-code/#8b-google-groups">8b: Submit patch to Google Groups</a>, use the Google Group above.</p>
|
175
|
+
|
176
|
+
|
177
|
+
<p>The trunk repository is <code>svn://rubyforge.org/var/svn/rucola/trunk</code> for anonymous access.</p>
|
178
|
+
|
179
|
+
|
180
|
+
<h2>License</h2>
|
181
|
+
|
182
|
+
|
183
|
+
<p>This code is free to use under the terms of the <span class="caps">MIT</span> license.</p>
|
184
|
+
|
185
|
+
|
186
|
+
<h2>Contact</h2>
|
187
|
+
|
188
|
+
|
189
|
+
<p>Comments are welcome. Send an email via the <a href="http://groups.google.com/group/rucola">forum</a></p>
|
190
|
+
<p class="coda">
|
191
|
+
<a href="http://groups.google.com/group/rucola">Eloy Duran, Justin Palmer</a>, 3rd November 2007<br>
|
192
|
+
Theme extended from <a href="http://rb2js.rubyforge.org/">Paul Battley</a>
|
193
|
+
</p>
|
194
|
+
</div>
|
195
|
+
|
196
|
+
<!-- insert site tracking codes here, like Google Urchin -->
|
197
|
+
|
198
|
+
</body>
|
199
|
+
</html>
|