global-list.vue 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268
  1. <template>
  2. <cwg-page-wrapper>
  3. <view class="bank-transaction-page">
  4. <view class="filters-container" :style="{ top: statusBarHeight + 53 + 'px' }">
  5. <view class="filter-item">
  6. <text class="filter-label">{{ t('global.p25') }}</text>
  7. <cwg-filter-select v-model="payoutCurrency" :options="currencyList" />
  8. </view>
  9. <view class="filter-item">
  10. <text class="filter-label">{{ t('card.Form.f45') }}</text>
  11. <cwg-filter-select v-model="statusFilterIndex" :options="statusOptions" />
  12. </view>
  13. <view class="filter-item">
  14. <text class="filter-label">{{ t('card.Form.f43') }}</text>
  15. <cwg-filter-picker v-model="dateFilter"></cwg-filter-picker>
  16. </view>
  17. <view class="reset-btn" @click="resetFilters">
  18. <uni-icons type="loop" size="16" color="#2563eb" />
  19. </view>
  20. </view>
  21. <view class="content">
  22. <GlobalList ref="globalListRef" :cardNumber="cardNumber" :payoutCurrency="payoutCurrency"
  23. :statusIndex="statusFilterIndex" :dateFilter="dateFilter" />
  24. </view>
  25. </view>
  26. </cwg-page-wrapper>
  27. </template>
  28. <script setup lang="ts">
  29. import { ref, computed, watch } from 'vue';
  30. import { onLoad } from '@dcloudio/uni-app';
  31. import { useI18n } from 'vue-i18n';
  32. import useGlobalStore from '@/stores/use-global-store';
  33. import GlobalList from './components/GlobalList.vue';
  34. import { globalStatusText1 } from '@/utils/dataMap';
  35. import useCardStore from "@/stores/use-card-store";
  36. const cardStore = useCardStore();
  37. const globalStore = useGlobalStore()
  38. const statusBarHeight = computed(() => globalStore.statusBarHeight);
  39. const { t } = useI18n();
  40. const cardNumber = ref('');
  41. onLoad((options) => {
  42. cardNumber.value = options.cardNumber || '';
  43. });
  44. const statusOptions = computed(() => {
  45. return globalStatusText1
  46. });
  47. const currencyList = computed(() => {
  48. const res = cardStore.currencyList.map(item => { return { label: item.payoutCurrency, value: item.payoutCurrency } });
  49. return res;
  50. });
  51. const payoutCurrency = ref(-1);
  52. const statusFilterIndex = ref(-1);
  53. const dateFilter = ref([]);
  54. const resetFilters = () => {
  55. payoutCurrency.value = -1;
  56. statusFilterIndex.value = -1;
  57. dateFilter.value = [];
  58. };
  59. </script>
  60. <style scoped lang="scss">
  61. @import "@/uni.scss";
  62. .page-wrapper {
  63. padding: 0;
  64. border: 0;
  65. }
  66. .bank-transaction-page {
  67. // background-color: #f9fafb;
  68. }
  69. .wallet-header {
  70. background: linear-gradient(135deg, #2563eb 0%, #60a5fa 100%);
  71. }
  72. /* Header */
  73. .header {
  74. background: linear-gradient(135deg, #2563eb 0%, #60a5fa 100%);
  75. padding: px2rpx(16);
  76. padding-bottom: px2rpx(20);
  77. }
  78. .header-content {
  79. display: flex;
  80. flex-direction: column;
  81. gap: px2rpx(16);
  82. }
  83. .header-title {
  84. display: flex;
  85. align-items: center;
  86. gap: px2rpx(8);
  87. }
  88. .title-text {
  89. color: #ffffff;
  90. font-size: px2rpx(20);
  91. }
  92. .stats-container {
  93. display: flex;
  94. gap: px2rpx(12);
  95. }
  96. .stat-card {
  97. flex: 1;
  98. background-color: rgba(255, 255, 255, 0.15);
  99. backdrop-filter: blur(px2rpx(10));
  100. border-radius: px2rpx(12);
  101. padding: px2rpx(12);
  102. }
  103. .stat-header {
  104. display: flex;
  105. align-items: center;
  106. gap: px2rpx(6);
  107. margin-bottom: px2rpx(8);
  108. }
  109. .icons {
  110. width: px2rpx(20);
  111. height: px2rpx(20);
  112. }
  113. .stat-label {
  114. font-size: px2rpx(12);
  115. color: rgba(255, 255, 255, 0.9);
  116. }
  117. .stat-value {
  118. font-size: px2rpx(20);
  119. color: #ffffff;
  120. display: block;
  121. margin-bottom: px2rpx(4);
  122. }
  123. .stat-count {
  124. font-size: px2rpx(11);
  125. color: rgba(255, 255, 255, 0.8);
  126. }
  127. /* Tabs */
  128. .tabs-container {
  129. background-color: #ffffff;
  130. display: flex;
  131. border-bottom: 1px solid #e5e7eb;
  132. position: sticky;
  133. top: 0;
  134. z-index: 10;
  135. }
  136. .tab-item {
  137. flex: 1;
  138. display: flex;
  139. align-items: center;
  140. justify-content: center;
  141. gap: px2rpx(6);
  142. padding: px2rpx(16);
  143. position: relative;
  144. transition: all 0.3s;
  145. }
  146. .tab-text {
  147. font-size: px2rpx(15);
  148. color: #9ca3af;
  149. transition: color 0.3s;
  150. }
  151. .tab-text-active {
  152. color: #2563eb;
  153. }
  154. .tab-indicator {
  155. position: absolute;
  156. bottom: 0;
  157. left: 0;
  158. right: 0;
  159. height: px2rpx(3);
  160. background-color: #2563eb;
  161. border-radius: px2rpx(3) px2rpx(3) 0 0;
  162. }
  163. /* Content */
  164. .content {
  165. padding: 0;
  166. }
  167. .filters-container {
  168. display: flex;
  169. align-items: center;
  170. gap: px2rpx(8);
  171. padding: px2rpx(12) px2rpx(16);
  172. background-color: #ffffff;
  173. position: sticky;
  174. top: 0;
  175. z-index: 10;
  176. // overflow-x: auto;
  177. -webkit-overflow-scrolling: touch;
  178. }
  179. .filter-item {
  180. display: flex;
  181. align-items: center;
  182. gap: px2rpx(4);
  183. flex-shrink: 0;
  184. min-width: 0;
  185. }
  186. .filter-label {
  187. font-size: px2rpx(12);
  188. color: #6b7280;
  189. white-space: nowrap;
  190. flex-shrink: 0;
  191. }
  192. .filter-picker {
  193. background-color: #ffffff;
  194. border: 1px solid #e5e7eb;
  195. border-radius: px2rpx(8);
  196. padding: px2rpx(6) px2rpx(8);
  197. display: flex;
  198. align-items: center;
  199. min-width: px2rpx(60);
  200. max-width: px2rpx(120);
  201. flex-shrink: 1;
  202. }
  203. .picker-value {
  204. display: flex;
  205. align-items: center;
  206. gap: px2rpx(4);
  207. width: 100%;
  208. min-width: 0;
  209. }
  210. .picker-text {
  211. flex: 1;
  212. min-width: 0;
  213. font-size: px2rpx(12);
  214. color: #111827;
  215. overflow: hidden;
  216. text-overflow: ellipsis;
  217. white-space: nowrap;
  218. }
  219. .picker-icon {
  220. flex-shrink: 0;
  221. width: px2rpx(14);
  222. height: px2rpx(14);
  223. }
  224. .reset-btn {
  225. background-color: #ffffff;
  226. border: 1px solid #e5e7eb;
  227. border-radius: px2rpx(8);
  228. padding: px2rpx(6) px2rpx(10);
  229. display: flex;
  230. align-items: center;
  231. justify-content: center;
  232. flex-shrink: 0;
  233. min-width: px2rpx(36);
  234. }
  235. </style>