C++ 13日目:ルートボタン

この章では、ルートボタンがおされたときの処理の説明をしていきます

処理概要

ルートボタンは、入力中の数字のルートを計算するときに使用します
このボタンを押すことで、入力した数字のルートを計算します
表示ディスプレイに表示されている数字のルートを計算し結果を表示します
場合に応じて、current_bufferやstack[0]の値の修正も行います

ルートボタンが押された位置で以下のことを考慮します

ケース1. ディスプレイの表示が空

ACボタンが押されたあとや電卓の起動時の状態をさします
(ディスプレイ、current_buffer、stack[0]、stack[1]がどれも空文字)
このときは、何も処理を実行しません

ケース2. 演算子を指定した直後

四則演算や=を押された直後、ディスプレイには演算結果が表示され、stack[0]にも演算結果が入っています
しかし、current_bufferは空文字です
このときは、ディスプレイの表示およびstack[0]の値のルート計算を実行します

前提条件

ルートボタンが押される直前の電卓は、処理概要および「考慮すること」に対して、それぞれどのような状態の場合があるかを考えてみます

演算子の表示部分数値の表示部分current_bufferstack[0]状態の説明
ACボタン直後の状態
数値数値左辺値を入力している状態
―、+、×、÷、=数値数値演算子が押された後の状態
―、+、×、÷、=数値数値数値右辺値を入力している状態

処理内容

ルートボタンのイベント処理フロー

  1. 現在入力中の数値の符号を反転
    • もしcurrent_bufferに値が入っている場合(=数値入力中)、current_bufferの値のルート計算を実行する
    • 更新したcurrent_bufferの値をディスプレイに表示する
  2. 計算結果の符号を反転
    • もしcurrent_bufferが空で、stack[0]に値が入っている場合(=計算結果が表示されている状態)、stack[0]の値のルート計算を実行する
    • 更新したstack[0]の値をディスプレイに表示する
  3. 何もしない
    • 上記以外の場合(例: 起動直後、ACボタン直後)は、何もしない

実装

イベントハンドラの設定

VisualC++の機能を使用して戻るボタンのイベントハンドラを作成します
作成されたイベントハンドラはafx_msg void OnBnClickedButtonRoot();です
その後、イベントハンドラに処理を記述していきます

1. MyCalculatorDlg.h

class CMyCalculatorDlg : public CDialogEx
{
// コンストラクション
public:
    CMyCalculatorDlg(CWnd* pParent = nullptr);  // 標準コンストラクター

// ダイアログ データ
#ifdef AFX_DESIGN_TIME
    enum { IDD = IDD_MYCALCULATOR_DIALOG };
#endif

    protected:
    virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV サポート


// 実装
private:
    void AddEditBoxText(LPCTSTR lpText);
    void setEditBoxText(LPCTSTR lpText);
    void initVariable();
    void clickOperatorButton(LPCTSTR lpText); 
    void setOperatorText(LPCTSTR lpText); 
    void clearCurrentBuffer();
    double calculate();   
    void HandleNumberClick(LPCTSTR number_char);
    void disableButton();    
    void enableButton();
    double IsNumberAndConvert(const TCHAR* lpText);  
    CString ConvertDoubleToCString(double result); 

    CString current_buffer = _T("");
    CString last_operator = _T("");
    CString stack[2] = {_T(""),_T("")};

protected:
    HICON m_hIcon;

    // 生成された、メッセージ割り当て関数
    virtual BOOL OnInitDialog();
    afx_msg void OnSysCommand(UINT nID, LPARAM lParam);
    afx_msg void OnPaint();
    afx_msg HCURSOR OnQueryDragIcon();
    DECLARE_MESSAGE_MAP()
public:
    afx_msg void OnBnClickedButtonAc();
    afx_msg void OnBnClickedButtonZero();
    afx_msg void OnBnClickedButtonOne();
    afx_msg void OnBnClickedButtonTwo();
    afx_msg void OnBnClickedButtonThree();
    afx_msg void OnBnClickedButtonFour();
    afx_msg void OnBnClickedButtonFive();
    afx_msg void OnBnClickedButtonSix();
    afx_msg void OnBnClickedButtonSeven();
    afx_msg void OnBnClickedButtonEight();
    afx_msg void OnBnClickedButtonNine();
    afx_msg void OnBnClickedButtonPlus();  
    afx_msg void OnBnClickedButton1Minus(); 
    afx_msg void OnBnClickedButtonMulti();  
    afx_msg void OnBnClickedButtonDiv();  
    afx_msg void OnBnClickedButtonEqual();  
    afx_msg void OnBnClickedButtonDecimal();
    afx_msg void OnBnClickedButtonBack();
    afx_msg void OnBnClickedButtonSign();
    afx_msg void OnBnClickedButtonRoot();  // ルートボタン
};

2. MyCalculatorDlg.cpp

void CMyCalculatorDlg::OnBnClickedButtonRoot()
{
    // TODO: ここにコントロール通知ハンドラー コードを追加します。
    try {
        double val;
        if (current_buffer.IsEmpty())
        {
            if (stack[0].IsEmpty()) {
                return;
            }
            double val = IsNumberAndConvert(stack[0]);
            val = sqrt(val);
            stack[0] = ConvertDoubleToCString(val);
            setEditBoxText(stack[0]);
        }
        else {
            double val = IsNumberAndConvert(current_buffer);
            val = sqrt(val);
            current_buffer = ConvertDoubleToCString(val);
            setEditBoxText(current_buffer);
        }
    }
    catch (const std::invalid_argument& e) {
        CString str(e.what());
        setEditBoxText(str);
        disableButton();
    }

}

以上が、√(ルート)ボタンを実装したプログラムです
これで、**フェーズ1**、**フェーズ2**の実装が完了しました
次回は、テストと実装のまとめを行います

コメント

この記事へのコメントはありません。

関連記事

Java 応用編 4日目

C++ 発展編 2日目

C言語 応用編 ~7日目~

PAGE TOP