def self.merge(*rule_sets)
@folded_declaration_cache = {}
rule_sets.flatten! if rule_sets[0].kind_of?(Array)
unless rule_sets.all? {|rs| rs.kind_of?(CssParser::RuleSet)}
raise ArgumentError, "all parameters must be CssParser::RuleSets."
end
return rule_sets[0] if rule_sets.length == 1
properties = {}
rule_sets.each do |rule_set|
rule_set.expand_shorthand!
specificity = rule_set.specificity
unless specificity
if rule_set.selectors.length == 0
specificity = 0
else
specificity = rule_set.selectors.map { |s| calculate_specificity(s) }.compact.max || 0
end
end
rule_set.each_declaration do |property, value, is_important|
if not properties.has_key?(property)
properties[property] = {:value => value, :specificity => specificity, :is_important => is_important}
elsif is_important
if not properties[property][:is_important] or properties[property][:specificity] <= specificity
properties[property] = {:value => value, :specificity => specificity, :is_important => is_important}
end
elsif properties[property][:specificity] < specificity or properties[property][:specificity] == specificity
unless properties[property][:is_important]
properties[property] = {:value => value, :specificity => specificity, :is_important => is_important}
end
end
end
end
merged = RuleSet.new(nil, nil)
properties.each do |property, details|
if details[:is_important]
merged[property.strip] = details[:value].strip.gsub(/\;\Z/, '') + '!important'
else
merged[property.strip] = details[:value].strip
end
end
merged.create_shorthand!
merged
end