// CDlgItemMgr.cpp: 实现文件 // #include "pch.h" #include "scanner-check.h" #include "CDlgItemMgr.h" #include "afxdialogex.h" #include "CDlgInput.h" #include #include // CDlgItemMgr 对话框 #pragma warning(disable: 4996) static bool is_checked(CWnd* ctrl) { return ((CButton*)ctrl)->GetCheck() == BST_CHECKED; } static bool is_checked(CDialogEx* dlg, UINT id) { return is_checked(dlg->GetDlgItem(id)); } static void set_checked(CWnd* ctrl, bool checked) { ((CButton*)ctrl)->SetCheck(checked ? BST_CHECKED : BST_UNCHECKED); } static void set_checked(CDialogEx* dlg, UINT id, bool checked) { return set_checked(dlg->GetDlgItem(id), checked); } IMPLEMENT_DYNAMIC(CDlgItemMgr, CDialogEx) CDlgItemMgr::CDlgItemMgr(CWnd* pParent /*=nullptr*/) : CDialogEx(IDD_TEST_ITEM, pParent), test_tmpl_(NULL), lst_trigger_sel_change_(false) { } CDlgItemMgr::~CDlgItemMgr() { if (test_tmpl_) test_tmpl_->release(); } void CDlgItemMgr::DoDataExchange(CDataExchange* pDX) { CDialogEx::DoDataExchange(pDX); DDX_Control(pDX, IDC_LIST1, list_); DDX_Control(pDX, IDC_LIST_VAL, lst_param_); DDX_Control(pDX, IDC_COMBO_PARAM_NAME, combo_param_); DDX_Control(pDX, IDC_COMBO_PARAM_VAL0, combo_param_val_); } BOOL CDlgItemMgr::OnInitDialog() { CDialogEx::OnInitDialog(); std::vector cols; LSTCOL col; col.align = 0; col.title = L"\u5E8F\u53F7"; col.width = 40; cols.push_back(col); col.title = L"\uFF29\uFF24"; col.width = 80; cols.push_back(col); col.title = L"\u6807\u9898"; col.width = 80; cols.push_back(col); col.title = L"\u6D4B\u8BD5\u5DE5\u4F4D"; col.width = 60; cols.push_back(col); col.title = L"\u5458\u5DE5\u6743\u9650"; col.width = 60; cols.push_back(col); col.title = L"\u8054\u673A"; col.width = 40; cols.push_back(col); col.title = L"\u5931\u8D25\u5219\u505C\u6B62"; col.width = 80; cols.push_back(col); col.title = L"\u63CF\u8FF0"; col.width = 200; cols.push_back(col); init_list_ctrl(&list_, cols); cols.clear(); col.title = L"\u53C2\u6570\u540D\u79F0"; col.width = 160; cols.push_back(col); col.title = L"\u53C2\u6570\u503C"; col.width = 200; cols.push_back(col); init_list_ctrl(&lst_param_, cols); init_sane_cfg(); load_stored_config(); return TRUE; // 除非将焦点设置到控件,否则返回 TRUE } BEGIN_MESSAGE_MAP(CDlgItemMgr, CDialogEx) ON_BN_CLICKED(IDC_BUTTON_ADD, &CDlgItemMgr::OnBnClickedButtonAdd) ON_NOTIFY(NM_DBLCLK, IDC_LIST1, &CDlgItemMgr::OnNMDblclkList1) ON_WM_DROPFILES() ON_BN_CLICKED(IDC_BUTTON_ADD2, &CDlgItemMgr::OnBnClickedButtonAdd2) ON_CBN_SELCHANGE(IDC_COMBO_PARAM_NAME, &CDlgItemMgr::OnCbnSelchangeComboParamName) ON_NOTIFY(LVN_ITEMCHANGED, IDC_LIST_VAL, &CDlgItemMgr::OnLvnItemchangedListVal) ON_NOTIFY(NM_CLICK, IDC_LIST1, &CDlgItemMgr::OnNMClickList1) ON_BN_CLICKED(IDC_BUTTON_SAVE_TEMPLATE, &CDlgItemMgr::OnBnClickedButtonSaveTemplate) ON_BN_CLICKED(IDC_BUTTON_CLEAR, &CDlgItemMgr::OnBnClickedButtonClear) END_MESSAGE_MAP() // CDlgItemMgr 消息处理程序 void CDlgItemMgr::OnBnClickedButtonAdd() { // TODO: 在此添加控件通知处理程序代码 wchar_t text[128] = { 0 }; int ind = -1; known_file_util::IJsonW* jsn = NULL; if (GetDlgItemTextW(IDC_EDIT_NAME, text, _countof(text) - 1) == 0) { ::MessageBoxW(m_hWnd, L"\u5FC5\u987B\u8F93\u5165NAME\uFF01", L"Error", MB_OK | MB_ICONSTOP); GotoDlgCtrl(GetDlgItem(IDC_EDIT_NAME)); return; } ind = find_test_item(text, &jsn); if (ind == -1) { jsn = known_file_util::create_jsonW(); jsn->set_value(L"name", text); ind = list_.InsertItem(list_.GetItemCount(), std::to_wstring(list_.GetItemCount() + 1).c_str()); list_.SetItemText(ind, 1, text); list_.SetItemData(ind, (DWORD_PTR)jsn); jsn->add_ref(); } GetDlgItemTextW(IDC_EDIT_TITLE, text, _countof(text) - 1); jsn->set_value(L"title", text); list_.SetItemText(ind, 2, text); GetDlgItemTextW(IDC_COMBO_STATION, text, _countof(text) - 1); jsn->set_value(L"station", text); list_.SetItemText(ind, 3, text); GetDlgItemTextW(IDC_EDIT_PRIV, text, _countof(text) - 1); jsn->set_value(L"authority", text); list_.SetItemText(ind, 4, text); bool bv = ((CButton*)GetDlgItem(IDC_CHECK_ONLINE))->GetCheck() == BST_CHECKED; jsn->set_value(L"man", !bv); list_.SetItemText(ind, 5, bv ? L"true" : L"false"); bv = ((CButton*)GetDlgItem(IDC_CHECK_FATAL))->GetCheck() == BST_CHECKED; jsn->set_value(L"err-level", bv ? L"fatal" : L"ignore"); list_.SetItemText(ind, 6, bv ? L"true" : L"false"); std::wstring desc(get_window_text(GetDlgItem(IDC_EDIT_DESC)->m_hWnd)); replace(desc, L"\r", L"\\r"); replace(desc, L"\n", L"\\n"); jsn->set_value(L"desc", desc.c_str()); list_.SetItemText(ind, 7, desc.c_str()); // param ... jsn->remove_value(L"param"); if (lst_param_.GetItemCount()) { known_file_util::IJsonW* param = known_file_util::create_jsonW(); for (int i = 0; i < lst_param_.GetItemCount(); ++i) { known_file_util::IJsonW* sane = (known_file_util::IJsonW*)lst_param_.GetItemData(i); const wchar_t* type = NULL; sane->get_value(L"type", &type); desc = get_list_item_text(&lst_param_, i, 1); if (wcscmp(type, L"bool") == 0) { param->set_value(sane->key(), desc == L"true"); } else if (wcscmp(type, L"int") == 0) { param->set_value(sane->key(), _wtoi(desc.c_str())); } else if (wcscmp(type, L"float") == 0) { param->set_value(sane->key(), _wtof(desc.c_str())); } else // string { param->set_value(sane->key(), desc.c_str()); } } jsn->set_value(L"param", param); } test_tmpl_->set_value(jsn->key(), jsn); jsn->release(); save_test_template(STORE_FILE_TEMP); } void CDlgItemMgr::OnNMDblclkList1(NMHDR* pNMHDR, LRESULT* pResult) { LPNMITEMACTIVATE pNMItemActivate = reinterpret_cast(pNMHDR); // TODO: 在此添加控件通知处理程序代码 if (pNMItemActivate->iItem != -1) { known_file_util::IJsonW* jsn = (known_file_util::IJsonW*)list_.GetItemData(pNMItemActivate->iItem); const wchar_t* val = NULL; jsn->get_value(L"title", &val); if (::MessageBoxW(m_hWnd, (std::wstring(L"\u60A8\u786E\u8BA4\u8981\u5220\u9664\u6D4B\u8BD5\u9879\u201C") + val + L"\u201D\u5417\uFF1F").c_str(), L"\u786E\u8BA4", MB_YESNO | MB_ICONQUESTION) == IDYES) { test_tmpl_->remove_value(jsn->key()); jsn->release(); list_.DeleteItem(pNMItemActivate->iItem); for (int i = pNMItemActivate->iItem; i < list_.GetItemCount(); ++i) { list_.SetItemText(i, 0, std::to_wstring(i + 1).c_str()); } save_test_template(STORE_FILE_TEMP); } } *pResult = 0; } void CDlgItemMgr::OnNMClickList1(NMHDR* pNMHDR, LRESULT* pResult) { LPNMITEMACTIVATE pNMItemActivate = reinterpret_cast(pNMHDR); // TODO: 在此添加控件通知处理程序代码 if (pNMItemActivate->iItem != -1) { known_file_util::IJsonW* jsn = (known_file_util::IJsonW*)list_.GetItemData(pNMItemActivate->iItem), * param = NULL; const wchar_t* sv = NULL; std::wstring str(L""); bool bv = true; int nv = 0; double dv = .0f; jsn->get_value(L"name", &sv); ::SetDlgItemTextW(m_hWnd, IDC_EDIT_NAME, sv); sv = NULL; jsn->get_value(L"title", &sv); ::SetDlgItemTextW(m_hWnd, IDC_EDIT_TITLE, sv); jsn->get_value(L"man", bv); ((CButton*)GetDlgItem(IDC_CHECK_ONLINE))->SetCheck(bv ? BST_UNCHECKED : BST_CHECKED); sv = NULL; jsn->get_value(L"station", &sv); ::SetDlgItemTextW(m_hWnd, IDC_COMBO_STATION, sv); jsn->get_value(L"authority", nv); SetDlgItemInt(IDC_EDIT_PRIV, nv); jsn->get_value(L"err-level", &sv); ((CButton*)GetDlgItem(IDC_CHECK_FATAL))->SetCheck(wcscmp(sv, L"fatal") ? BST_UNCHECKED : BST_CHECKED); if (jsn->get_value(L"desc", &sv) && sv) { str = sv; replace(str, L"\\r", L"\r"); replace(str, L"\\n", L"\n"); ::SetDlgItemTextW(m_hWnd, IDC_EDIT_DESC, str.c_str()); str.clear(); } jsn->get_value(L"param", ¶m); lst_param_.DeleteAllItems(); if (param) { known_file_util::JSONMEMW jm = param->first_member(); while (jm.type != known_file_util::JV_UNKNOWN) { known_file_util::IJsonW* sane = NULL; nv = find_sane_item(jm.key, &sane); if (sane) { sane->get_value(L"title", &sv); nv = lst_param_.InsertItem(lst_param_.GetItemCount(), sv); sane->get_value(L"type", &sv); if (wcscmp(sv, L"bool") == 0) { lst_param_.SetItemText(nv, 1, jm.bool_val ? L"true" : L"false"); } else if (wcscmp(sv, L"int") == 0) { lst_param_.SetItemText(nv, 1, std::to_wstring(jm.int_val).c_str()); } else if (wcscmp(sv, L"float") == 0) { lst_param_.SetItemText(nv, 1, std::to_wstring(jm.double_val).c_str()); } else { lst_param_.SetItemText(nv, 1, jm.str_val); } sane->release(); } jm = param->next_member(); } param->release(); } } *pResult = 0; } std::wstring CDlgItemMgr::get_stored_config_file(int type) { wchar_t path[MAX_PATH] = { 0 }; std::wstring file(L""); size_t pos = 0; GetModuleFileNameW(NULL, path, _countof(path) - 1); file = path; pos = file.rfind(L'\\'); if (pos++ != std::wstring::npos) file.erase(pos); if(type == STORE_FILE_BACKUP) file += L"config\\stored_bkp.txt"; else if(type == STORE_FILE_TEMP) file += L"config\\stored_tmp.txt"; else file += L"config\\stored.txt"; return file; } void CDlgItemMgr::load_from_file(const wchar_t* file) { int size = 2048, cnt = 0; wchar_t *path = (wchar_t*)malloc(size), *sn = path, *n = sn + 40, *t = n + 40, *m = t + 40, *f = m + 40, *d = f + 40; size_t pos = 0; std::string bom(""); std::wstring cont(L""); list_.DeleteAllItems(); file_util::load_file(file, got_str, &bom); coding_util::bom::to_unicode(bom.c_str(), bom.length(), got_wstr, &cont); bom.clear(); if (test_tmpl_) test_tmpl_->release(); test_tmpl_ = known_file_util::create_jsonW(); if (!test_tmpl_->attach(cont.c_str())) { test_tmpl_->clear(); cont += L"\r\n"; while ((pos = cont.find(L"\r\n")) != std::wstring::npos) { int num = swscanf(cont.substr(0, pos).c_str(), L"%s %s %s %s %s", n, t, m, f, d); if (num >= 2) { known_file_util::IJsonW* child = known_file_util::create_jsonW(); child->set_value(L"name", n); child->set_value(L"title", t); if (!m) m = L"false"; child->set_value(L"man", wcscmp(m, L"true") != 0); if (!f) f = L"true"; child->set_value(L"err-level", wcscmp(f, L"true") ? L"ignore" : L"fatal"); if (!d) d = L""; child->set_value(L"desc", d); test_tmpl_->set_value(n, child); child->release(); } memset(path, 0, size); cont.erase(0, pos + 2); } cont.clear(); test_tmpl_->to_string(got_wstr, &cont); file_util::force_move_file(file, (std::wstring(file) + L".bkp").c_str()); coding_util::bom::from_unicode(cont.c_str(), cont.length() * 2, got_str, &bom); file_util::save_2_file(bom.c_str(), bom.length(), file); bom.clear(); cont.clear(); } cnt = 1; known_file_util::IJsonW* child = test_tmpl_->first_child(); while (child) { const wchar_t* sv = NULL; bool bv = true; int nv = 0; int ind = list_.InsertItem(list_.GetItemCount(), std::to_wstring(list_.GetItemCount() + 1).c_str()); child->get_value(L"name", &sv); list_.SetItemText(ind, 1, sv); if(child->get_value(L"title", &sv)) list_.SetItemText(ind, 2, sv); if(child->get_value(L"station", &sv)) list_.SetItemText(ind, 3, sv); if(child->get_value(L"authority", nv)) list_.SetItemText(ind, 4, std::to_wstring(nv).c_str()); if(child->get_value(L"man", bv)) list_.SetItemText(ind, 5, bv ? L"false" : L"true"); if(child->get_value(L"err-level", &sv)) list_.SetItemText(ind, 6, wcscmp(sv, L"fatal") == 0 ? L"true" : L"false"); child->get_value(L"desc", &sv); list_.SetItemText(ind, 7, sv); list_.SetItemData(ind, (DWORD_PTR)child); child = test_tmpl_->next_child(); } ::PostMessage(GetParent()->m_hWnd, WM_TEST_ITEM_CHANGED, 0, 0); free(path); } void CDlgItemMgr::load_stored_config(void) { std::wstring file(get_stored_config_file()); load_from_file(file.c_str()); } void CDlgItemMgr::init_sane_cfg(void) { std::wstring text(L""); const wchar_t *val = NULL; int ind = -1; known_file_util::IJsonW* jsn = NULL, * child = NULL; for (int i = 0; i < combo_param_.GetCount(); ++i) { ((known_file_util::IJsonW*)combo_param_.GetItemData(i))->release(); } combo_param_.ResetContent(); get_sane_config(text); jsn = known_file_util::create_jsonW(text.c_str()); if (jsn) { child = jsn->first_child(); if (child) { child->release(); while ((child = jsn->next_child())) { child->get_value(L"type", &val); if (wcscmp(val, L"button") && wcscmp(val, L"group")) { child->get_value(L"title", &val); while (*val == L' ' || *val == L'\t') val++; ind = combo_param_.AddString(val); combo_param_.SetItemData(ind, (DWORD_PTR)child); } } } jsn->release(); } } int CDlgItemMgr::find_test_item(const wchar_t* name, known_file_util::IJsonW** jsn) { for (int i = 0; i < list_.GetItemCount(); ++i) { known_file_util::IJsonW* js = (known_file_util::IJsonW*)list_.GetItemData(i); const wchar_t* val = 0; js->get_value(L"name", &val); if (wcscmp(val, name) == 0) { if (jsn) { *jsn = js; js->add_ref(); } return i; } } return -1; } int CDlgItemMgr::find_sane_item(const wchar_t* name, known_file_util::IJsonW** jsn) { for (int i = 0; i < combo_param_.GetCount(); ++i) { known_file_util::IJsonW* js = (known_file_util::IJsonW*)combo_param_.GetItemData(i); if (wcscmp(js->key(), name) == 0) { if (jsn) { *jsn = js; js->add_ref(); } return i; } } return -1; } void CDlgItemMgr::save_test_template(int type) { if (test_tmpl_) { std::wstring cont(L""), file(get_stored_config_file(type)); std::string bom(""); test_tmpl_->to_string(got_wstr, &cont); coding_util::bom::from_unicode(cont.c_str(), cont.length() * 2, got_str, &bom); cont.clear(); file_util::save_2_file(bom.c_str(), bom.length(), file.c_str()); } } known_file_util::IJsonW* CDlgItemMgr::get_all_items(void) { if (test_tmpl_) { std::wstring text(L""); test_tmpl_->to_string(got_wstr, &text); known_file_util::IJsonW* jsn = known_file_util::create_jsonW(text.c_str()); return jsn; } return NULL; } void CDlgItemMgr::OnDropFiles(HDROP hDropInfo) { // TODO: 在此添加消息处理程序代码和/或调用默认值 // TODO: 在此添加消息处理程序代码和/或调用默认值 wchar_t path[MAX_PATH] = { 0 }; std::wstring cont(L""); std::string bom(""); DragQueryFileW(hDropInfo, 0, path, _countof(path) - 1); load_from_file(path); CDialogEx::OnDropFiles(hDropInfo); } void CDlgItemMgr::OnBnClickedButtonAdd2() { // TODO: 在此添加控件通知处理程序代码 添加测试参数 add_param(m_hWnd, &combo_param_, &combo_param_val_, &lst_param_, IDC_EDIT_PARAM_VAL1); } void CDlgItemMgr::OnCbnSelchangeComboParamName() { // TODO: 在此添加控件通知处理程序代码 on_combo_param_changed(m_hWnd, &combo_param_, &combo_param_val_, &lst_param_, IDC_EDIT_PARAM_VAL1, lst_trigger_sel_change_); } void CDlgItemMgr::notify_combo_param_changed(void* param) { struct _cb_chg { CDlgItemMgr* dlg; void(CDlgItemMgr::* cb_sel_change)(void); }; struct _cb_chg* chg = (struct _cb_chg*)param; chg->dlg->lst_trigger_sel_change_ = true; (chg->dlg->*chg->cb_sel_change)(); chg->dlg->lst_trigger_sel_change_ = false; } void CDlgItemMgr::OnLvnItemchangedListVal(NMHDR* pNMHDR, LRESULT* pResult) { LPNMLISTVIEW pNMLV = reinterpret_cast(pNMHDR); // TODO: 在此添加控件通知处理程序代码 struct _cb_chg { CDlgItemMgr* dlg; void(CDlgItemMgr::* cb_sel_change)(void); }param = { this, &CDlgItemMgr::OnCbnSelchangeComboParamName }; on_list_param_sel_changed(&combo_param_, &lst_param_, pNMLV->iItem, &CDlgItemMgr::notify_combo_param_changed, ¶m); *pResult = 0; } void CDlgItemMgr::OnBnClickedButtonSaveTemplate() { // TODO: 在此添加控件通知处理程序代码 save_test_template(STORE_FILE_SELF); file_util::force_delete_file(get_stored_config_file(STORE_FILE_TEMP).c_str()); } void CDlgItemMgr::OnBnClickedButtonClear() { // TODO: 在此添加控件通知处理程序代码 lst_param_.DeleteAllItems(); }