Calculator

Diagnostic Fee Calculator (Sheet) + Phone Script Mini‑Card

Calculator + script kit for owner‑operators to set a defensible diagnostic/service‑call fee using loaded rate, windshield time, first‑hour productivity, and close rate. Includes a phone script mini‑card, invoice line‑item structure, and rollout metrics.

Set, explain, and enforce a diagnostic/service‑call fee without guessing. Plug in your shop’s numbers to get two defensible fee targets (non‑convert and pooled/crediting), then hand the CSR mini‑card to your phones team. Built for HVAC, plumbing, electrical, and similar residential service.

Input: [Loaded hourly rate per billable hour (L)]

Your true, fully loaded $/billable hour for service work. Include wage, benefits/burden, vehicle, tools, uniforms, insurance, software, and overhead allocated to service, divided by expected billable hours. If you don’t track it yet, use your internal labor‑rate method and enter that figure here. Valid range: any positive dollar value. Default: [ENTER YOUR RATE].

Input: [Average windshield time — minutes (W)]

Average one‑way drive time from the previous stop (or shop) to the diagnostic visit. Pull from GPS/CRM over the last 30 days; exclude outliers if needed. Use a realistic average your dispatch sees most days. Units: minutes. Valid range: 0–120. Default: [30].

Input: [Average diagnostic time on site — minutes (D)]

Average on‑site time to greet, diagnose, and build a same‑day repair option (no repair time). Units: minutes. Valid range: 15–120. Default: [40].

Input: [First‑hour productivity (P)]

Percent of the first hour that’s actually productive billable time (setup/admin eats the rest). Enter as a decimal in the Sheet (e.g., 0.70 for 70%). Valid range: 0.30–1.00. Default: [0.70].

Input: [Diagnostic close rate — same‑day approval (C)]

Percent of diagnostic visits that approve a same‑day repair. Enter as a decimal (e.g., 0.60). Valid range: 0.00–0.95 (use 0.95 cap for math safety). Default: [0.60].

Output: [Cost basis — effective billable hours per diagnostic visit]

We translate minutes and first‑hour drag into effective billable hours, then multiply by your loaded rate to get your cost per diagnostic visit. Use this as the base for both fee options. Formulas:

  • Define minutes: T = W + D
  • First hour minutes: T1 = MIN(T, 60)
  • Beyond first hour: T2 = MAX(T - 60, 0)
  • Effective billable hours: H = (T1/60)/P + (T2/60)
  • Cost basis ($): Cost = L * H

Note: The P adjustment only applies to the first 60 minutes to reflect real first‑hour inefficiency. Keep P as a decimal in your sheet.

Output: [Non‑convert breakeven fee — F_nonconvert]

If a call does not convert to a repair, this fee covers your time at break‑even. Round up to a clean price.

  • Math: F_nonconvert = CEILING( Cost , 10 )
  • Google Sheets formula (assuming: L=B3, W=B4, D=B5, P=B6):

```
=CEILING( $B$3 * ( (MIN($B$4+$B$5,60)/60)/$B$6 + MAX($B$4+$B$5-60,0)/60 ), 10 )
```
Tip: Use CEILING to round to the next $10 for a clean published fee.

Output: [Pooled breakeven if crediting fees — F_pooled]

If you credit the diagnostic fee to same‑day repairs (common policy), you only keep the fee on non‑converts. Price so that non‑converts, on average, cover all visits.

  • Math: F_pooled = CEILING( Cost / (1 - C) , 10 )
  • Google Sheets formula (same inputs plus C=B7):

```
=IF($B$7>=0.95,
"Close rate too high to credit 100% — consider fee‑stands policy",
CEILING( ($B$3 * ( (MIN($B$4+$B$5,60)/60)/$B$6 + MAX($B$4+$B$5-60,0)/60 )) / (1 - $B$7), 10 )
)
```
Note: If C→1, pooled math blows up. In that case, run a fee‑stands policy or reduce the credit.

Output: [Recommended seasonal targets — publish this]

Pick your policy and publish a clean number. Use a light capacity buffer in season.

  • If you CREDIT the fee to same‑day repairs:
  • In‑season target: Fpublish = CEILING( MAX(Fnonconvert, F_pooled) * 1.10 , 10 )
  • Off‑season target: Fpublish = CEILING( MAX(Fnonconvert, F_pooled) * 1.00 , 10 )
  • If your FEE STANDS on every visit (members get a small loyalty credit):
  • In‑season target: Fpublish = CEILING( MAX(Fnonconvert, Cost) * 1.10 , 10 )
  • Off‑season target: Fpublish = CEILING( MAX(Fnonconvert, Cost) * 1.00 , 10 )

Notes:

  • 1.10 is a default buffer for peak capacity protection; adjust to taste.
  • Keep the published price ending clean ($79/$89/$99 or rounded to $10s).

Output: [CSR Booking Script Mini‑Card]

Paste on a one‑pager for CSRs. Replace bracketed fields from your sheet.

Script (fee credited to same‑day repair):

  • “We can get you taken care of. Our professional diagnostic visit is [Fpublish]. That covers travel and a full licensed diagnosis. If you approve the repair today, we apply that [Fpublish] to the work. Do you prefer a morning or afternoon window?”

Script (fee stands + member credit):

  • “The visit is [F_publish]. It covers travel and a full licensed diagnosis. Members get a [MemberCredit] credit on today’s visit. Would morning or afternoon work better?”

Four quick objection beats:

  1. Price‑shopper (“Do you waive it?”)
  • “We don’t waive the diagnostic. It protects same‑day availability for customers ready to fix it now. If you approve today’s repair, we [apply it/credit members]. Morning or afternoon?”
  1. Warranty (“Parts are under warranty, so the visit should be free.”)
  • “Manufacturer parts coverage doesn’t include travel or diagnosis. Today’s [F_publish] covers our licensed diagnosis so we can confirm what the warranty covers. Want the 10–12 window?”
  1. Landlord/Tenant (“I’m renting.”)
  • “No problem. The visit is [F_publish]. If your landlord is covering it, we can note them for billing, but we disclose the fee before dispatch. Would you like today or tomorrow?”
  1. “My other guy waives it.”
  • “Some shops fold that cost into repair pricing. We price it up front so you know exactly what the visit includes, and we [apply it with same‑day approval/credit members]. I can hold a 2–4pm — take it?”

Handle‑the‑pause rule: State the fee once, then move straight to scheduling. Don’t fill the silence — let the customer decide.

Output: [Invoice line‑item structure — what the customer sees]

Keep it simple and transparent:

  • Line 1: Service/Diagnostic Visit — includes travel and professional diagnosis[F_publish]
  • Line 2: Repair — [Flat‑rate task/code/description][Price]
  • Optional Line 3 (crediting policy): Diagnostic credit applied to approved same‑day repair‑[F_publish]
  • Optional Line 4 (members): Member loyalty credit‑[MemberCredit]

Notes:

  • Disclose the diagnostic fee before dispatch.
  • Include travel within the diagnostic/service line (avoid a confusing separate “trip” add‑on unless you clearly explain it).

Output: [Post‑rollout metrics to validate the policy]

Track these weekly for 30–60 days after rollout:

  • Fee acceptance rate = booked visits ÷ calls where fee was disclosed.
  • Cancellations after fee disclosure = cancellations ÷ calls where fee was disclosed.
  • Average ticket on diagnostic jobs = revenue ÷ closed diagnostic jobs.

Where to pull: booking report (CSR/CRM), opportunity/close report, job revenue report. If acceptance dips in off‑season, reduce the buffer or tighten windows; if average ticket rises and cancellations are stable, hold your line.

Output: [Google Sheets spec — cells and formulas]

Drop these into a clean Google Sheet.

Suggested layout (cells):

  • B3 L (loaded $/billable hr) … default [ENTER]
  • B4 W (windshield, min) … default [30]
  • B5 D (diagnostic, min) … default [40]
  • B6 P (first‑hour productivity, decimal) … default [0.70]
  • B7 C (diagnostic close rate, decimal) … default [0.60]

Derived:

  • B9 H (effective billable hours)

```
=(MIN(B4+B5,60)/60)/B6 + MAX(B4+B5-60,0)/60
```

  • B10 Cost

```
=B3*B9
```

  • B12 F_nonconvert

```
=CEILING(B10,10)
```

  • B13 F_pooled (crediting policy)

```
=IF(B7>=0.95,"Use fee-stands or reduce credit",CEILING(B10/(1-B7),10))
```

  • B15 Publish fee (crediting) — in‑season buffer 10%

```
=IF(ISNUMBER(B13),CEILING(MAX(B12,B13)1.10,10),CEILING(B121.10,10))
```

  • B16 Publish fee (crediting) — off‑season

```
=IF(ISNUMBER(B13),CEILING(MAX(B12,B13),10),CEILING(B12,10))
```

  • B18 Publish fee (fee‑stands) — in‑season

```
=CEILING(MAX(B12,B10)*1.10,10)
```

  • B19 Publish fee (fee‑stands) — off‑season

```
=CEILING(MAX(B12,B10),10)
```

  • B20 MemberCredit (optional 15% loyalty credit)

```
=CEILING(B18*0.15,5)
```
Notes: Enter P and C as decimals (e.g., 0.70, 0.60). Adjust the 1.10 buffer and 0.15 credit to match your capacity and membership promise.