chriseppstein-compass 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (144) hide show
  1. data/Manifest +143 -0
  2. data/README.markdown +18 -0
  3. data/Rakefile +104 -0
  4. data/VERSION +1 -0
  5. data/bin/compass +8 -0
  6. data/compass.gemspec +37 -0
  7. data/examples/blueprint_default/index.html +73 -0
  8. data/examples/blueprint_default/parts/elements.html +246 -0
  9. data/examples/blueprint_default/parts/forms.html +100 -0
  10. data/examples/blueprint_default/parts/grid.html +206 -0
  11. data/examples/blueprint_default/parts/test-small.jpg +0 -0
  12. data/examples/blueprint_default/parts/test.jpg +0 -0
  13. data/examples/blueprint_default/parts/valid.png +0 -0
  14. data/examples/blueprint_default/stylesheets/ie.sass +4 -0
  15. data/examples/blueprint_default/stylesheets/images/grid.png +0 -0
  16. data/examples/blueprint_default/stylesheets/print.sass +4 -0
  17. data/examples/blueprint_default/stylesheets/screen.sass +9 -0
  18. data/examples/blueprint_plugins/index.html +60 -0
  19. data/examples/blueprint_plugins/parts/fancy_type.html +84 -0
  20. data/examples/blueprint_plugins/parts/test-small.jpg +0 -0
  21. data/examples/blueprint_plugins/parts/test.jpg +0 -0
  22. data/examples/blueprint_plugins/parts/valid.png +0 -0
  23. data/examples/blueprint_plugins/stylesheets/ie.sass +4 -0
  24. data/examples/blueprint_plugins/stylesheets/images/grid.png +0 -0
  25. data/examples/blueprint_plugins/stylesheets/print.sass +4 -0
  26. data/examples/blueprint_plugins/stylesheets/screen.sass +11 -0
  27. data/examples/blueprint_scoped/stylesheets/ie.sass +4 -0
  28. data/examples/blueprint_scoped/stylesheets/print.sass +4 -0
  29. data/examples/blueprint_scoped/stylesheets/screen.sass +5 -0
  30. data/examples/blueprint_scoped_form/stylesheets/ie.sass +4 -0
  31. data/examples/blueprint_scoped_form/stylesheets/print.sass +4 -0
  32. data/examples/blueprint_scoped_form/stylesheets/screen.sass +9 -0
  33. data/examples/blueprint_semantic/index.html +68 -0
  34. data/examples/blueprint_semantic/parts/fancy_type.html +84 -0
  35. data/examples/blueprint_semantic/parts/liquid.html +84 -0
  36. data/examples/blueprint_semantic/parts/test-small.jpg +0 -0
  37. data/examples/blueprint_semantic/parts/test.jpg +0 -0
  38. data/examples/blueprint_semantic/parts/valid.png +0 -0
  39. data/examples/blueprint_semantic/stylesheets/ie.sass +4 -0
  40. data/examples/blueprint_semantic/stylesheets/images/grid.png +0 -0
  41. data/examples/blueprint_semantic/stylesheets/liquid.sass +70 -0
  42. data/examples/blueprint_semantic/stylesheets/print.sass +4 -0
  43. data/examples/blueprint_semantic/stylesheets/screen.sass +69 -0
  44. data/examples/compass/compass.html +19 -0
  45. data/examples/compass/stylesheets/compass.sass +47 -0
  46. data/examples/compass/stylesheets/images/blue_arrow.gif +0 -0
  47. data/examples/compass/stylesheets/utilities.sass +65 -0
  48. data/examples/compass/utilities.html.haml +136 -0
  49. data/examples/yui/divisions.html.haml +179 -0
  50. data/examples/yui/index.html.haml +19 -0
  51. data/examples/yui/stylesheets/screen.sass +13 -0
  52. data/examples/yui/sub_divisions.html.haml +169 -0
  53. data/examples/yui/templates.html.haml +54 -0
  54. data/examples/yui/test.jpg +0 -0
  55. data/examples/yui/typography.html.haml +132 -0
  56. data/frameworks/blueprint/lib/blueprint/constants.rb +17 -0
  57. data/frameworks/blueprint/lib/blueprint/grid_builder.rb +54 -0
  58. data/frameworks/blueprint/stylesheets/blueprint/_ie.sass +19 -0
  59. data/frameworks/blueprint/stylesheets/blueprint/_print.sass +69 -0
  60. data/frameworks/blueprint/stylesheets/blueprint/_screen.sass +15 -0
  61. data/frameworks/blueprint/stylesheets/blueprint/modules/_colors.sass +25 -0
  62. data/frameworks/blueprint/stylesheets/blueprint/modules/_debug.sass +9 -0
  63. data/frameworks/blueprint/stylesheets/blueprint/modules/_fancy_type.sass +85 -0
  64. data/frameworks/blueprint/stylesheets/blueprint/modules/_form.sass +43 -0
  65. data/frameworks/blueprint/stylesheets/blueprint/modules/_grid.sass +140 -0
  66. data/frameworks/blueprint/stylesheets/blueprint/modules/_interaction.sass +55 -0
  67. data/frameworks/blueprint/stylesheets/blueprint/modules/_liquid.sass +140 -0
  68. data/frameworks/blueprint/stylesheets/blueprint/modules/_scaffolding.sass +29 -0
  69. data/frameworks/blueprint/stylesheets/blueprint/modules/_typography.sass +131 -0
  70. data/frameworks/blueprint/stylesheets/blueprint/modules/_utilities.sass +39 -0
  71. data/frameworks/blueprint/templates/project/grid.png +0 -0
  72. data/frameworks/blueprint/templates/project/ie.sass +4 -0
  73. data/frameworks/blueprint/templates/project/print.sass +4 -0
  74. data/frameworks/blueprint/templates/project/screen.sass +9 -0
  75. data/frameworks/compass/stylesheets/compass/_reset.sass +19 -0
  76. data/frameworks/compass/stylesheets/compass/_utilities.sass +5 -0
  77. data/frameworks/compass/stylesheets/compass/utilities/_general.sass +4 -0
  78. data/frameworks/compass/stylesheets/compass/utilities/_links.sass +3 -0
  79. data/frameworks/compass/stylesheets/compass/utilities/_lists.sass +3 -0
  80. data/frameworks/compass/stylesheets/compass/utilities/_tables.sass +1 -0
  81. data/frameworks/compass/stylesheets/compass/utilities/_text.sass +2 -0
  82. data/frameworks/compass/stylesheets/compass/utilities/general/_clearfix.sass +11 -0
  83. data/frameworks/compass/stylesheets/compass/utilities/general/_inline_block.sass +6 -0
  84. data/frameworks/compass/stylesheets/compass/utilities/general/_reset.sass +32 -0
  85. data/frameworks/compass/stylesheets/compass/utilities/general/_tabs.sass +0 -0
  86. data/frameworks/compass/stylesheets/compass/utilities/general/_tag_cloud.sass +19 -0
  87. data/frameworks/compass/stylesheets/compass/utilities/links/_hover_link.sass +5 -0
  88. data/frameworks/compass/stylesheets/compass/utilities/links/_link_colors.sass +24 -0
  89. data/frameworks/compass/stylesheets/compass/utilities/links/_unstyled_link.sass +5 -0
  90. data/frameworks/compass/stylesheets/compass/utilities/lists/_bullets.sass +21 -0
  91. data/frameworks/compass/stylesheets/compass/utilities/lists/_horizontal_list.sass +20 -0
  92. data/frameworks/compass/stylesheets/compass/utilities/lists/_inline_list.sass +29 -0
  93. data/frameworks/compass/stylesheets/compass/utilities/tables/_alternating_rows_and_columns.sass +25 -0
  94. data/frameworks/compass/stylesheets/compass/utilities/text/_nowrap.sass +3 -0
  95. data/frameworks/compass/stylesheets/compass/utilities/text/_replacement.sass +10 -0
  96. data/frameworks/compass/templates/project/grid.png +0 -0
  97. data/frameworks/compass/templates/project/ie.sass +3 -0
  98. data/frameworks/compass/templates/project/print.sass +4 -0
  99. data/frameworks/compass/templates/project/screen.sass +4 -0
  100. data/frameworks/yui/COPYRIGHT +15 -0
  101. data/frameworks/yui/stylesheets/yui/_screen.sass +7 -0
  102. data/frameworks/yui/stylesheets/yui/modules/_base.sass +60 -0
  103. data/frameworks/yui/stylesheets/yui/modules/_fonts.sass +38 -0
  104. data/frameworks/yui/stylesheets/yui/modules/_grids.sass +341 -0
  105. data/frameworks/yui/templates/project/screen.sass +5 -0
  106. data/lib/compass.rb +19 -0
  107. data/lib/compass/commands/base.rb +94 -0
  108. data/lib/compass/commands/create_project.rb +30 -0
  109. data/lib/compass/commands/install_rails.rb +115 -0
  110. data/lib/compass/commands/print_version.rb +23 -0
  111. data/lib/compass/commands/update_project.rb +91 -0
  112. data/lib/compass/commands/watch_project.rb +42 -0
  113. data/lib/compass/core_ext.rb +39 -0
  114. data/lib/compass/exec.rb +156 -0
  115. data/lib/compass/frameworks.rb +27 -0
  116. data/lib/compass/frameworks/blueprint.rb +2 -0
  117. data/lib/compass/frameworks/compass.rb +2 -0
  118. data/lib/compass/frameworks/yui.rb +2 -0
  119. data/lib/compass/merb.rb +43 -0
  120. data/lib/compass/test_case.rb +37 -0
  121. data/lib/compass/validate.rb +13 -0
  122. data/lib/compass/validate/COPYRIGHT.html +93 -0
  123. data/lib/compass/validate/JIGSAW_COPYRIGHT +64 -0
  124. data/lib/compass/validate/README.html +83 -0
  125. data/lib/compass/validate/XERCES_COPYING.txt +56 -0
  126. data/lib/compass/validate/css-validator-javadoc.jar +0 -0
  127. data/lib/compass/validate/css-validator.jar +0 -0
  128. data/lib/compass/validate/jigsaw.jar +0 -0
  129. data/lib/compass/validate/xerces.jar +0 -0
  130. data/lib/compass/validator.rb +59 -0
  131. data/lib/compass/version.rb +48 -0
  132. data/lib/sass_extensions.rb +13 -0
  133. data/test/compass_test.rb +142 -0
  134. data/test/fixtures/stylesheets/default/sass/ie.sass +4 -0
  135. data/test/fixtures/stylesheets/default/sass/print.sass +4 -0
  136. data/test/fixtures/stylesheets/default/sass/screen.sass +18 -0
  137. data/test/fixtures/stylesheets/yui/css/mixins.css +16 -0
  138. data/test/fixtures/stylesheets/yui/sass/base.sass +3 -0
  139. data/test/fixtures/stylesheets/yui/sass/fonts.sass +3 -0
  140. data/test/fixtures/stylesheets/yui/sass/grids.sass +3 -0
  141. data/test/fixtures/stylesheets/yui/sass/mixins.sass +16 -0
  142. data/test/sass_extensions_test.rb +26 -0
  143. data/test/test_helper.rb +37 -0
  144. metadata +247 -0
@@ -0,0 +1,5 @@
1
+ @import yui/screen.sass
2
+ @import compass/reset.sass
3
+
4
+ body
5
+ +yui
data/lib/compass.rb ADDED
@@ -0,0 +1,19 @@
1
+ require 'sass'
2
+ require File.join(File.dirname(__FILE__), 'sass_extensions')
3
+
4
+ ['core_ext', 'version'].each do |file|
5
+ require File.join(File.dirname(__FILE__), 'compass', file)
6
+ end
7
+
8
+ module Compass
9
+ extend Compass::Version
10
+ def base_directory
11
+ File.expand_path(File.join(File.dirname(__FILE__), '..'))
12
+ end
13
+ module_function :base_directory
14
+ end
15
+
16
+ require File.join(File.dirname(__FILE__), 'compass', 'frameworks')
17
+ # make sure we're running inside Merb
18
+ require File.join(File.dirname(__FILE__), 'compass', 'merb') if defined?(Merb::Plugins)
19
+
@@ -0,0 +1,94 @@
1
+ module Compass
2
+ module Commands
3
+ class Base
4
+ attr_accessor :working_directory, :options
5
+ def initialize(working_directory, options)
6
+ self.working_directory = working_directory
7
+ self.options = options
8
+ end
9
+
10
+ def perform
11
+ raise StandardError.new("Not Implemented")
12
+ end
13
+
14
+ protected
15
+
16
+ def projectize(path)
17
+ File.join(project_directory, separate(path))
18
+ end
19
+ # create a directory and all the directories necessary to reach it.
20
+ def directory(subdir, options = nil)
21
+ options ||= self.options
22
+ dir = subdir ? projectize(subdir) : project_directory
23
+ if File.exists?(dir) && File.directory?(dir) && options[:force]
24
+ print_action :exists, basename(dir) + File::SEPARATOR
25
+ elsif File.exists?(dir) && File.directory?(dir)
26
+ msg = "Directory #{basename(dir)} already exists. Run with --force to force project creation."
27
+ raise ::Compass::Exec::ExecError.new(msg)
28
+ elsif File.exists?(dir)
29
+ msg = "#{basename(dir)} already exists and is not a directory."
30
+ raise ::Compass::Exec::ExecError.new(msg)
31
+ else
32
+ print_action :directory, basename(dir) + File::SEPARATOR
33
+ FileUtils.mkdir_p(dir) unless options[:dry_run]
34
+ end
35
+ end
36
+
37
+ # copy/process a template in the compass template directory to the project directory.
38
+ def template(from, to, options)
39
+ to = projectize(to)
40
+ from = File.join(templates_directory, separate(from))
41
+ if File.exists?(to) && !options[:force]
42
+ #TODO: Detect differences & provide an overwrite prompt
43
+ msg = "#{basename(to)} already exists."
44
+ raise ::Compass::Exec::ExecError.new(msg)
45
+ elsif File.exists?(to)
46
+ print_action :remove, basename(to)
47
+ FileUtils.rm to unless options[:dry_run]
48
+ end
49
+ print_action :create, basename(to)
50
+ FileUtils.cp from, to unless options[:dry_run]
51
+ end
52
+
53
+ def write_file(file_name, contents)
54
+ if File.exists?(file_name) && !options[:force]
55
+ msg = "File #{basename(file_name)} already exists. Run with --force to force creation."
56
+ raise ::Compass::Exec::ExecError.new(msg)
57
+ end
58
+ if File.exists?(file_name)
59
+ print_action :overwrite, basename(file_name)
60
+ else
61
+ print_action :create, basename(file_name)
62
+ end
63
+ output = open(file_name,'w')
64
+ output.write(contents)
65
+ output.close
66
+ end
67
+
68
+ # returns the path to the templates directory and caches it
69
+ def templates_directory
70
+ @templates_directory ||= File.expand_path(File.join(File.dirname(__FILE__), separate("../../../frameworks/#{options[:framework]}/templates")))
71
+ end
72
+
73
+ # Write paths like we're on unix and then fix it
74
+ def separate(path)
75
+ path.gsub(%r{/}, File::SEPARATOR)
76
+ end
77
+
78
+ def basename(file, extra = 0)
79
+ if file.length > (working_directory.length + extra)
80
+ file[(working_directory.length + extra + 1)..-1]
81
+ else
82
+ File.basename(file)
83
+ end
84
+ end
85
+
86
+ ACTIONS = [:directory, :exists, :remove, :create, :overwrite]
87
+ MAX_ACTION_LENGTH = ACTIONS.inject(0){|memo, a| [memo, a.to_s.length].max}
88
+ def print_action(action, extra)
89
+ puts "#{' ' * (MAX_ACTION_LENGTH - action.to_s.length)}#{action} #{extra}" if !options[:quiet] || options[:dry_run]
90
+ end
91
+
92
+ end
93
+ end
94
+ end
@@ -0,0 +1,30 @@
1
+ require 'fileutils'
2
+ require File.join(File.dirname(__FILE__), 'base')
3
+ require File.join(File.dirname(__FILE__), 'update_project')
4
+
5
+ module Compass
6
+ module Commands
7
+ class CreateProject < Base
8
+
9
+ attr_accessor :project_directory, :project_name
10
+
11
+ def initialize(working_directory, options)
12
+ super(working_directory, options)
13
+ self.project_name = options[:project_name]
14
+ self.project_directory = File.expand_path File.join(working_directory, project_name)
15
+ end
16
+
17
+ # all commands must implement perform
18
+ def perform
19
+ directory nil, options
20
+ directory 'stylesheets', options.merge(:force => true)
21
+ directory 'src', options.merge(:force => true)
22
+ template 'project/screen.sass', 'src/screen.sass', options
23
+ template 'project/print.sass', 'src/print.sass', options
24
+ template 'project/ie.sass', 'src/ie.sass', options
25
+ UpdateProject.new(working_directory, options).perform
26
+ end
27
+
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,115 @@
1
+ require File.join(File.dirname(__FILE__), 'base')
2
+
3
+ module Compass
4
+ module Commands
5
+ class InstallRails < Base
6
+ def initialize(working_directory, options)
7
+ super(working_directory, options)
8
+ end
9
+ def perform
10
+ set_install_location
11
+ set_output_location
12
+ directory options[:stylesheets_location]
13
+ template 'project/screen.sass', "#{options[:stylesheets_location]}/screen.sass", options
14
+ template 'project/print.sass', "#{options[:stylesheets_location]}/print.sass", options
15
+ template 'project/ie.sass', "#{options[:stylesheets_location]}/ie.sass", options
16
+ write_file projectize('config/initializers/compass.rb'), initializer_contents
17
+ if has_application_layout?
18
+ next_steps
19
+ else
20
+ write_file projectize('app/views/layouts/application.html.haml'), application_layout_contents
21
+ end
22
+ end
23
+
24
+ def initializer
25
+ init_file =
26
+ if File.exists?(init_file) && !options[:force]
27
+ msg = "File #{basename(init_file)} already exists. Run with --force to force project creation."
28
+ raise ::Compass::Exec::ExecError.new(msg)
29
+ end
30
+ if File.exists?(init_file)
31
+ print_action :overwrite, basename(init_file)
32
+ else
33
+ print_action :create, basename(init_file)
34
+ end
35
+ output = open(init_file,'w')
36
+ output.write(initializer_contents)
37
+ output.close
38
+ end
39
+
40
+ def initializer_contents
41
+ %Q{require 'compass'
42
+ # If you have any compass plugins, require them here.
43
+ Sass::Plugin.options[:template_location] = {
44
+ "\#{RAILS_ROOT}#{File::SEPARATOR}#{options[:stylesheets_location]}" => "\#{RAILS_ROOT}#{File::SEPARATOR}#{options[:css_location]}"
45
+ }
46
+ Compass::Frameworks::ALL.each do |framework|
47
+ Sass::Plugin.options[:template_location][framework.stylesheets_directory] = "\#{RAILS_ROOT}#{File::SEPARATOR}#{options[:css_location]}"
48
+ end
49
+ }
50
+ end
51
+
52
+ def application_layout_contents
53
+ %Q{!!! XML
54
+ !!!
55
+ %html{:xmlns => "http://www.w3.org/1999/xhtml", "xml:lang" => "en", :lang => "en"}
56
+ %head
57
+ %meta{'http-equiv' => "content-type", :content => "text/html;charset=UTF-8"}
58
+ %title= @browser_title || 'Default Browser Title'
59
+ = stylesheet_link_tag '#{stylesheet_prefix}screen.css', :media => 'screen, projection'
60
+ = stylesheet_link_tag '#{stylesheet_prefix}print.css', :media => 'print'
61
+ /[if IE]
62
+ = stylesheet_link_tag '#{stylesheet_prefix}ie.css', :media => 'screen, projection'
63
+ %body
64
+ %h1 Welcome to Compass
65
+ = yield
66
+ }
67
+ end
68
+
69
+ def next_steps
70
+ puts <<NEXTSTEPS
71
+
72
+ Congratulations! Your project has been configured to use Compass.
73
+ Next add these lines to the head of your application.html.haml:
74
+
75
+ %head
76
+ = stylesheet_link_tag '#{stylesheet_prefix}screen.css', :media => 'screen, projection'
77
+ = stylesheet_link_tag '#{stylesheet_prefix}print.css', :media => 'print'
78
+ /[if IE]
79
+ = stylesheet_link_tag '#{stylesheet_prefix}ie.css', :media => 'screen, projection'
80
+
81
+ (you are using haml, aren't you?)
82
+ NEXTSTEPS
83
+ end
84
+
85
+ def has_application_layout?
86
+ File.exists?(projectize('app/views/layouts/application.rhtml')) ||
87
+ File.exists?(projectize('app/views/layouts/application.html.erb')) ||
88
+ File.exists?(projectize('app/views/layouts/application.html.haml'))
89
+ end
90
+
91
+ def stylesheet_prefix
92
+ if options[:css_location].length >= 19
93
+ "#{options[:css_location][19..-1]}/"
94
+ else
95
+ nil
96
+ end
97
+ end
98
+
99
+ def project_directory
100
+ working_directory
101
+ end
102
+
103
+ def set_install_location
104
+ print "Compass recommends that you keep your stylesheets in app/stylesheets/ instead of the Sass default location of public/stylesheets/sass/.\nIs this OK? (Y/n) "
105
+ answer = gets
106
+ self.options[:stylesheets_location] = separate(answer.downcase[0] == ?n ? 'public/stylesheets/sass' : 'app/stylesheets')
107
+ end
108
+ def set_output_location
109
+ print "\nCompass recommends that you keep your compiled css in public/stylesheets/compiled/ instead the Sass default of public/stylesheets/.\nHowever, if you're exclusively using Sass, then public/stylesheets/ is recommended.\nEmit compiled stylesheets to public/stylesheets/compiled? (Y/n) "
110
+ answer = gets
111
+ self.options[:css_location] = separate(answer.downcase[0] == ?n ? 'public/stylesheets' : 'public/stylesheets/compiled')
112
+ end
113
+ end
114
+ end
115
+ end
@@ -0,0 +1,23 @@
1
+ module Compass
2
+ module Commands
3
+ class PrintVersion
4
+ attr_accessor :options
5
+ def initialize(working_directory, options)
6
+ self.options = options
7
+ end
8
+
9
+ def perform
10
+ if options[:quiet]
11
+ # The quiet option may make scripting easier
12
+ puts ::Compass.version[:string]
13
+ else
14
+ lines = []
15
+ lines << "Compass #{::Compass.version[:string]}"
16
+ lines << "Copyright (c) 2008 Chris Eppstein"
17
+ lines << "Released under the MIT License."
18
+ puts lines.join("\n")
19
+ end
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,91 @@
1
+ require 'rubygems'
2
+ require 'sass'
3
+ require 'fileutils'
4
+ require 'pathname'
5
+ require File.join(File.dirname(__FILE__), 'base')
6
+
7
+ module Compass
8
+ module Commands
9
+ class UpdateProject < Base
10
+
11
+ Base::ACTIONS << :compile
12
+ Base::ACTIONS << :overwrite
13
+
14
+ attr_accessor :project_directory, :project_name, :options
15
+
16
+ def initialize(working_directory, options = {})
17
+ super(working_directory, options)
18
+ if options[:project_name]
19
+ options[:project_name] = options[:project_name][0..-2] if options[:project_name][-1..-1] == File::SEPARATOR
20
+ self.project_name = File.basename(options[:project_name])
21
+ if options[:project_name][0] == File::SEPARATOR
22
+ self.project_directory = options[:project_name]
23
+ elsif File.directory?(File.join(working_directory, options[:project_name]))
24
+ self.project_directory = File.expand_path(File.join(working_directory, options[:project_name]))
25
+ else
26
+ if File.exists?(options[:project_name]) or File.exists?(File.join(working_directory, options[:project_name]))
27
+ raise ::Compass::Exec::ExecError.new("#{options[:project_name]} is not a directory.")
28
+ elsif !(options[:force] || options[:dry_run])
29
+ raise ::Compass::Exec::ExecError.new("#{options[:project_name]} does not exist.")
30
+ end
31
+ end
32
+ else
33
+ self.project_name = File.basename(working_directory)
34
+ self.project_directory = working_directory
35
+ end
36
+ end
37
+
38
+ def perform
39
+ Dir.glob(separate("#{project_directory}/src/**/[^_]*.sass")).each do |sass_file|
40
+ stylesheet_name = sass_file[("#{project_directory}/src/".length)..-6]
41
+ compile "src/#{stylesheet_name}.sass", "stylesheets/#{stylesheet_name}.css", options
42
+ end
43
+ end
44
+
45
+ # Compile one Sass file
46
+ def compile(sass_filename, css_filename, options)
47
+ sass_filename = projectize(sass_filename)
48
+ css_filename = projectize(css_filename)
49
+ if !File.directory?(File.dirname(css_filename))
50
+ directory basename(File.dirname(css_filename)), options.merge(:force => true) unless options[:dry_run]
51
+ end
52
+ print_action :compile, basename(sass_filename)
53
+ if File.exists?(css_filename)
54
+ print_action :overwrite, basename(css_filename)
55
+ else
56
+ print_action :create, basename(css_filename)
57
+ end
58
+ unless options[:dry_run]
59
+ engine = ::Sass::Engine.new(open(sass_filename).read,
60
+ :filename => sass_filename,
61
+ :line_comments => options[:environment] == :development,
62
+ :style => output_style,
63
+ :css_filename => css_filename,
64
+ :load_paths => sass_load_paths)
65
+ output = open(css_filename,'w')
66
+ output.write(engine.render)
67
+ output.close
68
+ end
69
+ end
70
+
71
+ def output_style
72
+ @output_style ||= options[:style] || if options[:environment] == :development
73
+ :expanded
74
+ else
75
+ :compact
76
+ end
77
+ end
78
+
79
+ # where to load sass files from
80
+ def sass_load_paths
81
+ @sass_load_paths ||= [project_src_directory] + Compass::Frameworks::ALL.map{|f| f.stylesheets_directory}
82
+ end
83
+
84
+ # The directory where the project source files are located.
85
+ def project_src_directory
86
+ @project_src_directory ||= separate("#{project_directory}/src")
87
+ end
88
+
89
+ end
90
+ end
91
+ end
@@ -0,0 +1,42 @@
1
+ require 'rubygems'
2
+ require 'sass'
3
+ require 'fileutils'
4
+ require 'pathname'
5
+ require File.join(File.dirname(__FILE__), 'base')
6
+ require File.join(File.dirname(__FILE__), 'update_project')
7
+
8
+ module Compass
9
+ module Commands
10
+ class WatchProject < UpdateProject
11
+ attr_accessor :last_update_time
12
+ def perform
13
+ super
14
+ self.last_update_time = most_recent_update_time
15
+ loop do
16
+ # TODO: Make this efficient by using filesystem monitoring.
17
+ sleep 1
18
+ file, t = should_update?
19
+ if t
20
+ begin
21
+ puts ">>> Change detected to #{file} <<<"
22
+ super
23
+ rescue StandardError => e
24
+ ::Compass::Exec.report_error(e, options)
25
+ end
26
+ self.last_update_time = t
27
+ end
28
+ end
29
+ end
30
+ def most_recent_update_time
31
+ Dir.glob(separate("#{project_directory}/src/**/*.sass")).map {|sass_file| File.stat(sass_file).mtime}.max
32
+ end
33
+ def should_update?
34
+ t = most_recent_update_time
35
+ if t > last_update_time
36
+ file = Dir.glob(separate("#{project_directory}/src/**/*.sass")).detect {|sass_file| File.stat(sass_file).mtime >= t}
37
+ [file, t]
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,39 @@
1
+ class String
2
+ # see if string has any content
3
+ def blank?; self.length.zero?; end
4
+
5
+ # strip space after :, remove newlines, replace multiple spaces with only one space, remove comments
6
+ def strip_space!
7
+ replace self.gsub(/:\s*/, ':').gsub(/\n/, '').gsub(/\s+/, ' ').gsub(/(\/\*).*?(\*\/)/, '')
8
+ end
9
+
10
+ # remove newlines, insert space after comma, replace two spaces with one space after comma
11
+ def strip_selector_space!
12
+ replace self.gsub(/(\n)/, '').gsub(',', ', ').gsub(', ', ', ')
13
+ end
14
+
15
+ # remove leading whitespace, remove end whitespace
16
+ def strip_side_space!
17
+ replace self.gsub(/^\s+/, '').gsub(/\s+$/, $/)
18
+ end
19
+ end
20
+
21
+ class NilClass
22
+ def blank?
23
+ true
24
+ end
25
+ end
26
+
27
+ class File
28
+ # string output from file
29
+ def self.path_to_string(path)
30
+ File.new(path).read
31
+ end
32
+
33
+ # saves a string to a specified file path
34
+ def self.string_to_file(string, path)
35
+ directory = File.dirname(path)
36
+ FileUtils.mkdir_p directory unless File.directory?(directory)
37
+ File.open(path, 'w') { |f| f << string }
38
+ end
39
+ end