mfc로 만든 계산기 질문입니다
-
게시물 수정 , 삭제는 로그인 필요
안녕하세요 계산기를 만들어 보면서 mfc를 공부중입니다만
아무리 생각해봐도 막히는 부분이 있어서 질문을 하려고 합니다
아래 사진처럼 있는데 아래에 있는 에디트 컨트롤이 m_edit1 이고 위에 있는 에디트 컨트롤이 m_edit2 입니다
m_edit1 이 값만 출력되고 m_edit2는 계산과정만 출력되는.
지금은 다른 블로그에서 작성해주신걸 보고 만들었는데 제 식대로 바꿔보고 싶은데 이게 막혀서 한발짝도 못나가고 있습니다
첫번째로 키보드로 입력 받는걸 제가 구현을 해놨는데 이게 이상하게 출력이 됩니다 버튼으로 눌렀을땐 1 + 2 + 3 + 이런식으로 나오는데
키보드로 저렇게 누르면 사진처럼 이상하게 나옵니다
키보드로 1 + 2 +3 눌렀을때
버튼으로 1 + 2 +3 눌렀을때
두번째는 숫자 버튼을 누르면 바로 m_edit2 에 출력되게 하고 싶은데 m_edit1에 먼저 출력이 되고 사칙연산 버튼을 눌러야 m_edit2에 눌러진 사칙연산과 함께 출력됩니다
m_edit1 에는 = 버튼을 눌렀을때 결과만이 나오게 하고 싶은데 이 부분도 제가 아는 선에서 여기저기 고쳐봤지만 결국 답이 안보입니다
예시를 곁들인 조언 부탁드립니다 도저히 답이 안보입니다....
// 0819Dlg.cpp : 구현 파일
//
#include "stdafx.h"
#include "0819.h"
#include "0819Dlg.h"
#include "afxdialogex.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
// 응용 프로그램 정보에 사용되는 CAboutDlg 대화 상자입니다.
class CAboutDlg : public CDialogEx
{
public:
CAboutDlg();
// 대화 상자 데이터입니다.
enum { IDD = IDD_ABOUTBOX };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV 지원입니다.
// 구현입니다.
protected:
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialogEx(CAboutDlg::IDD)
{
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()
// CMy0819Dlg 대화 상자
CMy0819Dlg::CMy0819Dlg(CWnd* pParent /*=NULL*/)
: CDialogEx(CMy0819Dlg::IDD, pParent)
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void CMy0819Dlg::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
DDX_Control(pDX, IDC_EDIT1, m_edit1);
DDX_Control(pDX, IDC_EDIT2, m_edit2);
}
BEGIN_MESSAGE_MAP(CMy0819Dlg, CDialogEx)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(B_Plus, &CMy0819Dlg::OnBnClickedPlus)
ON_BN_CLICKED(B_Minus, &CMy0819Dlg::OnBnClickedMinus)
ON_BN_CLICKED(B_Divi, &CMy0819Dlg::OnBnClickedDivi)
ON_BN_CLICKED(B_Mult, &CMy0819Dlg::OnBnClickedMult)
ON_BN_CLICKED(B_Eq, &CMy0819Dlg::OnBnClickedEq)
ON_BN_CLICKED(B_Clear, &CMy0819Dlg::OnBnClickedClear)
END_MESSAGE_MAP()
// CMy0819Dlg 메시지 처리기
BOOL CMy0819Dlg::OnInitDialog()
{
CDialogEx::OnInitDialog();
// 시스템 메뉴에 "정보..." 메뉴 항목을 추가합니다.
// IDM_ABOUTBOX는 시스템 명령 범위에 있어야 합니다.
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
BOOL bNameValid;
CString strAboutMenu;
bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
ASSERT(bNameValid);
if (!strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// 이 대화 상자의 아이콘을 설정합니다. 응용 프로그램의 주 창이 대화 상자가 아닐 경우에는
// 프레임워크가 이 작업을 자동으로 수행합니다.
SetIcon(m_hIcon, TRUE); // 큰 아이콘을 설정합니다.
SetIcon(m_hIcon, FALSE); // 작은 아이콘을 설정합니다.
// TODO: 여기에 추가 초기화 작업을 추가합니다.
return TRUE; // 포커스를 컨트롤에 설정하지 않으면 TRUE를 반환합니다.
}
void CMy0819Dlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialogEx::OnSysCommand(nID, lParam);
}
}
// 대화 상자에 최소화 단추를 추가할 경우 아이콘을 그리려면
// 아래 코드가 필요합니다. 문서/뷰 모델을 사용하는 MFC 응용 프로그램의 경우에는
// 프레임워크에서 이 작업을 자동으로 수행합니다.
void CMy0819Dlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // 그리기를 위한 디바이스 컨텍스트입니다.
SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);
// 클라이언트 사각형에서 아이콘을 가운데에 맞춥니다.
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// 아이콘을 그립니다.
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialogEx::OnPaint();
}
}
// 사용자가 최소화된 창을 끄는 동안에 커서가 표시되도록 시스템에서
// 이 함수를 호출합니다.
HCURSOR CMy0819Dlg::OnQueryDragIcon()
{
return static_cast<HCURSOR>(m_hIcon);
}
BOOL CMy0819Dlg::OnCommand(WPARAM wParam, LPARAM lParam)
{
if (B_Number0 <= wParam&&wParam <= B_Number9)
{
CString str,str2, number_str;
number_str.Format(L"%d", wParam - B_Number0);
if (m_step == 0)
{
m_edit1.GetWindowTextW(str2);
}
else if (m_step == 1)
{
m_edit1.GetWindowTextW(str);
m_step = 0;
m_value = _wtof(str);
}
m_edit1.SetWindowTextW(str2 + number_str);
}
// TODO: 여기에 특수화된 코드를 추가 및/또는 기본 클래스를 호출합니다.
return CDialogEx::OnCommand(wParam, lParam);
}
void CMy0819Dlg::OnBnClickedPlus()
{
CString str, str2, str3, omg;
double m_value_two;
m_value_two = _ttoi(str2);
m_edit1.GetWindowTextW(str2);
m_edit1.GetWindowTextW(omg);
m_value_two = _wtof(omg);
m_count++;
if (m_count == 1)
{
m_value = m_value_two;
}
else
{
M_Operate(m_value_two);
}
m_operater_flag = 0;
m_step = 1;
m_edit1.GetWindowTextW(str2);
m_edit2.GetWindowTextW(str);
m_edit2.SetWindowTextW(str + str2 + "+");
omg.Format(L"%f", m_value);
omg.TrimRight(L"0");
omg.TrimRight(L".");
m_edit1.SetWindowTextW(omg);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
void CMy0819Dlg::OnBnClickedMinus()
{
CString str, str2, omg;
double m_value_two;
m_value_two = _ttoi(str2);
m_edit1.GetWindowTextW(str2);
m_edit1.GetWindowTextW(omg);
m_value_two = _wtof(omg);
m_count++;
if (m_count == 1)
{
m_value = m_value_two;
}
else
{
M_Operate(m_value_two);
}
m_operater_flag = 1;
m_step = 1;
m_edit1.GetWindowTextW(str2);
m_edit2.GetWindowTextW(str);
m_edit2.SetWindowTextW(str + str2 + "-");
omg.Format(L"%f", m_value);
omg.TrimRight(L"0");
omg.TrimRight(L".");
m_edit1.SetWindowTextW(omg);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
void CMy0819Dlg::OnBnClickedDivi()
{
CString str, str2, omg;
double m_value_two;
m_value_two = _ttoi(str2);
m_edit1.GetWindowTextW(str2);
m_edit1.GetWindowTextW(omg);
m_value_two = _wtof(omg);
m_count++;
if (m_count == 1)
{
m_value = m_value_two;
}
else
{
M_Operate(m_value_two);
}
m_operater_flag = 2;
m_step = 1;
m_edit1.GetWindowTextW(str2);
m_edit2.GetWindowTextW(str);
m_edit2.SetWindowTextW(str + str2 + "*");
omg.Format(L"%f", m_value);
omg.TrimRight(L"0");
omg.TrimRight(L".");
m_edit1.SetWindowTextW(omg);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
void CMy0819Dlg::OnBnClickedMult()
{
CString str, str2, omg;
double m_value_two;
m_value_two = _ttoi(str2);
m_edit1.GetWindowTextW(str2);
m_edit1.GetWindowTextW(omg);
m_value_two = _wtof(omg);
m_count++;
if (m_count == 1)
{
m_value = m_value_two;
}
else
{
M_Operate(m_value_two);
}
m_operater_flag = 3;
m_step = 1;
m_edit1.GetWindowTextW(str2);
m_edit2.GetWindowTextW(str);
m_edit2.SetWindowTextW(str + str2 + "/");
omg.Format(L"%f", m_value);
omg.TrimRight(L"0");
omg.TrimRight(L".");
m_edit1.SetWindowTextW(omg);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
void CMy0819Dlg::OnBnClickedEq()
{
CString str;
double m_value_two;
m_value_two = _wtof(str);
m_edit1.GetWindowTextW(str);
m_edit1.GetWindowTextW(str);
m_value_two = _wtof(str);
M_Operate(m_value_two);
m_count = 0;
str.Format(L"%f", m_value);
str.TrimRight(L"0");
str.TrimRight(L".");
m_edit1.SetWindowTextW(str);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
void CMy0819Dlg::M_Operate(double m_value_two)
{
CString str, m_value_two2;
m_edit1.GetWindowTextW(m_value_two2);
double m_value_two1;
m_value_two1 = _ttoi(m_value_two2);
switch (m_operater_flag)
{
case 0:
m_value += m_value_two;
break;
case 1:
m_value -= m_value_two;
break;
case 2:
m_value *= m_value_two;
break;
case 3:
if (m_value_two != 0)
{
m_value /= m_value_two;
}
else
{
m_value = 0;
}
break;
}
}
void CMy0819Dlg::OnBnClickedClear()
{
UpdateData(TRUE);
m_edit1.SetWindowTextW(L" ");
m_edit2.SetWindowTextW(L" ");
m_value = 0;
m_step = 0;
m_operater_flag = 0;
m_count = 0;
UpdateData(FALSE);
// TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다.
}
BOOL CMy0819Dlg::PreTranslateMessage(MSG* pMsg)
{
// TODO: 여기에 특수화된 코드를 추가 및/또는 기본 클래스를 호출합니다.
switch (pMsg->message)
{
case WM_KEYDOWN:
switch (pMsg->wParam)
{
case VK_NUMPAD0: B_Number0; break;
case VK_NUMPAD1: B_Number1; break;
case VK_NUMPAD2: B_Number2; break;
case VK_NUMPAD3: B_Number3; break;
case VK_NUMPAD4: B_Number4; break;
case VK_NUMPAD5: B_Number5; break;
case VK_NUMPAD6: B_Number6; break;
case VK_NUMPAD7: B_Number7; break;
case VK_NUMPAD8: B_Number8; break;
case VK_NUMPAD9: B_Number9; break;
case VK_ADD: OnBnClickedPlus(); break;
case VK_SUBTRACT: OnBnClickedMinus(); break;
case VK_DIVIDE: OnBnClickedDivi(); break;
case VK_MULTIPLY: OnBnClickedMult(); break;
case VK_RETURN: OnBnClickedEq(); break; return true;
}
break;
}
return CDialogEx::PreTranslateMessage(pMsg);
}
#mfc로 만든 프로그램