Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

261 строка
15KB

  1. <%
  2. Dim isRemoved, isCustomer, bid, mth, oc, ix, it, indKey2, nextDue
  3. If fv Is Nothing Then Set fv = b
  4. isRemoved = (b("status") & "" = "removed")
  5. isCustomer = (b("is_customer") & "" = "1")
  6. bid = CLng(id)
  7. nextDue = False
  8. If Not IsNull(b("next_action_date")) Then
  9. If IsDate(b("next_action_date")) Then nextDue = (CDate(b("next_action_date")) <= Date)
  10. End If
  11. %>
  12. <% Flash().ShowErrorsIfPresent : Flash().ShowSuccessIfPresent %>
  13. <nav aria-label="breadcrumb">
  14. <ol class="breadcrumb small mb-2">
  15. <li class="breadcrumb-item"><a href="/businesses">Businesses</a></li>
  16. <li class="breadcrumb-item active" aria-current="page"><%= H(b("name")) %></li>
  17. </ol>
  18. </nav>
  19. <div class="d-flex flex-wrap align-items-center gap-2 mb-3">
  20. <h1 class="h3 mb-0"><%= H(b("name")) %></h1>
  21. <span class="badge <%= Businesses_StatusClass(b("status")) %>"><%= Businesses_StatusLabel(b("status")) %></span>
  22. <% If isCustomer Then %><span class="badge text-bg-success">Customer</span><% End If %>
  23. <% If Len(b("industry_name") & "") > 0 Then %><span class="badge text-bg-light border"><%= H(b("industry_name")) %></span><% End If %>
  24. </div>
  25. <% If isRemoved Then %>
  26. <div class="alert alert-dark d-flex justify-content-between align-items-center">
  27. <div>
  28. <strong>Removed</strong><% If Not IsNull(b("removed_at")) Then Response.Write " on " & Date_Fmt(b("removed_at")) %>.
  29. <% If Len(b("removed_reason") & "") > 0 Then %>Reason: <%= H(b("removed_reason")) %><% End If %>
  30. </div>
  31. <form method="post" action="/businesses/<%= bid %>/restore" class="mb-0">
  32. <input type="hidden" name="csrf" value="<%= H(csrf) %>" />
  33. <button type="submit" class="btn btn-sm btn-outline-dark">Restore to list</button>
  34. </form>
  35. </div>
  36. <% ElseIf Not IsNull(b("next_action_date")) Then %>
  37. <div class="alert <% If nextDue Then Response.Write "alert-warning" Else Response.Write "alert-info" %> py-2">
  38. <i class="bi bi-calendar-event"></i> Next contact: <strong><%= Date_Fmt(b("next_action_date")) %></strong><% If nextDue Then Response.Write " &mdash; due" %>
  39. </div>
  40. <% End If %>
  41. <div class="row g-3">
  42. <!-- LEFT: log a touch + history -->
  43. <div class="col-lg-7">
  44. <% If Not isRemoved Then %>
  45. <div class="card shadow-sm mb-3">
  46. <div class="card-body">
  47. <h2 class="h5 mb-3">Log a contact</h2>
  48. <form method="post" action="/businesses/<%= bid %>/log" id="logForm">
  49. <input type="hidden" name="csrf" value="<%= H(csrf) %>" />
  50. <div class="mb-3">
  51. <div class="btn-group" role="group" aria-label="How">
  52. <% For Each mth In Businesses_Methods() %>
  53. <input type="radio" class="btn-check" name="method" id="m_<%= mth(0) %>" value="<%= mth(0) %>" autocomplete="off"<% If mth(0) = "call" Then Response.Write " checked" %> />
  54. <label class="btn btn-outline-primary btn-sm" for="m_<%= mth(0) %>"><%= H(mth(1)) %></label>
  55. <% Next %>
  56. </div>
  57. </div>
  58. <div class="row g-2 mb-2">
  59. <div class="col-md-5">
  60. <label for="outcome" class="form-label small mb-1">Outcome</label>
  61. <select class="form-select form-select-sm" id="outcome" name="outcome">
  62. <option value="">&mdash;</option>
  63. <% For Each oc In Businesses_Outcomes() %>
  64. <option value="<%= oc(0) %>"><%= H(oc(1)) %></option>
  65. <% Next %>
  66. </select>
  67. </div>
  68. <div class="col-6 col-md-3">
  69. <label for="contacted_at" class="form-label small mb-1">Date</label>
  70. <input type="date" class="form-control form-control-sm" id="contacted_at" name="contacted_at" value="<%= today %>" max="<%= Date_Iso(Date + 1) %>" />
  71. </div>
  72. <div class="col-6 col-md-4">
  73. <label for="follow_up_date" class="form-label small mb-1">Contact again on</label>
  74. <input type="date" class="form-control form-control-sm" id="follow_up_date" name="follow_up_date" value="" />
  75. </div>
  76. </div>
  77. <div class="mb-2 small">
  78. <span class="text-muted">Quick:</span>
  79. <button type="button" class="btn btn-link btn-sm p-0 me-2" data-days="3">3 days</button>
  80. <button type="button" class="btn btn-link btn-sm p-0 me-2" data-days="7">1 week</button>
  81. <button type="button" class="btn btn-link btn-sm p-0 me-2" data-days="14">2 weeks</button>
  82. <button type="button" class="btn btn-link btn-sm p-0 me-2" data-days="30">1 month</button>
  83. <button type="button" class="btn btn-link btn-sm p-0 text-secondary" data-days="0">clear</button>
  84. </div>
  85. <div class="mb-3">
  86. <label for="log_notes" class="form-label small mb-1">Notes</label>
  87. <textarea class="form-control form-control-sm" id="log_notes" name="notes" rows="3" maxlength="10000"></textarea>
  88. </div>
  89. <button type="submit" class="btn btn-primary btn-sm"><i class="bi bi-check2"></i> Save contact</button>
  90. <span class="text-muted small ms-2" id="removeHint" hidden>This will remove the business from the list (the notes are kept as the reason).</span>
  91. </form>
  92. </div>
  93. </div>
  94. <% End If %>
  95. <div class="card shadow-sm mb-3">
  96. <div class="card-body">
  97. <h2 class="h5 mb-3">History <span class="text-muted fs-6">(<%= interactions.Count %>)</span></h2>
  98. <% If interactions.Count = 0 Then %>
  99. <p class="text-muted mb-0">No contact logged yet.</p>
  100. <% Else %>
  101. <ul class="list-unstyled mb-0">
  102. <% For ix = 0 To interactions.Count - 1
  103. Set it = interactions(ix) %>
  104. <li class="border-start border-3 ps-3 pb-3">
  105. <div class="d-flex flex-wrap gap-2 align-items-center">
  106. <strong><%= Date_Fmt(it("contacted_at")) %></strong>
  107. <span class="badge text-bg-primary"><%= H(Businesses_Label(Businesses_Methods(), it("method"))) %></span>
  108. <% If Len(it("outcome") & "") > 0 Then %><span class="badge text-bg-light border"><%= H(Businesses_Label(Businesses_Outcomes(), it("outcome"))) %></span><% End If %>
  109. <% If Not IsNull(it("follow_up_date")) Then %><span class="small text-muted"><i class="bi bi-arrow-return-right"></i> again on <%= Date_Fmt(it("follow_up_date")) %></span><% End If %>
  110. </div>
  111. <% If Len(it("notes") & "") > 0 Then %><div class="mt-1"><%= Html_Nl2Br(it("notes")) %></div><% End If %>
  112. </li>
  113. <% Next %>
  114. </ul>
  115. <% End If %>
  116. </div>
  117. </div>
  118. </div>
  119. <!-- RIGHT: details -->
  120. <div class="col-lg-5">
  121. <div class="card shadow-sm mb-3">
  122. <div class="card-body">
  123. <h2 class="h5 mb-3">Details</h2>
  124. <div class="mb-3 small">
  125. <% If Len(b("phone") & "") > 0 Then %><div><i class="bi bi-telephone"></i> <a href="tel:<%= H(b("phone")) %>"><%= H(b("phone")) %></a></div><% End If %>
  126. <% If Len(b("email") & "") > 0 Then %><div><i class="bi bi-envelope"></i> <a href="mailto:<%= H(b("email")) %>"><%= H(b("email")) %></a></div><% End If %>
  127. <% If Len(b("website") & "") > 0 Then %><div><i class="bi bi-globe"></i> <a href="<% If LCase(Left(b("website"), 4)) = "http" Then Response.Write H(b("website")) Else Response.Write "https://" & H(b("website")) %>" target="_blank" rel="noopener noreferrer"><%= H(b("website")) %></a></div><% End If %>
  128. <% If Len(b("address1") & "") > 0 Or Len(b("city") & "") > 0 Then %><div><i class="bi bi-geo-alt"></i> <%= H(b("address1")) %><% If Len(b("address1") & "") > 0 And Len(b("city") & "") > 0 Then Response.Write ", " %><%= H(b("city")) %><% If Len(b("state") & "") > 0 Then Response.Write ", " & H(b("state")) %>&nbsp;<%= H(b("zip")) %></div><% End If %>
  129. </div>
  130. <% If Not dup Is Nothing Then %>
  131. <div class="alert alert-warning small">
  132. <i class="bi bi-exclamation-triangle"></i>
  133. Nothing was saved yet. The <%= dup("matched") %> you entered is already used by
  134. <a href="/businesses/<%= dup("id") %>" target="_blank" rel="noopener"><%= H(dup("name")) %></a>.
  135. Fix it, or press <strong>Save anyway</strong> to keep both.
  136. </div>
  137. <% End If %>
  138. <form method="post" action="/businesses/<%= bid %>/update">
  139. <input type="hidden" name="csrf" value="<%= H(csrf) %>" />
  140. <% If Not dup Is Nothing Then %><input type="hidden" name="allow_duplicate" value="1" /><% End If %>
  141. <div class="mb-2">
  142. <label class="form-label small mb-1" for="f_name">Business name</label>
  143. <input type="text" class="form-control form-control-sm" id="f_name" name="name" value="<%= H(fv("name")) %>" maxlength="255" required />
  144. </div>
  145. <div class="mb-2">
  146. <label class="form-label small mb-1" for="f_contact">Contact</label>
  147. <input type="text" class="form-control form-control-sm" id="f_contact" name="contact_name" value="<%= H(fv("contact_name")) %>" maxlength="150" />
  148. </div>
  149. <div class="row g-2 mb-2">
  150. <div class="col-6">
  151. <label class="form-label small mb-1" for="f_phone">Phone</label>
  152. <input type="text" class="form-control form-control-sm" id="f_phone" name="phone" value="<%= H(fv("phone")) %>" maxlength="40" />
  153. </div>
  154. <div class="col-6">
  155. <label class="form-label small mb-1" for="f_email">Email</label>
  156. <input type="text" class="form-control form-control-sm" id="f_email" name="email" value="<%= H(fv("email")) %>" maxlength="255" />
  157. </div>
  158. </div>
  159. <div class="mb-2">
  160. <label class="form-label small mb-1" for="f_web">Website</label>
  161. <input type="text" class="form-control form-control-sm" id="f_web" name="website" value="<%= H(fv("website")) %>" maxlength="255" />
  162. </div>
  163. <div class="mb-2">
  164. <label class="form-label small mb-1" for="f_addr">Address</label>
  165. <input type="text" class="form-control form-control-sm" id="f_addr" name="address1" value="<%= H(fv("address1")) %>" maxlength="255" />
  166. </div>
  167. <div class="row g-2 mb-2">
  168. <div class="col-5"><label class="form-label small mb-1" for="f_city">City</label><input type="text" class="form-control form-control-sm" id="f_city" name="city" value="<%= H(fv("city")) %>" maxlength="100" /></div>
  169. <div class="col-3"><label class="form-label small mb-1" for="f_state">State</label><input type="text" class="form-control form-control-sm" id="f_state" name="state" value="<%= H(fv("state")) %>" maxlength="50" /></div>
  170. <div class="col-4"><label class="form-label small mb-1" for="f_zip">Zip</label><input type="text" class="form-control form-control-sm" id="f_zip" name="zip" value="<%= H(fv("zip")) %>" maxlength="20" /></div>
  171. </div>
  172. <div class="row g-2 mb-2">
  173. <div class="col-6">
  174. <label class="form-label small mb-1" for="f_ind">Industry</label>
  175. <select class="form-select form-select-sm" id="f_ind" name="industry_id">
  176. <option value="">(none)</option>
  177. <% For Each indKey2 In industries.Keys %>
  178. <option value="<%= indKey2 %>"<% If CStr(fv("industry_id") & "") = indKey2 Then Response.Write " selected" %>><%= H(industries(indKey2)) %></option>
  179. <% Next %>
  180. </select>
  181. </div>
  182. <div class="col-6">
  183. <label class="form-label small mb-1" for="f_indnew">&hellip;or add new</label>
  184. <input type="text" class="form-control form-control-sm" id="f_indnew" name="industry_new" maxlength="100" value="<% If fv.Exists("_industry_new") Then Response.Write H(fv("_industry_new")) %>" />
  185. </div>
  186. </div>
  187. <div class="row g-2 mb-2 align-items-end">
  188. <div class="col-6">
  189. <div class="form-check">
  190. <input class="form-check-input" type="checkbox" id="f_cust" name="is_customer" value="1"<% If fv("is_customer") & "" = "1" Then Response.Write " checked" %> />
  191. <label class="form-check-label small" for="f_cust">Previous customer</label>
  192. </div>
  193. </div>
  194. <div class="col-6">
  195. <label class="form-label small mb-1" for="f_first">First order</label>
  196. <input type="date" class="form-control form-control-sm" id="f_first" name="first_order_date" value="<%= Date_Iso(fv("first_order_date")) %>" />
  197. </div>
  198. </div>
  199. <div class="mb-3">
  200. <label class="form-label small mb-1" for="f_notes">Notes <span class="text-muted">(other people, anything else)</span></label>
  201. <textarea class="form-control form-control-sm" id="f_notes" name="notes" rows="4" maxlength="10000"><%= H(fv("notes")) %></textarea>
  202. </div>
  203. <button type="submit" class="btn <% If dup Is Nothing Then Response.Write "btn-outline-primary" Else Response.Write "btn-warning" %> btn-sm"><% If dup Is Nothing Then Response.Write "Save details" Else Response.Write "Save anyway" %></button>
  204. </form>
  205. </div>
  206. </div>
  207. <% If Not isRemoved Then %>
  208. <div class="card border-danger-subtle shadow-sm mb-3">
  209. <div class="card-body">
  210. <h2 class="h6 text-danger">Remove from list</h2>
  211. <form method="post" action="/businesses/<%= bid %>/remove" class="d-flex gap-2">
  212. <input type="hidden" name="csrf" value="<%= H(csrf) %>" />
  213. <input type="text" class="form-control form-control-sm" name="reason" placeholder="Reason (optional)" maxlength="255" />
  214. <button type="submit" class="btn btn-outline-danger btn-sm text-nowrap">Remove</button>
  215. </form>
  216. <div class="form-text">Removed businesses are hidden from the list and won't be re-added by an import. You can restore them.</div>
  217. </div>
  218. </div>
  219. <% End If %>
  220. <p class="text-muted small">
  221. Added <%= Date_Fmt(b("created_at")) %><% If Not IsNull(b("import_batch_id")) Then Response.Write " &middot; import batch #" & b("import_batch_id") %>
  222. <% If Len(b("source") & "") > 0 Then %>&middot; <%= H(b("source")) %><% End If %>
  223. </p>
  224. </div>
  225. </div>
  226. <script>
  227. (function () {
  228. var fu = document.getElementById('follow_up_date');
  229. document.querySelectorAll('[data-days]').forEach(function (btn) {
  230. btn.addEventListener('click', function () {
  231. var n = parseInt(btn.getAttribute('data-days'), 10);
  232. if (!fu) return;
  233. if (n === 0) { fu.value = ''; return; }
  234. var d = new Date(); d.setDate(d.getDate() + n);
  235. var m = ('0' + (d.getMonth() + 1)).slice(-2), day = ('0' + d.getDate()).slice(-2);
  236. fu.value = d.getFullYear() + '-' + m + '-' + day;
  237. });
  238. });
  239. var oc = document.getElementById('outcome'), hint = document.getElementById('removeHint');
  240. if (oc && hint) oc.addEventListener('change', function () { hint.hidden = (oc.value !== 'remove'); });
  241. })();
  242. </script>

Powered by TurnKey Linux.