Last active
August 29, 2015 14:00
-
-
Save backpackerhh/11333441 to your computer and use it in GitHub Desktop.
Modals in Rails with jQuery, Haml, SASS & Twitter Bootstrap 2.3+
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Some basic styles | |
.modal { | |
width: 660px; | |
.modal-header { | |
.close { | |
margin: 0; | |
padding: 0; | |
&:hover { opacity: 1; } | |
} | |
h3 { font-size: 20px; } | |
} | |
.modal-body { | |
padding: 10px; | |
position: relative; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
def link_to_modal(*args, &block) | |
if block_given? | |
name = capture(&block) | |
options = args[0] || {} | |
html_options = args[1] || {} | |
else | |
name = args[0] | |
options = args[1] || {} | |
html_options = args[2] || {} | |
end | |
link_to name, options, html_options.merge('data-toggle' => 'modal', role: 'button') | |
end | |
def modal(id, label_id = "#{id}Label", label:, &block) | |
raise ArgumentError.new 'No block given with modal content' unless block_given? | |
capture_haml do | |
haml_tag :div, { | |
id: id, | |
class: 'modal hide fade', | |
tabindex: -1, | |
role: 'dialog', | |
'aria-labelledby' => label_id, | |
'aria-hidden' => true | |
} do | |
haml_tag :div, class: 'modal-header' do | |
haml_tag :button, { | |
type: 'button', | |
class: 'btn btn-link close', | |
'data-dismiss' => 'modal', | |
'aria-hidden' => true | |
} do | |
haml_tag :img, src: '<path/to/image>', alt: '<Alternative text>' | |
end | |
haml_tag :h3, label, id: label_id | |
end | |
haml_tag :div, capture(&block), class: 'modal-body' | |
end | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Use 'nokogiri' gem to check HTML nodes. | |
# Note: I prefer to skip the "single expectation test" in this kind of test. | |
describe "link_to_modal(*args, &block)" do | |
let(:block) { ->{ content_tag(:strong, 'myText') } } | |
context "with a block" do | |
it "creates a link with given block and target to open related modal" do | |
link = Nokogiri::HTML(helper.link_to_modal('#target', &block)).css('a')[0] | |
expect(link.attributes['href'].value).to eq('#target') | |
expect(link.attributes['data-toggle'].value).to eq('modal') | |
expect(link.attributes['role'].value).to eq('button') | |
expect(link.css('strong')[0].text).to eq('myText') | |
end | |
it "creates a link with given block, target, and attributes to open related modal" do | |
link = Nokogiri::HTML(helper.link_to_modal('#target', id: 'myLink', &block)).css('a')[0] | |
expect(link.attributes['id'].value).to eq('myLink') | |
end | |
end | |
context "with no block" do | |
it "creates a link with given text and target to open related modal" do | |
link = Nokogiri::HTML(helper.link_to_modal('myText', '#target')).css('a')[0] | |
expect(link.text).to eq('myText') | |
expect(link.attributes['href'].value).to eq('#target') | |
expect(link.attributes['data-toggle'].value).to eq('modal') | |
expect(link.attributes['role'].value).to eq('button') | |
end | |
it "creates a link with given text, target, and attributes to open related modal" do | |
link = Nokogiri::HTML(helper.link_to_modal('myText', '#target', id: 'myLink')).css('a')[0] | |
expect(link.attributes['id'].value).to eq('myLink') | |
end | |
end | |
end | |
describe "modal(id, label_id, label:, &block)" do | |
let(:content) { ->{ content_tag(:div, nil, id: 'myBlockId') } } | |
let(:modal) { Nokogiri::HTML(helper.modal('myId', label: 'myLabelText', &content)).css('div')[0] } | |
let(:modal_header) { modal.css('div')[0] } | |
let(:close_button) { modal_header.css('button')[0] } | |
let(:label) { modal_header.css('h3')[0] } | |
let(:modal_body) { modal.css('div')[1] } | |
it "render given content to show it after clicking a specified link" do | |
expect(modal.attributes['id'].value).to eq('myId') | |
expect(modal.attributes['aria-labelledby'].value).to eq('myIdLabel') | |
expect(modal.attributes['aria-hidden'].value).to be_true | |
expect(modal.attributes['role'].value).to eq('dialog') | |
expect(modal.attributes['tabindex'].value).to eq('-1') | |
expect(close_button.attributes['type'].value).to eq('button') | |
expect(close_button.attributes['aria-hidden'].value).to be_true | |
expect(close_button.attributes['data-dismiss'].value).to eq('modal') | |
expect(close_button.attributes['class'].value).to include('close') | |
expect(label.attributes['id'].value).to eq('myIdLabel') | |
expect(label.text).to eq('myLabelText') | |
expect(modal_body).to have_selector 'div#myBlockId' | |
end | |
it "raises error when no block is given" do | |
expect { helper.modal('myId', label: 'myLabelText') }.to raise_error ArgumentError | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
= link_to_modal 'Text', '#<id>' | |
= modal '<id>', label: 'Your label' do | |
-# any content to display |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment