Skip to content

Commit

Permalink
repeat-y for horizontal layouts
Browse files Browse the repository at this point in the history
  • Loading branch information
scottdavis committed Jun 5, 2012
1 parent 5f267a2 commit a8241e7
Show file tree
Hide file tree
Showing 4 changed files with 58 additions and 2 deletions.
7 changes: 6 additions & 1 deletion lib/compass/sass_extensions/sprites/image.rb
Expand Up @@ -8,9 +8,10 @@ class Image
PARENT = %r{(.+)[-_](.+)$}

REPEAT_X = 'repeat-x'
REPEAT_Y = 'repeat-y'
NO_REPEAT = 'no-repeat'

VALID_REPEATS = [REPEAT_X, NO_REPEAT]
VALID_REPEATS = [REPEAT_Y, REPEAT_X, NO_REPEAT]

attr_reader :relative_file, :options, :base
attr_accessor :top, :left
Expand Down Expand Up @@ -73,6 +74,10 @@ def repeat_x?
repeat == REPEAT_X
end

def repeat_y?
repeat == REPEAT_Y
end

def no_repeat?
repeat == NO_REPEAT
end
Expand Down
32 changes: 31 additions & 1 deletion lib/compass/sass_extensions/sprites/layout/horizontal.rb
Expand Up @@ -6,20 +6,35 @@ class Horizontal < SpriteLayout

def layout!
calculate_height!
calculate_positions!
calculate_width!
calculate_positions!
tile_images_that_repeat!
end

private # ===========================================================================================>

def calculate_height!
@height = @images.map {|image| image.height + image.offset}.max
if repeating_images?
calculate_repeat_extra_height!
end
@height
end

def calculate_width!
@width = @images.inject(0) { |sum, image| sum += (image.width + image.spacing) }
end

def repeating_images?
@repeating_images ||= @images.any?(&:repeat_y?)
end

def calculate_repeat_extra_height!
m = @images.inject(1) {|m,img| img.repeat_y? ? m.lcm(img.height) : m }
remainder = @height % m
@height += (m - remainder) unless remainder.zero?
end

def calculate_positions!
@images.each_with_index do |image, index|
image.top = image.position.unit_str == '%' ? (@height - image.height) * (image.position.value / 100.0) : image.position.value
Expand All @@ -29,6 +44,21 @@ def calculate_positions!
end
end

def tile_images_that_repeat!
return unless repeating_images?
@images.map {|img| img if img.repeat_y?}.compact.each do |image|
y = (image.top + image.height)
while y < @height do
begin
img = image.dup
img.top = y.to_i
@images << img
y += image.height
end
end #while
end
end

end
end
end
Expand Down
5 changes: 5 additions & 0 deletions test/units/sprites/image_test.rb
Expand Up @@ -74,6 +74,11 @@ def test_image(options ={})
assert img.repeat_x?
end

test 'image repeat-y' do
img = test_image "selectors_ten_by_ten_repeat" => Sass::Script::String.new('repeat-y')
assert img.repeat_y?
end

test 'image position' do
image = test_image "selectors_ten_by_ten_position" => Sass::Script::Number.new(100, ["px"])
assert_equal 100, image.position.value
Expand Down
16 changes: 16 additions & 0 deletions test/units/sprites/layout_test.rb
Expand Up @@ -67,6 +67,22 @@ def horizontal(options= {})
assert_equal 12, map.width
end

test "repeat-y layout single image" do
opts = {"layout" => Sass::Script::String.new('horizontal'), "squares_ten_by_ten_repeat" => Sass::Script::String.new('repeat-y')}
map = sprite_map_test(@options.merge(opts), 'squares/*.png')
assert_equal 30, map.width
assert_equal 20, map.height
assert_equal 3, map.images.size
assert_equal [[0,0], [0,10], [10,0]], map.images.map { |img| [img.top, img.left] }
assert map.horizontal?
end

test "repeat-y layout multi image" do
opts = {"layout" => Sass::Script::String.new('horizontal'), "repeat_x_three_repeat" => Sass::Script::String.new('repeat-y'), "repeat_x_four_repeat" => Sass::Script::String.new('repeat-y')}
map = sprite_map_test(@options.merge(opts), 'repeat_x/*.png')
assert_equal [[0, 0], [0, 5], [0, 9], [0, 10], [0, 13], [4, 5], [8, 5], [3, 10], [6, 10], [9, 10]], map.images.map { |img| [img.top, img.left] }
end

# VERTICAL LAYOUT

it "should have a vertical layout" do
Expand Down

0 comments on commit a8241e7

Please sign in to comment.