Annotation of mstools/ole20/samples/dispcalc/dispcalc.cpp, revision 1.1.1.1

1.1       root        1: /*** 
                      2: *dispcalc.cpp
                      3: *
                      4: *  Copyright (C) 1992, Microsoft Corporation.  All Rights Reserved.
                      5: *  Information Contained Herein Is Proprietary and Confidential.
                      6: *
                      7: *Purpose:
                      8: *  This module implements the basic user interface and arithmetic
                      9: *  functionality of the IDispatch calculator. 
                     10: *
                     11: *  The implementation of IDispatch it via aggregation with an
                     12: *  instance of the "standard" IDispatch implementation, which is
                     13: *  initialized with a DispTypeInfo constructed from an INTERFACEDATA
                     14: *  description.
                     15: *
                     16: *Implementation Notes:
                     17: *
                     18: *****************************************************************************/
                     19: 
                     20: #include <windows.h>
                     21: #include <ole2.h>
                     22: #if !defined(WIN32)
                     23: #include <olenls.h>
                     24: #endif
                     25: #include <dispatch.h>
                     26: 
                     27: #include "resource.h"
                     28: #include "dispcalc.h"
                     29: 
                     30: 
                     31: /***
                     32: *CCalc *CCalc::Create(void)
                     33: *Purpose:
                     34: *  Create an instance of the IDispatch calculator, build a
                     35: *  TypeInfo that describes the exposed functionality and
                     36: *  aggregate with an instance of CStdDispatch that has been
                     37: *  initialized with this TypeInfo.
                     38: *
                     39: *Entry:
                     40: *  None
                     41: *
                     42: *Exit:
                     43: *  return value = CCalc*, NULL if the creation failed.
                     44: *
                     45: ***********************************************************************/
                     46: CCalc FAR*
                     47: CCalc::Create()
                     48: {
                     49:     HRESULT hresult;
                     50:     CCalc FAR* pcalc;
                     51:     ITypeInfo FAR* ptinfo;
                     52:     IUnknown FAR* punkStdDisp;
                     53: extern INTERFACEDATA NEAR g_idataCCalc;
                     54: 
                     55: 
                     56:     if((pcalc = new FAR CCalc()) == NULL)
                     57:       return NULL;
                     58: 
                     59:     // Build a TypeInfo for the functionality on this object that
                     60:     // is being exposing for external programmability.
                     61:     //
                     62:     hresult = CreateDispTypeInfo(
                     63:       &g_idataCCalc, LOCALE_SYSTEM_DEFAULT, &ptinfo);
                     64:     if(hresult != NOERROR)
                     65:       goto LError0;
                     66: 
                     67:     // Create and aggregate with an instance of the default
                     68:     // implementation of IDispatch that is initialized with our
                     69:     // TypeInfo.
                     70:     //
                     71:     hresult = CreateStdDispatch(
                     72:       pcalc,                           // controlling unknown
                     73:       &pcalc->m_arith,                 // vtable* to dispatch on
                     74:       ptinfo,
                     75:       &punkStdDisp);
                     76: 
                     77:     ptinfo->Release();
                     78: 
                     79:     if(hresult != NOERROR)
                     80:       goto LError0;
                     81: 
                     82:     pcalc->m_punkStdDisp = punkStdDisp;
                     83: 
                     84:     return pcalc;
                     85: 
                     86: LError0:;
                     87:     pcalc->Release();
                     88: 
                     89:     return NULL;
                     90: }
                     91: 
                     92: 
                     93: //---------------------------------------------------------------------
                     94: //                        IUnknown methods
                     95: //---------------------------------------------------------------------
                     96: 
                     97: 
                     98: STDMETHODIMP
                     99: CCalc::QueryInterface(REFIID riid, void FAR* FAR* ppv)
                    100: {
                    101:     if(riid == IID_IUnknown){
                    102:       *ppv = this;
                    103:     }else
                    104:     if(riid == IID_IDispatch){
                    105:       return m_punkStdDisp->QueryInterface(riid, ppv);
                    106:     }else
                    107:       return ResultFromScode(E_NOINTERFACE);
                    108: 
                    109:     AddRef();
                    110:     return NOERROR;
                    111: }
                    112: 
                    113: 
                    114: STDMETHODIMP_(ULONG)
                    115: CCalc::AddRef()
                    116: {
                    117:     return ++m_refs;
                    118: }
                    119: 
                    120: 
                    121: STDMETHODIMP_(ULONG)
                    122: CCalc::Release()
                    123: {
                    124:     if(--m_refs == 0){
                    125:       if(m_punkStdDisp != NULL)
                    126:        m_punkStdDisp->Release();
                    127:       PostQuitMessage(0);
                    128:       delete this;
                    129:       return 0;
                    130:     }
                    131:     return m_refs;
                    132: }
                    133: 
                    134: 
                    135: //---------------------------------------------------------------------
                    136: //                       Arithmetic features
                    137: //---------------------------------------------------------------------
                    138: 
                    139: 
                    140: STDMETHODIMP_(void)
                    141: CCalc::CArith::Clear()
                    142: {
                    143:     m_opnd = 0;
                    144:     m_accum = 0;
                    145:     m_op = OP_NONE;
                    146:     m_state = STATE_LOPND;
                    147: }
                    148: 
                    149: STDMETHODIMP_(void)
                    150: CCalc::CArith::put_Accum(long l)
                    151: {
                    152:     m_accum = l;
                    153: }
                    154: 
                    155: 
                    156: STDMETHODIMP_(long)
                    157: CCalc::CArith::get_Accum()
                    158: {
                    159:     return m_accum;
                    160: }
                    161: 
                    162: 
                    163: STDMETHODIMP_(void)
                    164: CCalc::CArith::put_Opnd(long l)
                    165: {
                    166:     m_opnd = l;
                    167: }
                    168: 
                    169: 
                    170: STDMETHODIMP_(long)
                    171: CCalc::CArith::get_Opnd()
                    172: {
                    173:     return m_opnd;
                    174: }
                    175: 
                    176: 
                    177: STDMETHODIMP_(void)
                    178: CCalc::CArith::put_Op(short op)
                    179: {
                    180:     m_op = op;
                    181: }
                    182: 
                    183: 
                    184: STDMETHODIMP_(short)
                    185: CCalc::CArith::get_Op()
                    186: {
                    187:     return m_op;
                    188: }
                    189: 
                    190: 
                    191: STDMETHODIMP_(BOOL)
                    192: CCalc::CArith::Eval()
                    193: {
                    194:     if(m_op == OP_NONE)
                    195:       return FALSE;
                    196: 
                    197:     switch(m_op){
                    198:     case OP_PLUS:
                    199:       m_accum += m_opnd;
                    200:       break;
                    201:     case OP_MINUS:
                    202:       m_accum -= m_opnd;
                    203:       break;
                    204:     case OP_MULT:
                    205:       m_accum *= m_opnd;
                    206:       break;
                    207:     case OP_DIV:
                    208:       m_accum = (m_opnd == 0) ? 0 : (m_accum / m_opnd);
                    209:       break;
                    210:     default:
                    211:       // ASSERT(UNREACHED);
                    212:       return FALSE;
                    213:       
                    214:     }
                    215: 
                    216:     m_state = STATE_EVAL;
                    217: 
                    218:     return TRUE;
                    219: }
                    220: 
                    221: 
                    222: //---------------------------------------------------------------------
                    223: //                       User Interface features
                    224: //---------------------------------------------------------------------
                    225: 
                    226: 
                    227: /***
                    228: *void CCalc::CArith::Display()
                    229: *Purpose:
                    230: *  Display the contents of the register currently being edited.
                    231: *
                    232: *Entry:
                    233: *  None
                    234: *
                    235: *Exit:
                    236: *  None
                    237: *
                    238: ***********************************************************************/
                    239: STDMETHODIMP_(void)
                    240: CCalc::CArith::Display()
                    241: {
                    242:     VARIANT var;
                    243: 
                    244:     V_VT(&var) = VT_I4;
                    245:     V_I4(&var) = (m_state == STATE_ROPND) ? m_opnd : m_accum;
                    246:     VariantChangeType(&var, &var, 0, VT_BSTR);
                    247:     SetDlgItemText(m_pcalc->m_hwnd, IDC_DISPLAY, V_BSTR(&var));
                    248:     VariantClear(&var);
                    249: }
                    250: 
                    251: 
                    252: STDMETHODIMP_(BOOL)
                    253: CCalc::CArith::Button(BSTR bstrButton)
                    254: {
                    255:     int i, button;
                    256: 
                    257: static struct {
                    258:     char ch;
                    259:     int idc;
                    260: } NEAR rgIdcOfCh[] = {
                    261:       { '+', IDC_PLUS   }
                    262:     , { '-', IDC_MINUS  }
                    263:     , { '*', IDC_MULT   }
                    264:     , { '/', IDC_DIV    }
                    265:     , { 'C', IDC_CLEAR  }
                    266:     , { 'c', IDC_CLEAR  }
                    267:     , { '=', IDC_EQUALS }
                    268:     , { '0', IDC_ZERO   }
                    269:     , { '1', IDC_ONE    }
                    270:     , { '2', IDC_TWO    }
                    271:     , { '3', IDC_THREE  }
                    272:     , { '4', IDC_FOUR   }
                    273:     , { '5', IDC_FIVE   }
                    274:     , { '6', IDC_SIX    }
                    275:     , { '7', IDC_SEVEN  }
                    276:     , { '8', IDC_EIGHT  }
                    277:     , { '9', IDC_NINE   }
                    278:     , { -1 , -1         }
                    279: };
                    280: 
                    281:     // if the string is more that 1 character long, then we know its wrong.
                    282:     if(SysStringLen(bstrButton) > 1)
                    283:       return FALSE;
                    284: 
                    285:     // translate button string into control ID
                    286:     for(i = 0;; ++i){
                    287:       if(rgIdcOfCh[i].ch == -1)
                    288:        return FALSE;
                    289:       if(rgIdcOfCh[i].ch == bstrButton[0]){
                    290:        button = rgIdcOfCh[i].idc;
                    291:        break;
                    292:       }
                    293:     }
                    294: 
                    295:     return ButtonPush(button);
                    296: }
                    297: 
                    298: 
                    299: // the following method is internal, and not exposed for programmability
                    300: BOOL
                    301: CCalc::CArith::ButtonPush(int button)
                    302: {
                    303:     if(button >= IDC_ZERO && button <= IDC_NINE){
                    304: 
                    305:       long lVal = button - IDC_ZERO;
                    306: 
                    307:       switch(m_state){
                    308:       case STATE_EVAL:
                    309:        m_accum = lVal;
                    310:        m_state = STATE_LOPND;
                    311:        break;
                    312:       case STATE_OP:
                    313:        m_opnd = lVal;
                    314:        m_state = STATE_ROPND;
                    315:        break;
                    316:       case STATE_LOPND:
                    317:        m_accum = (m_accum * 10) + lVal;
                    318:        break;
                    319:       case STATE_ROPND:
                    320:        m_opnd  = (m_opnd * 10) + lVal;
                    321:        break;
                    322:       }
                    323: 
                    324:     }else if(button >= IDC_PLUS && button <= IDC_DIV){
                    325: 
                    326:       if(m_state == STATE_LOPND){
                    327:        m_opnd  = m_accum;
                    328:        m_state = STATE_OP;
                    329:        m_op    = button - IDC_PLUS + OP_PLUS;
                    330:       }
                    331: 
                    332:     }else if(button == IDC_EQUALS){
                    333: 
                    334:       if(m_state > STATE_LOPND)
                    335:         Eval();
                    336: 
                    337:     }else if (button == IDC_CLEAR){
                    338: 
                    339:       Clear();
                    340: 
                    341:     }
                    342: 
                    343:     SendMessage(m_pcalc->m_hwnd, BM_SETSTATE, 1, 0L);
                    344:     SendMessage(m_pcalc->m_hwnd, BM_SETSTATE, 0, 0L);
                    345: 
                    346:     Display();
                    347: 
                    348:     return TRUE;
                    349: }
                    350: 
                    351: /***
                    352: *void CCalc::CArith::Quit()
                    353: *Purpose:
                    354: *
                    355: *Entry:
                    356: *  None
                    357: *
                    358: *Exit:
                    359: *  None
                    360: *
                    361: ***********************************************************************/
                    362: STDMETHODIMP_(void)
                    363: CCalc::CArith::Quit()
                    364: {
                    365:     PostQuitMessage(0);
                    366: }
                    367: 
                    368: 
                    369: //---------------------------------------------------------------------
                    370: //                      The CCalc Class Factory
                    371: //---------------------------------------------------------------------
                    372: 
                    373: 
                    374: IClassFactory FAR*
                    375: CCalcCF::Create()
                    376: {
                    377:     return new FAR CCalcCF();
                    378: }
                    379: 
                    380: 
                    381: STDMETHODIMP
                    382: CCalcCF::QueryInterface(REFIID riid, void FAR* FAR* ppv)
                    383: {
                    384:     if(riid == IID_IUnknown || riid == IID_IClassFactory){
                    385:       AddRef();
                    386:       *ppv = this;
                    387:       return NOERROR;
                    388:     }
                    389:     return ResultFromScode(E_NOINTERFACE);
                    390: }
                    391: 
                    392: 
                    393: STDMETHODIMP_(ULONG)
                    394: CCalcCF::AddRef()
                    395: {
                    396:     return ++m_refs;
                    397: }
                    398: 
                    399: 
                    400: STDMETHODIMP_(ULONG)
                    401: CCalcCF::Release()
                    402: {
                    403:     if(--m_refs == 0){
                    404:       delete this;
                    405:       return 0;
                    406:     }
                    407:     return m_refs;
                    408: }
                    409: 
                    410: 
                    411: STDMETHODIMP
                    412: CCalcCF::CreateInstance(
                    413:     IUnknown FAR* punkOuter,
                    414:     REFIID riid,
                    415:     void FAR* FAR* ppv)
                    416: {
                    417: extern CCalc FAR* g_pcalc;
                    418: 
                    419:     return g_pcalc->QueryInterface(riid, ppv);
                    420: }
                    421: 
                    422: 
                    423: STDMETHODIMP
                    424: CCalcCF::LockServer(BOOL fLock)
                    425: {
                    426:     return NOERROR;
                    427: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.