// QReward Customer — My Card (4 states), Linked accounts const { useState: uS3, useEffect: uE3 } = React; /* ============ MY CARD ============ */ const MyCardScreen = ({ lang, status, onBack, asTab, toast }) => { // status: notapplied | submitted | activated | declined return (
{/* Shared header: card visual */}
LifeCard QUALIA
{status === 'activated' && } {status === 'submitted' && {lang === 'jp' ? '審査中' : 'In review'}}
{status === 'activated' ? DATA.card.masked : '•••• •••• •••• ••••'}
{lang === 'jp' ? 'カード名義' : 'Card holder'}
{status === 'activated' ? DATA.card.holder : '—'}
{lang === 'jp' ? '有効期限' : 'Expires'}
{status === 'activated' ? DATA.card.expiry : '••/••'}
{status === 'notapplied' && } {status === 'submitted' && } {status === 'activated' && } {status === 'declined' && }
); }; const benefits = (lang) => [ { icon: 'spark', t: lang === 'jp' ? '利用金額の最大2%をポイント還元' : 'Up to 2% points back on every purchase' }, { icon: 'gift', t: lang === 'jp' ? '提携店舗で限定オファー' : 'Exclusive offers at partner stores' }, { icon: 'shield', t: lang === 'jp' ? '年会費無料・不正利用補償付き' : 'No annual fee · fraud protection included' }, ]; const CardNotApplied = ({ lang, toast }) => { const [showInterstitial, setShow] = uS3(false); if (showInterstitial) return (
{lang === 'jp' ? '申請を受け付けました' : 'Application submitted'}
{lang === 'jp' ? 'LifeCardの審査結果は、次回のデータ更新時に反映されます。' : "We'll update your status when LifeCard's daily report arrives."}
toast(lang === 'jp' ? 'マイカードで状況を確認できます' : 'Track it in My Card')}>{lang === 'jp' ? 'マイカードで追跡' : 'Track in My Card'}
); return (
{lang === 'jp' ? '特典' : 'Benefits'}
{benefits(lang).map((b, i) => (
{b.t}
))}
setShow(true)}>{lang === 'jp' ? '今すぐ申請' : 'Apply now'} {lang === 'jp' ? '詳しく見る' : 'Learn more'}
{lang === 'jp' ? '「今すぐ申請」をタップすると、LifeCardの申請フォームが開きます。' : 'Apply now opens LifeCard\'s secure application form in an in-app browser.'}
); }; const Timeline = ({ items }) => (
{items.map((it, i) => (
{it.state === 'done' ? : it.state === 'active' ? : it.state === 'failed' ? : null}
{it.title}
{it.time &&
{it.time}
} {it.meta &&
{it.meta}
}
))}
); const CardSubmitted = ({ lang }) => (
{lang === 'jp' ? '申請状況' : 'Application timeline'}
{lang === 'jp' ? '審査には数営業日かかる場合があります。' : 'Decisions can take a few business days. We\'ll notify you the moment it changes.'}
); const CardActivated = ({ lang }) => (
{lang === 'jp' ? '申請状況' : 'Application timeline'}
{lang === 'jp' ? 'カード詳細' : 'Card details'}
{lang === 'jp' ? 'カード番号' : 'Card number'}
{DATA.card.masked}
{lang === 'jp' ? '有効期限' : 'Expiry'}
{DATA.card.expiry}
{lang === 'jp' ? 'カード名義' : 'Cardholder'}
{DATA.card.holder}
); const CardDeclined = ({ lang, toast }) => (
{lang === 'jp' ? '今回はご希望に添えませんでした' : "Your application wasn't successful this time"}
{lang === 'jp' ? '理由はさまざまです。時間をおいて再度お申し込みいただけます。' : 'There are many possible reasons. You can apply again, and we\'re here to help.'}
toast(lang === 'jp' ? '申請フローを開きます' : 'Re-opening application')}>{lang === 'jp' ? '再申請する' : 'Apply again'}
); /* ============ LINKED ACCOUNTS ============ */ const LinkedAccountsScreen = ({ lang, onBack, toast }) => { const [sources, setSources] = uS3([ { id: 'qualia', name: 'QUALIA', linked: true, last: '2026/06/07 09:14', color: '#7c3aed', letter: 'Q' }, { id: 'lifecard', name: 'LifeCard', linked: true, last: '2026/06/07 10:31', color: '#0ea5e9', letter: 'L' }, { id: 'rakuten', name: 'Rakuten', linked: false, last: null, color: '#bf0000', letter: 'R' }, ]); const [linking, setLinking] = uS3(null); // id being linked (browser open) const [unlinkTarget, setUnlink] = uS3(null); const doLink = (id) => { setLinking(id); setTimeout(() => { setSources(s => s.map(x => x.id === id ? { ...x, linked: true, last: '2026/06/08 just now' } : x)); setLinking(null); toast(lang === 'jp' ? '連携しました' : 'Linked successfully'); }, 1800); }; const doUnlink = () => { setSources(s => s.map(x => x.id === unlinkTarget ? { ...x, linked: false, last: null } : x)); toast(lang === 'jp' ? '連携を解除しました' : 'Unlinked'); setUnlink(null); }; return (
{lang === 'jp' ? '提携先を連携すると、ポイントが自動で同期されます。' : 'Link partner accounts to sync your points automatically.'}
{sources.map(s => (
{s.letter}
{s.name}
{s.linked ?
:
} {s.last &&
{lang === 'jp' ? '最終同期' : 'Last sync'} {s.last}
}
{linking === s.id ?
{lang === 'jp' ? '連携中' : 'Linking'}
: s.linked ? : }
))}
{lang === 'jp' ? '連携時は提携先の認証画面が開きます。認証情報がQRewardに保存されることはありません。' : "Linking opens the partner's secure sign-in. We never store your partner credentials."}
setUnlink(null)} title={lang === 'jp' ? '連携を解除しますか?' : `Unlink ${sources.find(s => s.id === unlinkTarget)?.name}?`}>
{lang === 'jp' ? '再連携するまで、新しいポイントは付与されません。' : "You'll stop earning new points from this source until you link again."}
{lang === 'jp' ? '連携を解除' : 'Unlink'}
); }; Object.assign(window, { MyCardScreen, LinkedAccountsScreen });