feat(convert): show history and let customers edit pending requests
Desktop history sits beside the form. Pending requests can be updated or deleted, and the shared wallet surface drops its extra border and padding. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -62,3 +62,7 @@
|
||||
- 2026-11-02 | سه زبانه تبدیل از اول | همان `CopperConvertCalculator.vue` | زبانه ۱.۵ و ۲.۵ دیگر پشت `remainderAmount > 0` نیستند؛ زیر زبانه مقدار، قبل از نتیجه
|
||||
- 2026-11-02 | زبانه سیم مکمل | `useCopperConvertPage.ts` | بودجه = ارزش مقدار انتخابشده؛ نصف به ۱.۵ و بقیه به ۲.۵؛ جابهجایی یکی دیگری را پر میکند
|
||||
- 2026-11-01 | تاریخچه برداشت کیف پول | `wallet/mobile/MobileWalletView.vue` + `desktop/DesktopWalletView.vue` + `useWalletPageData.ts` | `walletWithdrawItems` از قبل لود میشد؛ زیر راهنمای برداشت و زیر حسابهای دسکتاپ نشان داده میشود
|
||||
- 2026-11-03 | تاریخچه تبدیل کاربر | `convert/components/CopperConvertHistory.vue` + `useCopperConvertPage.ts` + سرور `Customer/CopperConvertRequestController@index` | GET `/customer/copper-convert-request` فقط ردیفهای همان مشتری؛ زیر فرم موبایل و دسکتاپ
|
||||
- 2026-11-03 | ویرایش/حذف تبدیل در انتظار | همان تاریخچه + `CopperConvertRequestService::update/remove` | فقط status=pending؛ ویرایش فرم را با همان حلقهها پر میکند و PUT میزند
|
||||
- 2026-11-03 | چیدمان دسکتاپ تبدیل | `convert/desktop/DesktopConvertView.vue` | مثل کیف پول: `dwallet-grid`؛ فرم راست، تاریخچه چپ با `variant=side`
|
||||
- 2026-11-03 | مداد ویرایش تبدیل | `convert/components/CopperConvertHistory.vue` | فقط pending؛ آیکون `vuesax-linear:edit` کنار وضعیت، همان `beginEdit`
|
||||
|
||||
@@ -1,6 +1,18 @@
|
||||
import useAxios from '@/utils/useAxios'
|
||||
import type { CopperConvertSource } from '@/utils/copperWireConvert'
|
||||
|
||||
export interface CopperConvertHistoryRow {
|
||||
id: number
|
||||
status: string
|
||||
source: string
|
||||
asset_unit: string
|
||||
consumed_amount: number
|
||||
leftover_amount: number
|
||||
wire15_rings: number
|
||||
wire25_rings: number
|
||||
created_at?: string
|
||||
}
|
||||
|
||||
export function createCopperConvertRequest(payload: {
|
||||
source: CopperConvertSource
|
||||
rings15: number
|
||||
@@ -8,3 +20,22 @@ export function createCopperConvertRequest(payload: {
|
||||
}) {
|
||||
return useAxios.post('/customer/copper-convert-request', payload)
|
||||
}
|
||||
|
||||
export function getCopperConvertRequests() {
|
||||
return useAxios.get<CopperConvertHistoryRow[]>('/customer/copper-convert-request')
|
||||
}
|
||||
|
||||
export function updateCopperConvertRequest(
|
||||
id: number,
|
||||
payload: {
|
||||
source: CopperConvertSource
|
||||
rings15: number
|
||||
rings25: number
|
||||
},
|
||||
) {
|
||||
return useAxios.put(`/customer/copper-convert-request/${id}`, payload)
|
||||
}
|
||||
|
||||
export function deleteCopperConvertRequest(id: number) {
|
||||
return useAxios.delete(`/customer/copper-convert-request/${id}`)
|
||||
}
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
<template>
|
||||
<div class="copper-convert" dir="rtl">
|
||||
<p class="copper-convert__lead">
|
||||
مقدار کاتد، مفتول یا شمش از دارایی شما خوانده میشود. با زبانه از صفر تا همان موجودی انتخاب کنید. معادل مفتول و حلقه سیم ۱.۵ و ۲.۵ با قیمت روز حساب میشود.
|
||||
</p>
|
||||
<div class="copper-convert" data-convert-form dir="rtl">
|
||||
|
||||
<a-spin :spinning="loading">
|
||||
<section class="copper-convert__panel" aria-label="قیمتهای مبنا">
|
||||
<p v-if="!result && amountAttempted && !loading" class="copper-convert__warn">
|
||||
مقدار معتبر وارد کنید و از فعال بودن قیمت کاتد/مفتول در سامانه مطمئن شوید.
|
||||
</p>
|
||||
<div class="copper-convert__panel-head">
|
||||
<span class="copper-convert__panel-kicker">قیمت لحظهای</span>
|
||||
<span class="copper-convert__panel-title">مبنای محاسبه</span>
|
||||
@@ -186,23 +186,28 @@
|
||||
<p class="copper-convert__asset-hint">
|
||||
از مقدار انتخابشده، <span class="copper-convert__measure"><bdi>{{ assetUnit }}</bdi><bdi>{{ formatAssetAmount(leftoverAmount) }}</bdi></span> به حلقهٔ کامل نمیرسد و در دارایی میماند. باقی دارایی که روی زبانه انتخاب نشده هم دستنخورده میماند.
|
||||
</p>
|
||||
<BasicButton
|
||||
type="primary"
|
||||
class="!w-full"
|
||||
:loading="submitting"
|
||||
:disabledB="wire15Rings + wire25Rings < 1"
|
||||
@click="submitRequest"
|
||||
>
|
||||
ثبت درخواست تبدیل
|
||||
</BasicButton>
|
||||
<p v-if="editingId" class="copper-convert__asset-hint">
|
||||
در حال ویرایش درخواست در انتظار تایید. ذخیره، همان درخواست را بهروز میکند.
|
||||
</p>
|
||||
<div :class="editingId ? 'grid grid-cols-2 gap-2' : ''">
|
||||
<BasicButton
|
||||
type="primary"
|
||||
class="!w-full"
|
||||
html-type="button"
|
||||
:loading="submitting"
|
||||
:disabledB="wire15Rings + wire25Rings < 1"
|
||||
@click="submitRequest"
|
||||
>
|
||||
{{ editingId ? 'ذخیره ویرایش' : 'ثبت درخواست تبدیل' }}
|
||||
</BasicButton>
|
||||
<BasicButton v-if="editingId" class="!w-full" html-type="button" :disabledB="submitting" @click="cancelEdit">
|
||||
انصراف
|
||||
</BasicButton>
|
||||
</div>
|
||||
<p class="copper-convert__asset-hint">
|
||||
درخواست برای ادمین میرود. بعد از تأیید، همان مقدار دارایی فروخته و حلقههای انتخابشده خریده میشود.
|
||||
</p>
|
||||
</section>
|
||||
|
||||
<p v-if="!result && amountAttempted && !loading" class="copper-convert__warn">
|
||||
مقدار معتبر وارد کنید و از فعال بودن قیمت کاتد/مفتول در سامانه مطمئن شوید.
|
||||
</p>
|
||||
</a-spin>
|
||||
</div>
|
||||
</template>
|
||||
@@ -227,6 +232,8 @@ const {
|
||||
leftoverAmount,
|
||||
submitting,
|
||||
submitRequest,
|
||||
editingId,
|
||||
cancelEdit,
|
||||
result,
|
||||
priceRows,
|
||||
} = useCopperConvertPageContext()
|
||||
|
||||
@@ -0,0 +1,126 @@
|
||||
<template>
|
||||
<section
|
||||
:class="side
|
||||
? 'flex min-h-0 min-w-0 flex-1 flex-col'
|
||||
: 'mt-3 flex flex-col gap-2 rounded-xl border border-gray-200 bg-white p-2.5'"
|
||||
aria-label="تاریخچه تبدیل"
|
||||
>
|
||||
<div :class="side ? 'dwallet-side__header' : ''">
|
||||
<div>
|
||||
<h2 :class="side ? 'dwallet-side__title' : 'm-0 text-sm font-bold text-slate-900'">تاریخچه تبدیل</h2>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div :class="side ? 'dwallet-side__scroll' : ''">
|
||||
<a-spin :spinning="historyLoading && !history.length">
|
||||
<div v-if="historyLoading && !history.length" class="min-h-16" />
|
||||
<p
|
||||
v-else-if="!history.length"
|
||||
class="m-0 rounded-lg bg-slate-50 px-3 py-4 text-center text-xs text-slate-500"
|
||||
>
|
||||
درخواست تبدیلی ثبت نشده است.
|
||||
</p>
|
||||
|
||||
<ul v-else class="m-0 flex list-none flex-col gap-2 p-0">
|
||||
<li
|
||||
v-for="item in history"
|
||||
:key="item.id"
|
||||
class="rounded-lg border p-2.5"
|
||||
:class="editingId === item.id ? 'border-amber-400' : 'border-gray-200'"
|
||||
>
|
||||
<div class="flex flex-wrap items-center justify-between gap-2">
|
||||
<span class="text-xs text-slate-500">{{ item.created_at ? toJalali(item.created_at) : '—' }}</span>
|
||||
<span class="inline-flex items-center gap-1 text-xs text-slate-600">
|
||||
<button
|
||||
v-if="item.status === 'pending'"
|
||||
type="button"
|
||||
class="inline-flex h-7 w-7 items-center justify-center rounded-md border border-gray-200 bg-white"
|
||||
aria-label="ویرایش درخواست"
|
||||
title="ویرایش"
|
||||
@click="beginEdit(item)"
|
||||
>
|
||||
<BasicIcon icon="vuesax-linear:edit" size="15" />
|
||||
</button>
|
||||
وضعیت
|
||||
<a-tag class="!m-0" :color="statusColor(item.status)">{{ statusLabel(item.status) }}</a-tag>
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div class="mt-2 grid grid-cols-2 gap-x-3 gap-y-1 text-xs text-slate-600">
|
||||
<span>دارایی: <b class="text-slate-900">{{ sourceLabel(item.source) }}</b></span>
|
||||
<span>
|
||||
مقدار:
|
||||
<b class="text-slate-900">
|
||||
<bdi>{{ item.asset_unit }}</bdi>
|
||||
<bdi> {{ formatAmount(item.consumed_amount) }}</bdi>
|
||||
</b>
|
||||
</span>
|
||||
<span>حلقه ۱.۵: <b class="text-slate-900">{{ item.wire15_rings }}</b></span>
|
||||
<span>حلقه ۲.۵: <b class="text-slate-900">{{ item.wire25_rings }}</b></span>
|
||||
<span v-if="Number(item.leftover_amount) > 0" class="col-span-2">
|
||||
مانده در دارایی:
|
||||
<b class="text-slate-900">
|
||||
<bdi>{{ item.asset_unit }}</bdi>
|
||||
<bdi> {{ formatAmount(item.leftover_amount) }}</bdi>
|
||||
</b>
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div v-if="item.status === 'pending'" class="mt-2 flex">
|
||||
<a-button
|
||||
size="small"
|
||||
danger
|
||||
:loading="deletingId === item.id"
|
||||
@click="deleteRequest(item.id)"
|
||||
>
|
||||
حذف
|
||||
</a-button>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</a-spin>
|
||||
</div>
|
||||
</section>
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
import { computed } from 'vue'
|
||||
import BasicIcon from '@/components/BasicPacks/BasicIcon.vue'
|
||||
import { toJalali } from '@/utils/useDateTime'
|
||||
import { useCopperConvertPageContext } from '../composables/useCopperConvertPage'
|
||||
|
||||
const props = withDefaults(defineProps<{ variant?: 'stack' | 'side' }>(), {
|
||||
variant: 'stack',
|
||||
})
|
||||
|
||||
const side = computed(() => props.variant === 'side')
|
||||
|
||||
const { history, historyLoading, editingId, beginEdit, deleteRequest, deletingId } =
|
||||
useCopperConvertPageContext()
|
||||
|
||||
function sourceLabel(source: string) {
|
||||
if (source === 'katod') return 'کاتد'
|
||||
if (source === 'maftoul') return 'مفتول'
|
||||
if (source === 'shamsh') return 'شمش'
|
||||
return source
|
||||
}
|
||||
|
||||
function statusLabel(status: string) {
|
||||
if (status === 'pending') return 'در انتظار تایید'
|
||||
if (status === 'approved') return 'تایید شد'
|
||||
if (status === 'rejected') return 'رد شد'
|
||||
return status
|
||||
}
|
||||
|
||||
function statusColor(status: string) {
|
||||
if (status === 'approved') return 'green'
|
||||
if (status === 'rejected') return 'red'
|
||||
return 'orange'
|
||||
}
|
||||
|
||||
function formatAmount(value: number) {
|
||||
const amount = Number(value)
|
||||
if (!Number.isFinite(amount)) return '—'
|
||||
return amount.toLocaleString('en-US', { maximumFractionDigits: 3 })
|
||||
}
|
||||
</script>
|
||||
@@ -1,6 +1,7 @@
|
||||
import {
|
||||
computed,
|
||||
inject,
|
||||
nextTick,
|
||||
onMounted,
|
||||
onUnmounted,
|
||||
provide,
|
||||
@@ -10,9 +11,15 @@ import {
|
||||
type InjectionKey,
|
||||
type Ref,
|
||||
} from 'vue'
|
||||
import { createCopperConvertRequest } from '@/api/copperConvert'
|
||||
import {
|
||||
createCopperConvertRequest,
|
||||
deleteCopperConvertRequest,
|
||||
getCopperConvertRequests,
|
||||
updateCopperConvertRequest,
|
||||
type CopperConvertHistoryRow,
|
||||
} from '@/api/copperConvert'
|
||||
import { getProducts } from '@/api/products'
|
||||
import { message } from 'ant-design-vue'
|
||||
import { message, Modal } from 'ant-design-vue'
|
||||
import { useWalletAssets } from '@/composables/useWalletAssets'
|
||||
import type { Product } from '@/models/products'
|
||||
import type { WalletInventoryCard } from '@/models/walletAssets'
|
||||
@@ -47,6 +54,13 @@ export interface CopperConvertPageContext {
|
||||
leftoverAmount: ComputedRef<number>
|
||||
submitting: Ref<boolean>
|
||||
submitRequest: () => Promise<void>
|
||||
editingId: Ref<number | null>
|
||||
beginEdit: (row: CopperConvertHistoryRow) => Promise<void>
|
||||
cancelEdit: () => void
|
||||
deleteRequest: (id: number) => void
|
||||
deletingId: Ref<number>
|
||||
history: Ref<CopperConvertHistoryRow[]>
|
||||
historyLoading: Ref<boolean>
|
||||
prices: ComputedRef<CopperConvertPrices>
|
||||
result: ComputedRef<CopperConvertResult | null>
|
||||
priceRows: ComputedRef<{ label: string; value: string; missing?: boolean }[]>
|
||||
@@ -142,6 +156,10 @@ export function useCopperConvertPage() {
|
||||
const wire25Rings = ref(0)
|
||||
const submitting = ref(false)
|
||||
const catalog = ref<Product[]>([])
|
||||
const history = ref<CopperConvertHistoryRow[]>([])
|
||||
const historyLoading = ref(true)
|
||||
const editingId = ref<number | null>(null)
|
||||
const deletingId = ref(0)
|
||||
const { assetsSummary, loadWalletAssets } = useWalletAssets()
|
||||
|
||||
const assetCards = computed(() => {
|
||||
@@ -310,24 +328,97 @@ export function useCopperConvertPage() {
|
||||
writeRings(rings15For(next25), next25)
|
||||
}, { flush: 'sync' })
|
||||
|
||||
function hasPendingRequest() {
|
||||
return history.value.some((row) => row.status === 'pending')
|
||||
}
|
||||
|
||||
async function beginEdit(row: CopperConvertHistoryRow) {
|
||||
if (row.status !== 'pending' || submitting.value) return
|
||||
editingId.value = row.id
|
||||
if (row.source === 'katod' || row.source === 'maftoul' || row.source === 'shamsh') {
|
||||
source.value = row.source
|
||||
}
|
||||
await nextTick()
|
||||
const rings15 = Math.max(0, Math.min(maxRings15.value, Math.floor(Number(row.wire15_rings) || 0)))
|
||||
const rings25 = Math.min(Math.floor(Number(row.wire25_rings) || 0), rings25For(rings15))
|
||||
writeRings(rings15, Math.max(0, rings25))
|
||||
const forms = document.querySelectorAll('[data-convert-form]')
|
||||
const visible = [...forms].find((node) => node instanceof HTMLElement && node.getClientRects().length > 0)
|
||||
visible?.scrollIntoView({ behavior: 'smooth', block: 'start' })
|
||||
}
|
||||
|
||||
function cancelEdit() {
|
||||
if (submitting.value) return
|
||||
editingId.value = null
|
||||
applyDefaultSplit()
|
||||
}
|
||||
|
||||
function deleteRequest(id: number) {
|
||||
if (deletingId.value || submitting.value) return
|
||||
const row = history.value.find((item) => item.id === id)
|
||||
if (!row || row.status !== 'pending') return
|
||||
Modal.confirm({
|
||||
title: 'حذف درخواست',
|
||||
content: 'این درخواست در انتظار تایید حذف شود؟',
|
||||
okText: 'حذف',
|
||||
cancelText: 'انصراف',
|
||||
okType: 'danger',
|
||||
async onOk() {
|
||||
deletingId.value = id
|
||||
try {
|
||||
await deleteCopperConvertRequest(id)
|
||||
if (editingId.value === id) editingId.value = null
|
||||
message.success('درخواست تبدیل حذف شد')
|
||||
await loadHistory()
|
||||
} finally {
|
||||
deletingId.value = 0
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
async function submitRequest() {
|
||||
if (submitting.value) return
|
||||
if (wire15Rings.value + wire25Rings.value < 1) return
|
||||
if (!editingId.value && hasPendingRequest()) {
|
||||
message.warning('یک درخواست در انتظار تایید دارید. همان را ویرایش یا حذف کنید.')
|
||||
return
|
||||
}
|
||||
submitting.value = true
|
||||
try {
|
||||
await createCopperConvertRequest({
|
||||
const payload = {
|
||||
source: source.value,
|
||||
rings15: wire15Rings.value,
|
||||
rings25: wire25Rings.value,
|
||||
})
|
||||
}
|
||||
if (editingId.value) {
|
||||
await updateCopperConvertRequest(editingId.value, payload)
|
||||
editingId.value = null
|
||||
message.success('درخواست تبدیل بهروز شد')
|
||||
} else {
|
||||
await createCopperConvertRequest(payload)
|
||||
message.success('درخواست تبدیل برای تأیید ادمین ثبت شد')
|
||||
}
|
||||
wire15Rings.value = 0
|
||||
wire25Rings.value = 0
|
||||
message.success('درخواست تبدیل برای تأیید ادمین ثبت شد')
|
||||
void loadHistory()
|
||||
} finally {
|
||||
submitting.value = false
|
||||
}
|
||||
}
|
||||
|
||||
async function loadHistory() {
|
||||
historyLoading.value = true
|
||||
try {
|
||||
const rows = await getCopperConvertRequests()
|
||||
history.value = Array.isArray(rows) ? rows : []
|
||||
} catch {
|
||||
// خطای شبکه را اینترسپتور نشان میدهد؛ لیست قبلی میماند
|
||||
} finally {
|
||||
historyLoading.value = false
|
||||
}
|
||||
}
|
||||
|
||||
const priceRows = computed(() => {
|
||||
const p = prices.value
|
||||
const row = (label: string, amount: number) => ({
|
||||
@@ -352,6 +443,7 @@ export function useCopperConvertPage() {
|
||||
getLastPrices(),
|
||||
getProducts(),
|
||||
loadWalletAssets(),
|
||||
loadHistory(),
|
||||
])
|
||||
catalog.value = Array.isArray(list) ? list : []
|
||||
} catch {
|
||||
@@ -385,6 +477,13 @@ export function useCopperConvertPage() {
|
||||
leftoverAmount,
|
||||
submitting,
|
||||
submitRequest,
|
||||
editingId,
|
||||
beginEdit,
|
||||
cancelEdit,
|
||||
deleteRequest,
|
||||
deletingId,
|
||||
history,
|
||||
historyLoading,
|
||||
prices,
|
||||
result,
|
||||
priceRows,
|
||||
|
||||
@@ -1,77 +1,43 @@
|
||||
<template>
|
||||
<div class="dconvert">
|
||||
<div class="dconvert__container">
|
||||
<header class="dconvert-topbar">
|
||||
<button type="button" class="dconvert-topbar__back" @click="router.back()">
|
||||
<BasicIcon icon="vuesax-linear:arrow-right-1" size="18" />
|
||||
<span>بازگشت</span>
|
||||
</button>
|
||||
<div class="dconvert-topbar__meta">
|
||||
<p class="dconvert-topbar__eyebrow">محصول</p>
|
||||
<h1 class="dconvert-topbar__title">تبدیل محصول</h1>
|
||||
</div>
|
||||
</header>
|
||||
<div class="dwallet" dir="rtl">
|
||||
<div class="dwallet__container">
|
||||
<DesktopPageTopbar
|
||||
eyebrow="محصول"
|
||||
title="تبدیل محصول"
|
||||
subtitle="تبدیل کاتد، مفتول یا شمش به حلقه سیم"
|
||||
show-back
|
||||
/>
|
||||
|
||||
<section class="dconvert-surface">
|
||||
<CopperConvertCalculator />
|
||||
</section>
|
||||
<div class="dwallet-grid dconvert-grid">
|
||||
<section class="dwallet-surface dwallet-form">
|
||||
<CopperConvertCalculator />
|
||||
</section>
|
||||
|
||||
<section class="dwallet-surface dwallet-side dconvert-side">
|
||||
<CopperConvertHistory variant="side" />
|
||||
</section>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
import BasicIcon from '@/components/BasicPacks/BasicIcon.vue'
|
||||
import router from '@/router'
|
||||
import DesktopPageTopbar from '@/layouts/components/DesktopPageTopbar.vue'
|
||||
import CopperConvertCalculator from '../components/CopperConvertCalculator.vue'
|
||||
import CopperConvertHistory from '../components/CopperConvertHistory.vue'
|
||||
</script>
|
||||
|
||||
<style scoped lang="less">
|
||||
.dconvert {
|
||||
.dconvert-grid {
|
||||
align-items: stretch;
|
||||
}
|
||||
|
||||
.dconvert-side {
|
||||
min-height: 100%;
|
||||
padding: 1.25rem 1.5rem 2rem;
|
||||
}
|
||||
|
||||
.dconvert__container {
|
||||
max-width: 720px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
.dconvert-topbar {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.75rem;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
|
||||
.dconvert-topbar__back {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 0.25rem;
|
||||
border: none;
|
||||
background: transparent;
|
||||
color: var(--colorPrimary, #2563eb);
|
||||
font-family: inherit;
|
||||
font-weight: 700;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.dconvert-topbar__eyebrow {
|
||||
margin: 0;
|
||||
font-size: 0.75rem;
|
||||
color: #64748b;
|
||||
}
|
||||
|
||||
.dconvert-topbar__title {
|
||||
margin: 0;
|
||||
font-size: 1.25rem;
|
||||
font-weight: 800;
|
||||
color: #0f172a;
|
||||
}
|
||||
|
||||
.dconvert-surface {
|
||||
border: 1px solid #e5e7eb;
|
||||
border-radius: 0.875rem;
|
||||
background: #fff;
|
||||
padding: 1.25rem;
|
||||
:deep(.dwallet-side__scroll) {
|
||||
max-height: none;
|
||||
flex: 1;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
<template>
|
||||
<div>
|
||||
<MobilePageHeader title="تبدیل محصول" show-back />
|
||||
<div class="px-5 mpage-content pb-2">
|
||||
<div class="px-5 mpage-content pb-[calc(var(--app-bottom-chrome-height)+1rem)]">
|
||||
<div class="border-gray-200 border-1 rounded-xl p-4 relative bg-white">
|
||||
<CopperConvertCalculator />
|
||||
</div>
|
||||
<CopperConvertHistory />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
@@ -12,4 +13,5 @@
|
||||
<script lang="ts" setup>
|
||||
import MobilePageHeader from '@/layouts/components/MobilePageHeader.vue'
|
||||
import CopperConvertCalculator from '../components/CopperConvertCalculator.vue'
|
||||
import CopperConvertHistory from '../components/CopperConvertHistory.vue'
|
||||
</script>
|
||||
|
||||
@@ -120,13 +120,11 @@
|
||||
|
||||
.dwallet-surface {
|
||||
background: #fff;
|
||||
border: 1px solid rgba(15, 23, 42, 0.06);
|
||||
border-radius: 16px;
|
||||
box-shadow: 0 1px 2px rgba(15, 23, 42, 0.04);
|
||||
}
|
||||
|
||||
.dwallet-form {
|
||||
padding: 24px;
|
||||
|
||||
&__title {
|
||||
font-size: 16px;
|
||||
|
||||
Reference in New Issue
Block a user