Skip to content

Commit

Permalink
Add utility selection
Browse files Browse the repository at this point in the history
  • Loading branch information
oyamauchi committed Aug 15, 2023
1 parent ca556cd commit bf717ac
Show file tree
Hide file tree
Showing 3 changed files with 185 additions and 99 deletions.
234 changes: 135 additions & 99 deletions src/calculator-form.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { html, css } from 'lit';
import { html, css, nothing } from 'lit';
import { downIcon, questionIcon } from './icons';
import { select, selectStyles, OptionParam } from './select';
import { inputStyles } from './styles/input';
Expand Down Expand Up @@ -73,110 +73,146 @@ const HOUSEHOLD_SIZE_OPTIONS: OptionParam[] = [1, 2, 3, 4, 5, 6, 7, 8].map(
);

export const formTemplate = (
[zip, ownerStatus, householdIncome, taxFiling, householdSize]: Array<string>,
[
zip,
ownerStatus,
householdIncome,
taxFiling,
householdSize,
utility,
]: Array<string>,
showUtilityField: boolean,
utilityOptions: OptionParam[],
onSubmit: (e: SubmitEvent) => void,
) => html`
<form @submit=${onSubmit}>
<div class="grid-3-2">
<div>
<label for="zip">
Zip
onZipChanged: (e: InputEvent) => void,
) => {
const utilityField = showUtilityField
? html`<div>
<label for="utility">
Utility
<sl-tooltip
content="Your zip code helps determine the amount of discounts and tax credits you qualify for."
content="See additional incentives by choosing the company you pay your electric bill to."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
<input
tabindex="0"
id="zip"
placeholder="12345"
name="zip"
required
type="text"
value="${zip}"
minlength="5"
maxlength="5"
inputmode="numeric"
pattern="[0-9]{5}"
/>
</label>
</div>
<div>
<label for="owner_status">
Homeowners Status
<sl-tooltip
content="Homeowners and renters qualify for different incentives."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
${select({
id: 'owner_status',
required: true,
options: OWNER_STATUS_OPTIONS,
currentValue: ownerStatus,
tabIndex: 0,
})}
</label>
</div>
<div>
<label for="household_income">
Household Income
<sl-tooltip
content="Enter your gross income (income before taxes). Include wages and salary plus other forms of income, including pensions, interest, dividends, and rental income. If you are married and file jointly, include your spouse's income"
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
<ra-currency-input
id="household_income"
placeholder="$60,000"
name="household_income"
required
value=${householdIncome}
min="0"
max="100000000"
></ra-currency-input>
</label>
</div>
<div>
<label for="tax_filing">
Tax Filing
<sl-tooltip hoist
><div slot="content">
Select "Head of Household" if you have a child or relative living
with you, and you pay more than half the costs of your home.
Select "Joint" if you file your taxes as a married couple."
</div>
${questionIcon(18, 18)}</sl-tooltip
><br />
>
<br />
${select({
id: 'tax_filing',
required: true,
options: TAX_FILING_OPTIONS,
currentValue: taxFiling,
id: 'utility',
required: false,
options: utilityOptions,
currentValue: utility,
tabIndex: 0,
})}
</label>
</div>`
: nothing;

return html`
<form @submit=${onSubmit}>
<div class="grid-3-2">
<div>
<label for="zip">
Zip
<sl-tooltip
content="Your zip code helps determine the amount of discounts and tax credits you qualify for."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
<input
tabindex="0"
id="zip"
placeholder="12345"
name="zip"
required
type="text"
value="${zip}"
minlength="5"
maxlength="5"
inputmode="numeric"
pattern="[0-9]{5}"
@change=${onZipChanged}
/>
</label>
</div>
<div>
<label for="owner_status">
Homeowners Status
<sl-tooltip
content="Homeowners and renters qualify for different incentives."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
${select({
id: 'owner_status',
required: true,
options: OWNER_STATUS_OPTIONS,
currentValue: ownerStatus,
tabIndex: 0,
})}
</label>
</div>
<div>
<label for="household_income">
Household Income
<sl-tooltip
content="Enter your gross income (income before taxes). Include wages and salary plus other forms of income, including pensions, interest, dividends, and rental income. If you are married and file jointly, include your spouse's income"
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
<ra-currency-input
id="household_income"
placeholder="$60,000"
name="household_income"
required
value=${householdIncome}
min="0"
max="100000000"
></ra-currency-input>
</label>
</div>
<div>
<label for="tax_filing">
Tax Filing
<sl-tooltip hoist
><div slot="content">
Select "Head of Household" if you have a child or relative
living with you, and you pay more than half the costs of your
home. Select "Joint" if you file your taxes as a married
couple."
</div>
${questionIcon(18, 18)}</sl-tooltip
><br />
${select({
id: 'tax_filing',
required: true,
options: TAX_FILING_OPTIONS,
currentValue: taxFiling,
tabIndex: 0,
})}
</label>
</div>
<div>
<label for="household_size">
Household Size
<sl-tooltip
content="Include anyone you live with who you claim as a dependent on your taxes, and your spouse or partner if you file taxes together."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
${select({
id: 'household_size',
required: true,
options: HOUSEHOLD_SIZE_OPTIONS,
currentValue: householdSize,
tabIndex: 0,
})}
</label>
</div>
${utilityField}
<div>
<button type="submit">Calculate! ${downIcon(18, 18)}</button>
</div>
</div>
<div>
<label for="household_size">
Household Size
<sl-tooltip
content="Include anyone you live with who you claim as a dependent on your taxes, and your spouse or partner if you file taxes together."
hoist
>${questionIcon(18, 18)}</sl-tooltip
><br />
${select({
id: 'household_size',
required: true,
options: HOUSEHOLD_SIZE_OPTIONS,
currentValue: householdSize,
tabIndex: 0,
})}
</label>
</div>
<div>
<button type="submit">Calculate! ${downIcon(18, 18)}</button>
</div>
</div>
</form>
`;
</form>
`;
};
3 changes: 3 additions & 0 deletions src/calculator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -156,7 +156,10 @@ export class RewiringAmericaCalculator extends LitElement {
this.taxFiling,
this.householdSize,
],
false,
[],
(event: SubmitEvent) => this.submit(event),
() => {},
)}
</div>
${this.hideResult
Expand Down
47 changes: 47 additions & 0 deletions src/state-calculator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
stateIncentivesTemplate,
stateIncentivesStyles,
} from './state-incentive-details';
import { OptionParam } from './select';

const loadingTemplate = () => html`
<div class="card card-content">Loading...</div>
Expand All @@ -26,6 +27,8 @@ const errorTemplate = (error: unknown) => html`

const DEFAULT_CALCULATOR_API_HOST: string = 'https://api.rewiringamerica.org';

const BLANK_UTILITY: OptionParam = { value: '', label: '' };

@customElement('rewiring-america-state-calculator')
export class RewiringAmericaStateCalculator extends LitElement {
static override styles = [
Expand Down Expand Up @@ -70,6 +73,9 @@ export class RewiringAmericaStateCalculator extends LitElement {
@property({ type: String, attribute: 'household-size' })
householdSize: string = '1';

@property({ type: String, attribute: 'utility' })
utility: string = '';

submit(e: SubmitEvent) {
e.preventDefault();
const formData = new FormData(e.target as HTMLFormElement);
Expand All @@ -78,6 +84,7 @@ export class RewiringAmericaStateCalculator extends LitElement {
this.householdIncome = (formData.get('household_income') as string) || '';
this.taxFiling = (formData.get('tax_filing') as FilingStatus) || '';
this.householdSize = (formData.get('household_size') as string) || '';
this.utility = (formData.get('utility') ?? '') as string;
}

get hideResult() {
Expand All @@ -99,6 +106,7 @@ export class RewiringAmericaStateCalculator extends LitElement {
household_income,
tax_filing,
household_size,
utility,
]) => {
if (this.hideResult) {
// this is a special response type provided by Task to keep it in the INITIAL state
Expand All @@ -113,6 +121,10 @@ export class RewiringAmericaStateCalculator extends LitElement {
});
query.append('authority_types', 'federal');
query.append('authority_types', 'state');
if (utility?.length > 0) {
query.append('authority_types', 'utility');
query.set('utility', utility);
}

return await fetchApi(
this.apiKey,
Expand All @@ -128,9 +140,34 @@ export class RewiringAmericaStateCalculator extends LitElement {
this.householdIncome,
this.taxFiling,
this.householdSize,
this.utility,
],
});

private _utilityOptionsTask = new Task(this, {
task: async ([zip]) => {
const query = new URLSearchParams({
'location[zip]': zip,
});
const url = `${this.apiHost}/api/v1/utilities?${query}`;
const response = await fetch(url, {
method: 'GET',
headers: {
Authorization: `Bearer ${this.apiKey}`,
},
});

const utilityMap = await response.json();
return Object.keys(utilityMap)
.map(id => ({
value: id,
label: utilityMap[id].name,
}))
.sort((a, b) => a.label.localeCompare(b.label));
},
args: () => [this.zip],
});

override render() {
return html`
<div class="calculator">
Expand All @@ -145,8 +182,18 @@ export class RewiringAmericaStateCalculator extends LitElement {
this.householdIncome,
this.taxFiling,
this.householdSize,
this.utility,
],
true,
this._utilityOptionsTask.render({
initial: () => [BLANK_UTILITY],
pending: () => [BLANK_UTILITY],
complete: a => [BLANK_UTILITY, ...a],
error: () => [BLANK_UTILITY],
}) as OptionParam[],
(event: SubmitEvent) => this.submit(event),
(event: InputEvent) =>
(this.zip = (event.target as HTMLInputElement).value),
)}
</div>
${this.hideResult
Expand Down

0 comments on commit bf717ac

Please sign in to comment.