Browse Source

会员信息页面优化好

张洋 1 month ago
parent
commit
e616ee1e40

+ 119 - 25
bin/Win32/Debug/zhipuzi_pos_windows/skin/huiyuan_info_show_wnd.xml

@@ -1,29 +1,123 @@
 <?xml version="1.0" encoding="UTF-8"?>
-<Window size="502,600" caption="0,0,0,36" roundcorner="4,4" shadowsize="3" showshadow="true">
-	<Font id="0" name="微软雅黑" size="22" />
-	
-	<VerticalLayout bkimage="shoukuan_bkg.png" >
-		<HorizontalLayout name="shoukuan_title_bkg" height="44" bkcolor="0xFF3CB371">
-			<Label name="memo_dlg_title" text="会员信息" height="44" align="center" valign="center" padding="0,0,0,0" textcolor="#FFFFFFFF" font="2"/>
-			<Button name="closebtn" keyboard="false" padding="0,13,15,0" width="16" height="16" normalimage="file='close_normal.png'" hotimage="file='close_hover.png'" pushedimage="file='close_normal.png'"/>
-		</HorizontalLayout>
-		
-		<VerticalLayout padding="0,20,0,0">
-			<Label name="huiyuan_num" text="会员卡号:" heiht="30" padding="30,10,10,10"></Label>
-				
-			<HorizontalLayout height="30" padding="30,10,10,10">
-				<Label name="huiyuan_phone" text="手机号:" width="200" heiht="30" padding="0,0,0,0"></Label>
-				<Label name="huiyuan_mimazhifu" text="密码支付:" width="200" heiht="30" padding="30,0,0,0"></Label>
+<Window size="520,574" caption="0,0,0,44" roundcorner="4,4" shadowsize="3" showshadow="true">
+	<Font id="220" name="微软雅黑" size="12" />
+	<Font id="221" name="微软雅黑" size="13" />
+	<Font id="222" name="微软雅黑" size="14" />
+	<Font id="223" name="微软雅黑" size="15" />
+	<Font id="224" name="微软雅黑" size="20" />
+	<Font id="225" name="微软雅黑" size="24" />
+	<Font id="226" name="微软雅黑" size="26" />
+
+	<VerticalLayout width="520" height="564" bkcolor="#FFF5F7FA">
+
+		<!-- ==================== 头部(520 x 132,纯色绿,冻结态由代码置灰) ==================== -->
+		<VerticalLayout name="huiyuan_info_head" width="520" height="132" bkcolor="#FF3CB371">
+
+			<!-- 标题栏 44:标题在左侧,关闭按钮 float 在右上角 -->
+			<HorizontalLayout width="520" height="44" padding="20,0,20,0" childvalign="center">
+				<Label text="会员信息" font="223" textcolor="#FFFFFFFF" width="200" height="44" maxheight="44" align="left" valign="center" />
+				<Button name="closebtn" keyboard="false" float="true" pos="486,14,502,30" width="16" height="16" tooltip="关闭" bkcolor="#00000000" hotbkcolor="#00000000" pushedbkcolor="#00000000" normalimage="file='close_normal.png'" hotimage="file='close_hover.png'" pushedimage="file='close_normal.png'" />
+			</HorizontalLayout>
+
+			<!-- 头像 + 姓名 + 徽章(88):设计稿中内容偏上 6px,底部留白 26px -->
+			<HorizontalLayout width="520" height="88" padding="20,6,20,26">
+				<Label name="huiyuan_info_avatar" text="" font="225" textcolor="#FFFFFFFF" width="56" height="56" maxheight="56" align="center" valign="center" bkimage="file='hyinfo_avatar.png'" />
+				<Control width="14" height="56" />
+				<VerticalLayout width="410" height="56">
+					<Label name="huiyuan_info_name" text="" font="224" textcolor="#FFFFFFFF" width="410" height="26" maxheight="26" valign="bottom" />
+					<Control width="410" height="8" />
+					<HorizontalLayout width="410" height="22">
+						<Label name="huiyuan_info_level" text="" font="220" textcolor="#FFFFFFFF" width="88" height="22" maxheight="22" align="center" valign="center" bkimage="file='hyinfo_pill_level.png'" />
+						<Control width="8" height="22" />
+						<Label name="huiyuan_info_status" text="" font="220" textcolor="#FF3CB371" width="56" height="22" maxheight="22" align="center" valign="center" bkimage="file='hyinfo_pill_state.png'" />
+					</HorizontalLayout>
+				</VerticalLayout>
+			</HorizontalLayout>
+		</VerticalLayout>
+
+		<!-- ==================== 内容区(520 x 444,冻结态;正常态由代码缩为 404) ==================== -->
+		<VerticalLayout name="huiyuan_info_body" width="520" height="444" padding="20,16,20,20">
+
+			<!-- 余额 / 积分(480 x 92) -->
+			<HorizontalLayout width="480" height="92" bkimage="file='hyinfo_bal_card.png'" childvalign="vcenter">
+				<VerticalLayout width="239" height="92" padding="0,18,0,18">
+					<Label text="当前余额" font="221" textcolor="#FF8A9099" width="239" height="20" maxheight="20" align="center" valign="center" />
+					<Control width="239" height="6" />
+					<Label name="huiyuan_info_balance" text="¥0.00" font="226" textcolor="#FFFF8910" width="239" height="30" maxheight="30" align="center" valign="center" />
+				</VerticalLayout>
+				<Control width="1" height="44" bkcolor="#FFE4E7EB" />
+				<VerticalLayout width="240" height="92" padding="0,18,0,18">
+					<Label text="可用积分" font="221" textcolor="#FF8A9099" width="240" height="20" maxheight="20" align="center" valign="center" />
+					<Control width="240" height="6" />
+					<Label name="huiyuan_info_point" text="0" font="226" textcolor="#FF3CB371" width="240" height="30" maxheight="30" align="center" valign="center" />
+				</VerticalLayout>
+			</HorizontalLayout>
+
+			<Control width="480" height="14" />
+
+			<!-- 信息栅格(480 x 190,白卡 9-slice 拉伸):4 行 + 行 1 与行 2 之间 1px 分隔线;设计稿 padding 18,6,18,15 -->
+			<VerticalLayout width="480" height="190" bkimage="file='hyinfo_info_card.png' corner='12,12,12,12'" padding="0,6,0,15" inset="15,0,15,0">
+
+				<!-- 行1:手机号 / 性别 -->
+				<HorizontalLayout width="444" height="42">
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="手机号" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_phone" text="" font="221" textcolor="#FF1F2329" width="148" height="30" maxheight="30" valign="center" />
+					</HorizontalLayout>
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="性别" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_sex" text="" font="221" textcolor="#FF1F2329" width="148" height="30" maxheight="30" valign="center" />
+					</HorizontalLayout>
+				</HorizontalLayout>
+
+				<!-- 分隔线 -->
+				<Control width="444" height="1" bkcolor="#FFE4E7EB" />
+
+				<!-- 行2:生日 / 密码支付 -->
+				<HorizontalLayout width="444" height="42">
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="生日" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_birthday" text="" font="221" textcolor="#FF1F2329" width="148" height="30" maxheight="30" valign="center" />
+					</HorizontalLayout>
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="密码支付" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_pay_password" text="已开启" font="220" textcolor="#FF3CB371" width="52" height="22" maxheight="22" align="center" valign="center" bkimage="file='hyinfo_tag_on.png'" />
+					</HorizontalLayout>
+				</HorizontalLayout>
+
+				<!-- 行3:实体卡 / 会员卡号 -->
+				<HorizontalLayout width="444" height="42">
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="实体卡" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_shitika" text="已绑定" font="220" textcolor="#FF3CB371" width="52" height="22" maxheight="22" align="center" valign="center" bkimage="file='hyinfo_tag_on.png'" />
+					</HorizontalLayout>
+					<HorizontalLayout width="222" height="42" childvalign="vcenter">
+						<Label text="会员卡号" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+						<Label name="huiyuan_info_card_no" text="" font="221" textcolor="#FF1F2329" width="148" height="30" maxheight="30" valign="center" />
+					</HorizontalLayout>
+				</HorizontalLayout>
+
+				<!-- 行4:地址(整行) -->
+				<HorizontalLayout width="444" height="42" childvalign="vcenter">
+					<Label text="地址" font="221" textcolor="#FF8A9099" width="74" height="30" maxheight="30" valign="center" />
+					<Label name="huiyuan_info_address" text="" font="221" textcolor="#FF1F2329" width="370" height="30" maxheight="30" valign="center" />
+				</HorizontalLayout>
+			</VerticalLayout>
+
+			<!-- 冻结提示条(40,正常态隐藏;代码同步调整窗口高度) -->
+			<VerticalLayout name="huiyuan_info_frozen_tip" visible="false" width="480" height="40">
+				<Label text="该会员已冻结,不可使用余额支付与积分抵扣" font="221" textcolor="#FFFF4500" width="480" height="40" maxheight="40" align="center" valign="center" bkimage="file='hyinfo_frozen_tip.png'" />
+			</VerticalLayout>
+
+			<!-- 底部按钮前间距(16) -->
+			<Control width="480" height="16" />
+
+			<!-- 底部按钮(480 x 44) -->
+			<HorizontalLayout width="480" height="44">
+				<Button name="huiyuan_info_chongzhi_btn" text="会员充值" font="223" textcolor="#FF5F6368" width="234" height="44" maxheight="44" bkcolor="#00000000" hotbkcolor="#00000000" pushedbkcolor="#00000000" normalimage="file='hyinfo_btn_ghost_normal.png'" hotimage="file='hyinfo_btn_ghost_hover.png'" pushedimage="file='hyinfo_btn_ghost_pushed.png'" />
+				<Control width="12" height="44" />
+				<Button name="huiyuan_info_close_btn" text="关闭" font="223" textcolor="#FFFFFFFF" width="234" height="44" maxheight="44" bkcolor="#00000000" hotbkcolor="#00000000" pushedbkcolor="#00000000" normalimage="file='hyinfo_btn_main_normal.png'" hotimage="file='hyinfo_btn_main_hover.png'" pushedimage="file='hyinfo_btn_main_pushed.png'" />
 			</HorizontalLayout>
-			
-			<Label name="huiyuan_yue" text="当前余额:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_name" text="会员姓名:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_sex" text="性别:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_address" text="地址:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_birthday" text="生日:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_levelname" text="会员级别:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_shitika" text="实体卡:" heiht="30" padding="30,10,10,10"></Label>
-			<Label name="huiyuan_status" text="会员状态:" heiht="30" padding="30,10,10,10"></Label>
 		</VerticalLayout>
 	</VerticalLayout>
-</Window>
+</Window>

BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_avatar.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_bal_card.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_ghost_hover.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_ghost_normal.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_ghost_pushed.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_main_hover.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_main_normal.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_btn_main_pushed.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_frozen_tip.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_info_card.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_pill_level.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_pill_state.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_tag_off.png


BIN
bin/Win32/Debug/zhipuzi_pos_windows/skin/hyinfo_tag_on.png


+ 9 - 1
zhipuzi_pos_windows/page/CDiandanPageUI.cpp

@@ -2568,13 +2568,21 @@ void CDiandanPageUI::ClickMemberInfoShow()
 		pMemberLoginDlg->SetIcon(IDI_ICON_DUILIB);
 		pMemberLoginDlg->CenterWindow();
 
-		pMemberLoginDlg->SetHuiyuanInfo(m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
+		pMemberLoginDlg->SetHuiyuanInfo(m_member_id, m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
 			m_birthday, m_sex, m_address, m_is_card, m_point, m_open_no_card_payment, m_pay_password, m_freeze, m_card_identify);
 
 		UINT ret = pMemberLoginDlg->ShowModal();
 
 		if (ret == IDOK)
 		{
+			//在会员信息弹框里充值过,用最新余额刷新结算区
+			if (pMemberLoginDlg->m_new_balance.empty() == false)
+			{
+				m_balance = pMemberLoginDlg->m_new_balance;
+
+				this->UpdateJiesuanInfo();
+			}
+
 			m_is_show_modal_wnd = false;
 			delete pMemberLoginDlg;
 		}

+ 1 - 1
zhipuzi_pos_windows/page/CSaomashouyinPageUI.cpp

@@ -2090,7 +2090,7 @@ void CSaomashouyinPageUI::ClickMemberInfoShow()
 		pMemberLoginDlg->SetIcon(IDI_ICON_DUILIB);
 		pMemberLoginDlg->CenterWindow();
 
-		pMemberLoginDlg->SetHuiyuanInfo(m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
+		pMemberLoginDlg->SetHuiyuanInfo(m_member_id, m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
 			m_birthday, m_sex, m_address, m_is_card, m_point, m_open_no_card_payment, m_pay_password, m_freeze, m_card_identify);
 
 		UINT ret = pMemberLoginDlg->ShowModal();

+ 1 - 1
zhipuzi_pos_windows/page/CZhengcanDiandanPageUI.cpp

@@ -3055,7 +3055,7 @@ void CZhengcanDiandanPageUI::ClickMemberInfoShow()
 		pMemberLoginDlg->SetIcon(IDI_ICON_DUILIB);
 		pMemberLoginDlg->CenterWindow();
 
-		pMemberLoginDlg->SetHuiyuanInfo(m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
+		pMemberLoginDlg->SetHuiyuanInfo(m_member_id, m_member_name, m_member_level, m_member_level_name, m_card_no, m_balance, m_phone, \
 			m_birthday, m_sex, m_address, m_is_card, m_point, m_open_no_card_payment, m_pay_password, m_freeze, m_card_identify);
 
 		UINT ret = pMemberLoginDlg->ShowModal();

+ 326 - 21
zhipuzi_pos_windows/wnd/CHuiyuanInfoShowWnd.cpp

@@ -1,5 +1,6 @@
 #include "pch.h"
 #include "CHuiyuanInfoShowWnd.h"
+#include "CHuiyuanChongzhiWnd.h"
 
 LRESULT CHuiyuanInfoShowWnd::OnNcHitTest(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
 {
@@ -132,12 +133,20 @@ void CHuiyuanInfoShowWnd::Notify(TNotifyUI& msg)
 	{
 		DuiLib::CDuiString senderName = msg.pSender->GetName();
 
-		if (senderName == _T("closebtn"))
+		if (senderName == _T("closebtn") || senderName == _T("huiyuan_info_close_btn"))
 		{
-			Close(IDCANCEL);
+			//发生过充值,则以 IDOK 结束,调用方据此刷新会员余额
+			Close(m_is_chongzhi_success ? IDOK : IDCANCEL);
+			return;
+		}
+		else if (senderName == _T("huiyuan_info_chongzhi_btn"))
+		{
+			this->StartHuiyuanChongzhi();
 			return;
 		}
 	}
+
+	CModalWnd::Notify(msg);
 }
 
 void CHuiyuanInfoShowWnd::Init()
@@ -145,43 +154,339 @@ void CHuiyuanInfoShowWnd::Init()
 
 }
 
-void CHuiyuanInfoShowWnd::SetHuiyuanInfo(std::string m_member_name, std::string m_member_level, std::string m_member_level_name, std::string m_card_no, std::string m_balance, std::string m_phone, \
+void CHuiyuanInfoShowWnd::SetHuiyuanInfo(std::string m_member_id, std::string m_member_name, std::string m_member_level, std::string m_member_level_name, std::string m_card_no, std::string m_balance, std::string m_phone, \
 	std::string m_birthday, std::string m_sex, std::string m_address, std::string m_is_card, std::string m_point, std::string m_open_no_card_payment, std::string m_pay_password, std::string m_freeze, std::string m_card_identify)
 {
-	m_pm.FindControl(L"huiyuan_num")->SetText((L"会员卡号:" + CLewaimaiString::UTF8ToUnicode(m_card_no)).c_str());
-	m_pm.FindControl(L"huiyuan_phone")->SetText((L"手机号:" + CLewaimaiString::UTF8ToUnicode(m_phone)).c_str());
+	this->m_member_id = m_member_id;
+	this->m_name = m_member_name;
+	this->m_level_name = m_member_level_name;
+	this->m_card_no = m_card_no;
+	this->m_balance = m_balance;
+	this->m_phone = m_phone;
+	this->m_birthday = m_birthday;
+	this->m_sex = m_sex;
+	this->m_address = m_address;
+	this->m_point = m_point;
+	this->m_open_no_card_payment = m_open_no_card_payment;
+	this->m_pay_password = m_pay_password;
+	this->m_freeze = m_freeze;
+	this->m_card_identify = m_card_identify;
+
+	this->UpdateHuiyuanInfo();
+}
+
+void CHuiyuanInfoShowWnd::UpdateHuiyuanInfo()
+{
+	//是否冻结:m_freeze 为 "0" 表示正常,其余("1")为已冻结
+	bool is_frozen = (!m_freeze.empty() && m_freeze != "0");
+
+	//头像:姓氏首字
+	std::wstring wname = CLewaimaiString::UTF8ToUnicode(m_name);
+	std::wstring first_char = L"";
+	if (wname.empty() == false)
+	{
+		first_char = wname.substr(0, 1);
+	}
+	static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_avatar"))->SetText(first_char.c_str());
+
+	//姓名(脱敏)
+	static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_name"))->SetText(this->GetMinganziName(m_name).c_str());
+
+	//等级:为空时兜底显示「普通会员」
+	CLabelUI* pLevel = static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_level"));
+	std::wstring level = CLewaimaiString::UTF8ToUnicode(m_level_name);
+	if (level.empty())
+	{
+		level = L"普通会员";
+	}
+	pLevel->SetText(level.c_str());
 
-	if (m_open_no_card_payment == "1")
+	//状态:正常绿字 / 已冻结红字
+	CLabelUI* pStatus = static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_status"));
+	if (is_frozen)
 	{
-		m_pm.FindControl(L"huiyuan_mimazhifu")->SetText(L"密码支付:已开启");
+		pStatus->SetText(L"已冻结");
+		pStatus->SetTextColor(0xFFFF4500);
 	}
 	else
 	{
-		m_pm.FindControl(L"huiyuan_mimazhifu")->SetText(L"密码支付:未开启");
+		pStatus->SetText(L"正常");
+		pStatus->SetTextColor(0xFF3CB371);
+	}
+
+	//头部背景:正常纯绿 #3CB371,冻结置灰 #9AA0A6
+	CControlUI* pHead = m_pm.FindControl(L"huiyuan_info_head");
+	if (pHead != NULL)
+	{
+		pHead->SetBkColor(is_frozen ? 0xFF9AA0A6 : 0xFF3CB371);
+	}
+
+	//手机号(脱敏)
+	static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_phone"))->SetText(this->GetMinganziPhone(m_phone).c_str());
+
+	//信息栅格
+	this->SetInfoText(L"huiyuan_info_sex", m_sex);
+	this->SetInfoText(L"huiyuan_info_birthday", m_birthday);
+	this->SetInfoText(L"huiyuan_info_card_no", m_card_no);
+	this->SetInfoText(L"huiyuan_info_address", m_address);
+	this->SetInfoTag(L"huiyuan_info_pay_password", (m_open_no_card_payment == "1"), L"已开启", L"未开启");
+	this->SetInfoTag(L"huiyuan_info_shitika", (!m_card_identify.empty()), L"已绑定", L"未绑定");
+
+	//余额 / 积分:冻结时置灰
+	CLabelUI* pBalance = static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_balance"));
+	pBalance->SetText(this->FormatMoney(m_balance).c_str());
+	pBalance->SetTextColor(is_frozen ? 0xFFA8ADB3 : 0xFFFF8910);
+
+	CLabelUI* pPoint = static_cast<CLabelUI*>(m_pm.FindControl(L"huiyuan_info_point"));
+	pPoint->SetText(this->FormatPoint(m_point).c_str());
+	pPoint->SetTextColor(is_frozen ? 0xFFA8ADB3 : 0xFF3CB371);
+
+	//冻结提示:正常态隐藏提示条并缩小窗口;冻结态显示提示条并使用较大窗口
+	//内容区高度:正常 392 = 16+92+14+190+16+44+20;冻结 432 = 正常 + 40
+	const int BODY_HEIGHT_NORMAL = 392;
+	const int BODY_HEIGHT_FROZEN = 432;
+	const int WINDOW_WIDTH = 520;
+	const int HEAD_HEIGHT = 132;
+
+	CControlUI* pBody = m_pm.FindControl(L"huiyuan_info_body");
+	CControlUI* pFrozenTip = m_pm.FindControl(L"huiyuan_info_frozen_tip");
+	if (pFrozenTip != NULL)
+	{
+		pFrozenTip->SetVisible(is_frozen);
+	}
+	if (pBody != NULL)
+	{
+		pBody->SetFixedHeight(is_frozen ? BODY_HEIGHT_FROZEN : BODY_HEIGHT_NORMAL);
+	}
+
+	//窗口尚未显示前(ShowModal 之前)根据状态调整窗口高度并重新居中;
+	//充值回调里窗口已可见,此时状态不会变化,不再调整尺寸避免跳动。
+	if (m_hWnd != NULL && !::IsWindowVisible(m_hWnd))
+	{
+		int targetHeight = HEAD_HEIGHT + (is_frozen ? BODY_HEIGHT_FROZEN : BODY_HEIGHT_NORMAL);
+		::SetWindowPos(m_hWnd, NULL, 0, 0, WINDOW_WIDTH, targetHeight, SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
+		this->CenterWindow();
+	}
+
+	m_pm.NeedUpdate();
+}
+
+void CHuiyuanInfoShowWnd::StartHuiyuanChongzhi()
+{
+	CHuiyuanChongzhiWnd* pChongzhiWnd = new CHuiyuanChongzhiWnd();
+	if (pChongzhiWnd == NULL)
+	{
+		return;
+	}
+
+	pChongzhiWnd->Create(m_hWnd, _T(""), UI_WNDSTYLE_DIALOG, WS_EX_TOOLWINDOW);
+	pChongzhiWnd->SetIcon(IDI_ICON_DUILIB);
+	pChongzhiWnd->CenterWindow();
+
+	pChongzhiWnd->SetCurBalance(m_balance);
+	pChongzhiWnd->m_member_id = m_member_id;
+	pChongzhiWnd->m_member_card_no = m_card_no;
+
+	UINT ret = pChongzhiWnd->ShowModal();
+
+	if (ret == IDOK)
+	{
+		//充值成功:新余额 = 原余额 + 充值金额 + 赠送金额
+		double cur = atof(m_balance.c_str());
+		double chongzhi = atof(pChongzhiWnd->m_chongzhi.c_str());
+		double zengsong = atof(pChongzhiWnd->m_zengsong.c_str());
+
+		m_balance = CLewaimaiString::DoubleToString(cur + chongzhi + zengsong, 2);
+		m_new_balance = m_balance;
+		m_is_chongzhi_success = true;
+
+		this->UpdateHuiyuanInfo();
+	}
+
+	delete pChongzhiWnd;
+}
+
+std::wstring CHuiyuanInfoShowWnd::GetMinganziName(const std::string& name)
+{
+	std::wstring wname = CLewaimaiString::UTF8ToUnicode(name);
+
+	if (wname.empty())
+	{
+		return L"";
+	}
+	if (wname.length() == 1)
+	{
+		return wname;
+	}
+	if (wname.length() == 2)
+	{
+		return wname.substr(0, 1) + L"*";
+	}
+
+	return wname.substr(0, 1) + L"**";
+}
+
+std::wstring CHuiyuanInfoShowWnd::GetMinganziPhone(const std::string& phone)
+{
+	//只保留数字,兼容带空格 / +86 前缀的号码
+	std::string digits;
+	for (size_t i = 0; i < phone.length(); i++)
+	{
+		if (phone[i] >= '0' && phone[i] <= '9')
+		{
+			digits += phone[i];
+		}
+	}
+
+	if (digits.empty())
+	{
+		return L"未绑定手机号";
+	}
+
+	//非 11 位不做脱敏,原样展示
+	if (digits.length() != 11)
+	{
+		return CLewaimaiString::UTF8ToUnicode(phone);
+	}
+
+	std::string masked = digits.substr(0, 3) + "****" + digits.substr(7, 4);
+	return CLewaimaiString::UTF8ToUnicode(masked);
+}
+
+std::wstring CHuiyuanInfoShowWnd::FormatMoney(const std::string& value)
+{
+	std::string v = value;
+	if (v.empty())
+	{
+		v = "0";
+	}
+
+	bool negative = false;
+	if (v[0] == '-')
+	{
+		negative = true;
+		v = v.substr(1);
+	}
+
+	std::string int_part = v;
+	std::string dec_part = "00";
+
+	size_t dot = v.find('.');
+	if (dot != std::string::npos)
+	{
+		int_part = v.substr(0, dot);
+		dec_part = v.substr(dot + 1);
+		if (dec_part.length() > 2)
+		{
+			dec_part = dec_part.substr(0, 2);
+		}
+		while (dec_part.length() < 2)
+		{
+			dec_part += "0";
+		}
+	}
+
+	if (int_part.empty())
+	{
+		int_part = "0";
 	}
 
-	m_pm.FindControl(L"huiyuan_name")->SetText((L"会员姓名:" + CLewaimaiString::UTF8ToUnicode(m_member_name)).c_str());
-	m_pm.FindControl(L"huiyuan_sex")->SetText((L"性别:" + CLewaimaiString::UTF8ToUnicode(m_sex)).c_str());
-	m_pm.FindControl(L"huiyuan_address")->SetText((L"地址:" + CLewaimaiString::UTF8ToUnicode(m_address)).c_str());
-	m_pm.FindControl(L"huiyuan_birthday")->SetText((L"生日:" + CLewaimaiString::UTF8ToUnicode(m_birthday)).c_str());
-	m_pm.FindControl(L"huiyuan_levelname")->SetText((L"会员级别:" + CLewaimaiString::UTF8ToUnicode(m_member_level_name)).c_str());
-	m_pm.FindControl(L"huiyuan_yue")->SetText((L"当前余额:" + CLewaimaiString::UTF8ToUnicode(m_balance)).c_str());
+	//千分位
+	std::string out;
+	int count = 0;
+	for (int i = (int)int_part.length() - 1; i >= 0; i--)
+	{
+		out.insert(out.begin(), int_part[i]);
+		count++;
+		if (count % 3 == 0 && i > 0)
+		{
+			out.insert(out.begin(), ',');
+		}
+	}
 
-	if (m_card_identify != "")
+	std::wstring ret = L"¥";
+	if (negative)
 	{
-		m_pm.FindControl(L"huiyuan_shitika")->SetText(L"实体会员卡:已绑定");
+		ret += L"-";
+	}
+	ret += CLewaimaiString::UTF8ToUnicode(out + "." + dec_part);
+
+	return ret;
+}
+
+std::wstring CHuiyuanInfoShowWnd::FormatPoint(const std::string& value)
+{
+	std::string v = value;
+	if (v.empty())
+	{
+		return L"0";
+	}
+
+	//去掉小数部分
+	size_t dot = v.find('.');
+	if (dot != std::string::npos)
+	{
+		v = v.substr(0, dot);
+	}
+	if (v.empty())
+	{
+		return L"0";
+	}
+
+	std::string out;
+	int count = 0;
+	for (int i = (int)v.length() - 1; i >= 0; i--)
+	{
+		out.insert(out.begin(), v[i]);
+		count++;
+		if (count % 3 == 0 && i > 0)
+		{
+			out.insert(out.begin(), ',');
+		}
+	}
+
+	return CLewaimaiString::UTF8ToUnicode(out);
+}
+
+void CHuiyuanInfoShowWnd::SetInfoText(LPCTSTR control_name, const std::string& value)
+{
+	CLabelUI* pLabel = static_cast<CLabelUI*>(m_pm.FindControl(control_name));
+	if (pLabel == NULL)
+	{
+		return;
+	}
+
+	std::wstring text = CLewaimaiString::UTF8ToUnicode(value);
+	if (text.empty())
+	{
+		pLabel->SetText(L"未填写");
+		pLabel->SetTextColor(0xFFA8ADB3);
 	}
 	else
 	{
-		m_pm.FindControl(L"huiyuan_shitika")->SetText(L"实体会员卡:未绑定");
+		pLabel->SetText(text.c_str());
+		pLabel->SetTextColor(0xFF1F2329);
 	}
+}
 
-	if (m_freeze == "0")
+void CHuiyuanInfoShowWnd::SetInfoTag(LPCTSTR control_name, bool is_on, LPCTSTR on_text, LPCTSTR off_text)
+{
+	CLabelUI* pLabel = static_cast<CLabelUI*>(m_pm.FindControl(control_name));
+	if (pLabel == NULL)
 	{
-		m_pm.FindControl(L"huiyuan_status")->SetText(L"会员状态:正常");
+		return;
+	}
+
+	if (is_on)
+	{
+		pLabel->SetText(on_text);
+		pLabel->SetTextColor(0xFF3CB371);
+		pLabel->SetAttribute(L"bkimage", L"file='hyinfo_tag_on.png'");
 	}
 	else
 	{
-		m_pm.FindControl(L"huiyuan_status")->SetText(L"会员状态:已冻结");
+		pLabel->SetText(off_text);
+		pLabel->SetTextColor(0xFFA8ADB3);
+		pLabel->SetAttribute(L"bkimage", L"file='hyinfo_tag_off.png'");
 	}
-}
+}

+ 52 - 2
zhipuzi_pos_windows/wnd/CHuiyuanInfoShowWnd.h

@@ -27,9 +27,15 @@ public:
 
 	void Init();
 
-	void SetHuiyuanInfo(std::string m_member_name, std::string m_member_level, std::string m_member_level_name, std::string m_card_no, std::string m_balance, std::string m_phone, \
+	void SetHuiyuanInfo(std::string m_member_id, std::string m_member_name, std::string m_member_level, std::string m_member_level_name, std::string m_card_no, std::string m_balance, std::string m_phone, \
 		std::string m_birthday, std::string m_sex, std::string m_address, std::string m_is_card, std::string m_point, std::string m_open_no_card_payment, std::string m_pay_password, std::string m_freeze, std::string m_card_identify);
 
+	//刷新头部姓名/等级/状态、余额、积分的展示
+	void UpdateHuiyuanInfo();
+
+	//打开会员充值窗口(以本弹框为父窗口的模态)
+	void StartHuiyuanChongzhi();
+
 	void Notify(TNotifyUI& msg);
 
 	LRESULT OnCreate(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
@@ -69,4 +75,48 @@ public:
 
 public:
 	CPaintManagerUI m_pm;
-};
+
+	//充值成功后的最新余额(供调用方刷新点餐页)
+	std::string m_new_balance;
+
+	//本次是否发生过充值(发生过则弹框以 IDOK 结束)
+	bool m_is_chongzhi_success = false;
+
+private:
+	//会员原始数据
+
+	//当前会员的 id(会员充值时需要,由调用方在 Create 之后赋值)
+	std::string m_member_id;
+
+	std::string m_name;
+	std::string m_level_name;
+	std::string m_card_no;
+	std::string m_balance;
+	std::string m_phone;
+	std::string m_birthday;
+	std::string m_sex;
+	std::string m_address;
+	std::string m_point;
+	std::string m_open_no_card_payment;
+	std::string m_pay_password;
+	std::string m_freeze;
+	std::string m_card_identify;
+
+	//姓名脱敏:首字保留,其余用 *(2 字显示 1 个 *,3 字及以上显示 2 个 *)
+	std::wstring GetMinganziName(const std::string& name);
+
+	//手机号脱敏:前 3 + **** + 后 4
+	std::wstring GetMinganziPhone(const std::string& phone);
+
+	//金额展示:带 ¥ 与千分位
+	std::wstring FormatMoney(const std::string& value);
+
+	//积分展示:千分位整数
+	std::wstring FormatPoint(const std::string& value);
+
+	//填充信息栅格里的文本项,为空时统一显示灰色「未填写」
+	void SetInfoText(LPCTSTR control_name, const std::string& value);
+
+	//填充信息栅格里的开关标签(已开启/未开启、已绑定/未绑定)
+	void SetInfoTag(LPCTSTR control_name, bool is_on, LPCTSTR on_text, LPCTSTR off_text);
+};