ShiftSalesReport.razor 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447
  1. @page "/report/shiftSalesReport"
  2. @attribute [ReuseTabsPage(Title = "班次销售报表")]
  3. <style>
  4. .daily-report-container {
  5. padding: 16px;
  6. background-color: #f5f7fa;
  7. min-height: 100vh;
  8. box-sizing: border-box;
  9. overflow: hidden;
  10. }
  11. .filter-section {
  12. margin-bottom: 16px;
  13. padding: 16px !important;
  14. background: white;
  15. border: 1px solid #ebeef5;
  16. border-radius: 4px;
  17. }
  18. .filter-content .filter-row {
  19. display: flex;
  20. align-items: center;
  21. gap: 16px;
  22. flex-wrap: wrap;
  23. }
  24. .filter-content .filter-row .filter-item {
  25. display: flex;
  26. align-items: center;
  27. }
  28. .filter-content .filter-row .filter-item .filter-label {
  29. margin-right: 8px;
  30. font-size: 14px;
  31. color: #606266;
  32. min-width: 32px;
  33. }
  34. .filter-content .filter-row .filter-actions {
  35. display: flex;
  36. gap: 8px;
  37. margin-left: auto;
  38. }
  39. .report-section {
  40. margin-bottom: 16px;
  41. padding: 16px;
  42. background: white;
  43. border: 1px solid #ebeef5;
  44. border-radius: 4px;
  45. }
  46. .section-header {
  47. margin-bottom: 16px;
  48. padding: 0 16px;
  49. }
  50. .section-header h3 {
  51. color: #303133;
  52. font-size: 16px;
  53. border-left: 4px solid #1890ff;
  54. padding-left: 10px;
  55. margin: 0;
  56. }
  57. .summary-section {
  58. padding: 16px;
  59. }
  60. .summary-section h3 {
  61. color: #303133;
  62. font-size: 16px;
  63. margin-bottom: 16px;
  64. border-left: 4px solid #1890ff;
  65. padding-left: 10px;
  66. }
  67. .summary-content {
  68. display: flex;
  69. justify-content: space-around;
  70. }
  71. .summary-item {
  72. display: flex;
  73. flex-direction: column;
  74. align-items: center;
  75. }
  76. .summary-value {
  77. font-size: 24px;
  78. font-weight: 600;
  79. color: #1890ff;
  80. margin-bottom: 8px;
  81. }
  82. .summary-label {
  83. font-size: 14px;
  84. color: #909399;
  85. }
  86. .table-container {
  87. padding: 0 16px 16px;
  88. }
  89. /* Div表格样式 - 复杂表头 */
  90. .div-table {
  91. display: flex;
  92. flex-direction: column;
  93. border: 1px solid #ebeef5;
  94. border-radius: 4px;
  95. overflow: hidden;
  96. font-size: 14px;
  97. }
  98. /* 第一行表头(合并单元格) */
  99. .div-table-header-1 {
  100. display: flex;
  101. background-color: #e6f7ff;
  102. font-weight: 600;
  103. color: #606266;
  104. border-bottom: 2px solid #91d5ff;
  105. }
  106. /* 第二行表头(子标题) */
  107. .div-table-header-2 {
  108. display: flex;
  109. background-color: #fafafa;
  110. font-weight: 600;
  111. color: #606266;
  112. border-bottom: 1px solid #ebeef5;
  113. }
  114. .div-table-row {
  115. display: flex;
  116. border-bottom: 1px solid #ebeef5;
  117. }
  118. .div-table-row:last-child {
  119. border-bottom: none;
  120. }
  121. .div-table-row.total-row {
  122. font-weight: 600;
  123. background-color: #f0f9ff;
  124. }
  125. .div-table-row:nth-child(even) {
  126. background-color: #fafafa;
  127. }
  128. .div-table-cell {
  129. padding: 12px 8px;
  130. text-align: center;
  131. overflow: hidden;
  132. text-overflow: ellipsis;
  133. white-space: nowrap;
  134. }
  135. .cell-left-align {
  136. text-align: left !important;
  137. justify-content: flex-start;
  138. }
  139. .cell-right-align {
  140. text-align: right !important;
  141. justify-content: flex-end;
  142. }
  143. .highlight-cell {
  144. color: #1890ff !important;
  145. font-weight: 500;
  146. }
  147. /* 列组标题样式 */
  148. .column-group-title {
  149. display: flex;
  150. align-items: center;
  151. justify-content: center;
  152. border-left: 1px solid #e8e8e8;
  153. }
  154. .column-group-title:first-child {
  155. border-left: none;
  156. }
  157. /* 子标题单元格 */
  158. .sub-header-cell {
  159. display: flex;
  160. align-items: center;
  161. justify-content: center;
  162. border-left: 1px solid #e8e8e8;
  163. }
  164. .sub-header-cell:first-child {
  165. border-left: none;
  166. }
  167. /* 数据单元格 */
  168. .data-cell {
  169. display: flex;
  170. align-items: center;
  171. justify-content: center;
  172. border-left: 1px solid #ebeef5;
  173. }
  174. .data-cell:first-child {
  175. border-left: none;
  176. }
  177. .data-cell-group {
  178. display: flex;
  179. flex: 1;
  180. }
  181. /* 响应式设计 */
  182. @@media (max-width: 768px) {
  183. .daily-report-container {
  184. padding: 12px;
  185. }
  186. .filter-section {
  187. padding: 12px !important;
  188. }
  189. .filter-content .filter-row {
  190. flex-direction: column;
  191. align-items: flex-start;
  192. }
  193. .filter-content .filter-row .filter-actions {
  194. margin-left: 0;
  195. width: 100%;
  196. display: flex;
  197. justify-content: center;
  198. margin-top: 8px;
  199. }
  200. .summary-content {
  201. flex-wrap: wrap;
  202. }
  203. .summary-item {
  204. width: 50%;
  205. margin-bottom: 16px;
  206. }
  207. .div-table {
  208. overflow-x: auto;
  209. }
  210. .div-table-header-1,
  211. .div-table-header-2,
  212. .div-table-row {
  213. min-width: 1200px;
  214. }
  215. .div-table-cell {
  216. padding: 8px 4px;
  217. font-size: 12px;
  218. }
  219. }
  220. </style>
  221. <div class="daily-report-container">
  222. <!-- 筛选条件 -->
  223. <div class="filter-section">
  224. <div class="filter-content">
  225. <div class="filter-row">
  226. <div class="filter-item">
  227. <span class="filter-label">日期</span>
  228. <DatePicker @bind-Value="Filter.StartDate"
  229. Format="yyyy-MM-dd"
  230. Style="width: 150px" />
  231. </div>
  232. <div class="filter-item">
  233. <span class="filter-label">设备编号</span>
  234. <Input @bind-Value="Filter.PlateNumber"
  235. Placeholder="请输入设备编号"
  236. Style="width: 150px" />
  237. </div>
  238. <!-- 班次 -->
  239. <div class="form-item">
  240. <span class="form-label">班次</span>
  241. <Select TItemValue="string" TItem="string"
  242. DataSource="@ShiftName"
  243. @bind-Value="@Filter.Shift"
  244. Style="width: 120px"
  245. Placeholder="请选择"
  246. AllowClear />
  247. </div>
  248. <div class="filter-actions">
  249. <Button Icon="search" OnClick="HandleQuery">查询</Button>
  250. <Button Icon="reload" OnClick="HandleReset">重置</Button>
  251. </div>
  252. </div>
  253. </div>
  254. </div>
  255. <!-- 统计摘要 -->
  256. <div class="report-section">
  257. <div class="summary-section">
  258. <h3>统计摘要</h3>
  259. <div class="summary-content">
  260. <div class="summary-item">
  261. <div class="summary-value">@Summary.TotalSalesQuantity</div>
  262. <div class="summary-label">总销售数量</div>
  263. </div>
  264. <div class="summary-item">
  265. <div class="summary-value">@FormatCurrency(Summary.TotalReceivable)</div>
  266. <div class="summary-label">总应收金额</div>
  267. </div>
  268. <div class="summary-item">
  269. <div class="summary-value">@FormatCurrency(Summary.TotalActual)</div>
  270. <div class="summary-label">总实收金额</div>
  271. </div>
  272. </div>
  273. </div>
  274. </div>
  275. <!-- 营业收入 -->
  276. <div class="report-section">
  277. <div class="section-header">
  278. <h3>营业收入</h3>
  279. </div>
  280. <div class="table-container">
  281. <div class="div-table">
  282. <!-- 第一行表头(合并单元格) -->
  283. <div class="div-table-header-1">
  284. <div class="div-table-cell column-group-title" style="width: 11.11%;">项目</div>
  285. <div class="div-table-cell column-group-title" style="width: 33.33%;">
  286. 销售数量
  287. </div>
  288. <div class="div-table-cell column-group-title" style="width: 33.33%;">
  289. 应收金额
  290. </div>
  291. <div class="div-table-cell column-group-title" style="width: 22.23%;">
  292. 实收金额
  293. </div>
  294. </div>
  295. <!-- 第二行表头(子标题) -->
  296. <div class="div-table-header-2">
  297. <div class="div-table-cell sub-header-cell" style="width: 11.11%;"></div>
  298. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  299. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  300. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  301. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  302. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  303. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  304. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  305. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  306. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  307. </div>
  308. <!-- 表格数据行 -->
  309. @foreach (var item in OperatingIncome)
  310. {
  311. <div class="div-table-row @(item.Name == "油品合计" ? "total-row" : "")">
  312. <div class="div-table-cell cell-left-align" style="width: 11.11%;">@item.Name</div>
  313. <!-- 销售数量 -->
  314. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatNumber(item.MorningSalesQuantity)</div>
  315. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatNumber(item.EveningSalesQuantity)</div>
  316. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatNumber(item.TotalSalesQuantity)</div>
  317. <!-- 应收金额 -->
  318. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.MorningReceivable)</div>
  319. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.EveningReceivable)</div>
  320. <div class="div-table-cell cell-right-align highlight-cell" style="width: 11.11%;">@FormatCurrency(item.TotalReceivable)</div>
  321. <!-- 实收金额 -->
  322. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.MorningActual)</div>
  323. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.EveningActual)</div>
  324. <div class="div-table-cell cell-right-align highlight-cell" style="width: 11.11%;">@FormatCurrency(item.TotalActual)</div>
  325. </div>
  326. }
  327. </div>
  328. </div>
  329. </div>
  330. <!-- 收入类别 -->
  331. <div class="report-section">
  332. <div class="section-header">
  333. <h3>收入类别</h3>
  334. </div>
  335. <div class="table-container">
  336. <div class="div-table">
  337. <!-- 第一行表头(合并单元格) -->
  338. <div class="div-table-header-1">
  339. <div class="div-table-cell column-group-title" style="width: 11.11%;">项目</div>
  340. <div class="div-table-cell column-group-title" style="width: 33.33%;">
  341. 收入笔数
  342. </div>
  343. <div class="div-table-cell column-group-title" style="width: 33.33%;">
  344. 应收金额
  345. </div>
  346. <div class="div-table-cell column-group-title" style="width: 22.23%;">
  347. 实收金额
  348. </div>
  349. </div>
  350. <!-- 第二行表头(子标题) -->
  351. <div class="div-table-header-2">
  352. <div class="div-table-cell sub-header-cell" style="width: 11.11%;"></div>
  353. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  354. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  355. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  356. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  357. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  358. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  359. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">早班</div>
  360. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">晚班</div>
  361. <div class="div-table-cell sub-header-cell" style="width: 11.11%;">小计</div>
  362. </div>
  363. <!-- 表格数据行 -->
  364. @foreach (var item in IncomeCategory)
  365. {
  366. <div class="div-table-row @(item.Name == "合计" ? "total-row" : "")">
  367. <div class="div-table-cell cell-left-align" style="width: 11.11%;">@item.Name</div>
  368. <!-- 收入笔数 -->
  369. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@item.MorningCount</div>
  370. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@item.EveningCount</div>
  371. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@item.TotalCount</div>
  372. <!-- 应收金额 -->
  373. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.MorningReceivable)</div>
  374. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.EveningReceivable)</div>
  375. <div class="div-table-cell cell-right-align highlight-cell" style="width: 11.11%;">@FormatCurrency(item.TotalReceivable)</div>
  376. <!-- 实收金额 -->
  377. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.MorningActual)</div>
  378. <div class="div-table-cell cell-right-align" style="width: 11.11%;">@FormatCurrency(item.EveningActual)</div>
  379. <div class="div-table-cell cell-right-align highlight-cell" style="width: 11.11%;">@FormatCurrency(item.TotalActual)</div>
  380. </div>
  381. }
  382. </div>
  383. </div>
  384. </div>
  385. </div>