Skip to content

Commit c27e3ec

Browse files
committed
Add ui/forms/address component
1 parent b9a0226 commit c27e3ec

File tree

6 files changed

+105
-0
lines changed

6 files changed

+105
-0
lines changed
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
<fieldset class="<%= stimulus_id %>"
2+
data-controller="<%= stimulus_id %>"
3+
<%= :disabled if @disabled %>
4+
>
5+
<div class="<%= stimulus_id %>--address-form flex flex-wrap gap-4 pb-4">
6+
<%= render component("ui/forms/field").text_field(@form, :name) %>
7+
<%= render component("ui/forms/field").text_field(@form, :address1) %>
8+
<%= render component("ui/forms/field").text_field(@form, :address2) %>
9+
<div class="flex w-full space-x-4">
10+
<%= render component("ui/forms/field").text_field(@form, :city, class: "flex-1") %>
11+
<%= render component("ui/forms/field").text_field(@form, :zipcode, class: "flex-1") %>
12+
</div>
13+
14+
<%= render component("ui/forms/field").select(
15+
@form,
16+
:country_id,
17+
Spree::Country.all.map { |c| [c.name, c.id] },
18+
value: @form.object.try(:country_id),
19+
"data-#{stimulus_id}-target": "country",
20+
"data-action": "change->#{stimulus_id}#loadStates"
21+
) %>
22+
23+
<%= render component("ui/forms/field").select(
24+
@form,
25+
:state_id,
26+
[],
27+
value: @form.object.try(:state_id),
28+
"data-#{stimulus_id}-target": "state"
29+
) %>
30+
31+
<%= render component("ui/forms/field").text_field(@form, :phone) %>
32+
</div>
33+
</fieldset>
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
import { Controller } from '@hotwired/stimulus'
2+
3+
export default class extends Controller {
4+
static targets = ["country", "state"]
5+
6+
connect() {
7+
this.loadStates()
8+
}
9+
10+
loadStates() {
11+
const countryId = this.countryTarget.value
12+
13+
fetch(`/admin/countries/${countryId}/states`)
14+
.then(response => response.json())
15+
.then(data => {
16+
this.updateStateOptions(data)
17+
})
18+
}
19+
20+
updateStateOptions(data) {
21+
const stateSelect = this.stateTarget
22+
23+
stateSelect.innerHTML = ""
24+
25+
data.forEach(state => {
26+
const option = document.createElement("option")
27+
28+
option.value = state.id
29+
option.innerText = state.name
30+
stateSelect.appendChild(option)
31+
})
32+
}
33+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
# frozen_string_literal: true
2+
3+
class SolidusAdmin::UI::Forms::Address::Component < SolidusAdmin::BaseComponent
4+
def initialize(form:, disabled: false)
5+
@form = form
6+
@disabled = disabled
7+
end
8+
end
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
# frozen_string_literal: true
2+
3+
# @component "ui/forms/address"
4+
class SolidusAdmin::UI::Forms::Address::ComponentPreview < ViewComponent::Preview
5+
include SolidusAdmin::Preview
6+
7+
def overview
8+
render_with_template
9+
end
10+
11+
# @param disabled toggle
12+
def playground(disabled: false)
13+
view = ActionView::Base.new(ActionView::LookupContext.new([]), {}, nil)
14+
render component("ui/forms/address").new(
15+
form: ActionView::Helpers::FormBuilder.new(:address, Spree::Address.new, view, {}),
16+
disabled: disabled
17+
)
18+
end
19+
end
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
<%= form_for Spree::Address.new, url: '#' do |f| %>
2+
<%= render current_component.new(form: f, disabled: false) %>
3+
<% end %>
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
# frozen_string_literal: true
2+
3+
require "spec_helper"
4+
5+
RSpec.describe SolidusAdmin::UI::Forms::Address::Component, type: :component do
6+
it "renders the overview preview" do
7+
render_preview(:overview)
8+
end
9+
end

0 commit comments

Comments
 (0)