不是工程类型里面的“控制台应用程序”而是像……像WinXP的cmd.exe那样的,形式当然是自定义。暂时还没个思路,以前偶尔看到一个外国资料,讲的是关于建立类似Doom,Quake,CS等游戏的console,后来又找不到了(其实内容也不多)。现在没什么思路。请教中

解决方案 »

  1.   

    搞一个SDI
    去掉菜单和工具条
    设置View为EditView
    字体颜色为RGB(255,255,255);
    背景色为RGB(0,0,0);
    隐藏光标
    然后....:)
      

  2.   

    甚至用一个Edit box就可以的~也许重要的不是这些……
    也许我应该发到别的区~呵呵。
      

  3.   

    入门时的一个win32 直接就OK了,哈,不过是把背景换成黑色,不就像dos了
      

  4.   

    一个console ,有提示符、输出的内容、键盘输入过的内容,键盘正在输入的内容如何控制,光标不跑到不应该去的地方,就如cmd.exe里面那样?
      

  5.   

     一下,最近正在做一个项目用到这样的界面元素,原来用CEdit派生过一个,改进中,成功的话一定贴上源码。
      

  6.   

    重载CEdit,然后自己写一些键盘消息的控制代码,目前基本功能实现了,还需要调试,争取明天搞定贴上来。
      

  7.   

    本来早想帖出来的,结果出差几天没上成网~~我的方法是从CEdit派生出一个名称为ConsoleEdit的类实现控制台方式输入,基本功能已经调试成功,帖出全部代码欢迎大家提出宝贵意见,以后会陆续改进^_^//////////////////////////////////////////////////////////////////////////
    // ConsoleEdit.h
    class ConsoleEdit : public CEdit {
        DECLARE_DYNAMIC(ConsoleEdit)public:
        ConsoleEdit();
        virtual ~ConsoleEdit();    BOOL CreateConsoleEdit(CWnd *pParent, UINT nID, CRect rect, 
            BOOL b3DFrame = FALSE,
            CString lpPrompt = "->");
        int xprintf(const CString& str);
        int xscanf(const char * strFormat, ...);
        int xgets(char * str);
        CString SetPrompt(const CString& lpPrompt);
        CString getCommand() const { return m_strCmd; }
        CString getPrompt() const { return m_strPrompt; }    // Default command callback interface.
        virtual void OnCommand();protected:
        afx_msg int  OnCreate(LPCREATESTRUCT lpCreateStruct);
        afx_msg void OnContextMenu(CWnd*, CPoint);
        afx_msg void OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags);
        afx_msg void OnChar(UINT nChar, UINT nRepCnt, UINT nFlags);
        DECLARE_MESSAGE_MAP()protected:
        virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
        void         OnReturnKeyPressed();
        CString      GetInput();
        CString      GetSelText();
        int          GetStringWidth(const CString& str);
        void         simLeftBtnClick();
        void         Append(const CString& str);private:
        int     m_cxChar;
        int     m_cyChar;
        int     m_cyLine;
        CPoint  m_ptCaretPos;
        CString m_strCmd;
        CString m_strPrompt;
    };
      

  8.   

    #include "ConsoleEdit.h"//////////////////////////////////////////////////////////////////////////
    // ConsoleEdit class member function.
    IMPLEMENT_DYNAMIC(ConsoleEdit, CEdit)BEGIN_MESSAGE_MAP(ConsoleEdit, CEdit)
        ON_WM_CHAR()
        ON_WM_KEYDOWN()
        ON_WM_CREATE()
        ON_WM_CONTEXTMENU()
        ON_WM_PAINT()
    END_MESSAGE_MAP()ConsoleEdit::ConsoleEdit() : m_strCmd("") , m_strPrompt("->") {
    }ConsoleEdit::~ConsoleEdit(){}int ConsoleEdit::OnCreate(LPCREATESTRUCT lpCreateStruct) {
        if (CEdit::OnCreate(lpCreateStruct) == -1)
            return -1;    TEXTMETRIC tm;
        CDC *pDC = GetDC();    pDC->GetTextMetrics(&tm);
        m_cxChar = tm.tmAveCharWidth;
        m_cyChar = tm.tmHeight;
        m_cyLine = tm.tmHeight + tm.tmExternalLeading;    Append(m_strPrompt);    ReleaseDC(pDC);    ShowScrollBar(SB_HORZ);    return 0;
    }void ConsoleEdit::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags) {
        CPoint pt = GetCaretPos();
        switch (nChar)
        {
        case VK_LEFT:
            if (pt.x <= GetStringWidth(m_strPrompt))
                return;
            break;
        case VK_RIGHT:
            break;
        case VK_HOME:
        case VK_END:
        case VK_DOWN:
        case VK_UP:
            return;
        case VK_DELETE:
            if (pt.y < m_ptCaretPos.y || 
                pt.x <= GetStringWidth(m_strPrompt))
                return;        if (GetSelText().Find(_T("\r\n")) >= 0)
                return;
            break;
        }    CEdit::OnKeyDown(nChar, nRepCnt, nFlags);
    }void ConsoleEdit::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags) {
        m_strCmd = GetInput();
        CPoint pt = GetCaretPos();
        switch (nChar)
        {
        case VK_RETURN:
            if (pt.y < m_ptCaretPos.y || 
                pt.x <= GetStringWidth(m_strPrompt))
                simLeftBtnClick();        OnCommand();        m_strCmd.Empty();
            Append(CString("\n"));
            Append(m_strPrompt);        return;
            break;    case VK_BACK:
            if (m_strCmd.GetLength() <= 0)
                return;        if (pt.y < m_ptCaretPos.y || 
                pt.x <= GetStringWidth(m_strPrompt))
                return;        if (GetSelText().Find(_T("\r\n")) >= 0)
                return;
            break;    default:
            if (pt.y < m_ptCaretPos.y || 
                pt.x <= GetStringWidth(m_strPrompt))
                simLeftBtnClick();        if (m_strCmd.GetLength() >= 130)
                return;
        }    CEdit::OnChar(nChar, nRepCnt, nFlags);
    }void ConsoleEdit::Append(const CString& str) {
        xprintf((LPCTSTR)str);    simLeftBtnClick();
        m_ptCaretPos = GetCaretPos();
    }CString ConsoleEdit::GetInput(void) {
        CString strText;
        int iLine = 1;    char chBuffer[256];
        int  len = 0;
        len = GetLine(GetLineCount() - 1, (LPTSTR)chBuffer, 256); 
        chBuffer[len] = '\0';
        strText = CString(chBuffer) + strText;    strText.Delete(0, m_strPrompt.GetLength());    return strText;
    }CString ConsoleEdit::GetSelText(void) {
        CString strText;
        DWORD dwSel = GetSel();    HIWORD(dwSel);
        LOWORD(dwSel);    GetWindowText(strText);
        strText.Delete(0, LOWORD(dwSel));
        strText = strText.Left(HIWORD(dwSel) - LOWORD(dwSel));
        
        return strText;
    }int ConsoleEdit::GetStringWidth(const CString& str) {
        CDC *pDC = GetDC();    int tmp = pDC->GetTextExtent(str).cx;    ReleaseDC(pDC);    return tmp;
    }void ConsoleEdit::simLeftBtnClick(void) {
        SendMessage(WM_VSCROLL, SB_BOTTOM, NULL);    CRect rc;
        GetClientRect(rc);    char chBuf[256];
        int len = 0;
        len = GetLine(GetLineCount() - 1, (LPTSTR)chBuf, 256);
        chBuf[len] = '\0';    CPoint pt;
        pt.x = GetStringWidth(chBuf);
        pt.y = rc.bottom;    DWORD lParam = 0;
        lParam |= pt.y;
        lParam <<= 16;
        lParam |= pt.x;    SendMessage(WM_LBUTTONDOWN, MK_LBUTTON, (LPARAM)lParam);
        SendMessage(WM_LBUTTONUP, MK_LBUTTON, (LPARAM)lParam);
    }BOOL ConsoleEdit::PreCreateWindow(CREATESTRUCT& cs) {
        // TODO: Add your specialized code here and/or call the base class
        cs.style &= ~ES_WANTRETURN;
        cs.style |= WS_VSCROLL | ES_MULTILINE | ES_AUTOVSCROLL | ES_AUTOHSCROLL;    return CEdit::PreCreateWindow(cs);
    }void ConsoleEdit::OnContextMenu(CWnd* /*pWnd*/, CPoint /*point*/) {
        // TODO: Add your message handler code here
        // Disable the context menu
        // Do nothing here...
    }UINT defaultOnEnterEvent(LPVOID lpParam) {
        return 0;
    }BOOL ConsoleEdit::CreateConsoleEdit(CWnd *pParent,
                                        UINT nID,
                                        CRect rect,
                                        BOOL b3DFrame /*=FALSE*/,
                                        CString lpPrompt /*=_T("->")*/
                                        ) {
        if (lpPrompt == "")
            m_strPrompt.Format(_T("%s"), _T("->"));
        else
            m_strPrompt = lpPrompt;    Create(WS_CHILD | WS_VISIBLE | WS_VSCROLL | ES_MULTILINE |
            ES_AUTOVSCROLL | ES_AUTOHSCROLL, rect, pParent, nID);    if (b3DFrame)
            ModifyStyleEx(0, WS_EX_CLIENTEDGE, SWP_DRAWFRAME);    return 0;
    }int ConsoleEdit::xprintf(const CString& str) {
        int newLineCount = 0;
        for (int i = 0; i < str.GetLength(); i++)
            if (str[i] == '\n')
                newLineCount++;    char *pBuf = new char[str.GetLength() + newLineCount + 1];
        int i = 0, j = 0;
        for (; i < str.GetLength(); i++) {
            if (str[i] == '\n') 
                pBuf[j++] = '\r';
            pBuf[j++] = (char)str[i];
        }
        pBuf[j] = '\0';
        ReplaceSel((LPCTSTR)pBuf);    delete []pBuf;    return j;
    }int ConsoleEdit::xscanf(const char * strFormat, ...) {
        return 0;
    }int ConsoleEdit::xgets(char *str) {
        strcpy(str, (LPCTSTR)m_strCmd);    return (int)strlen(str);
    }CString ConsoleEdit::SetPrompt(const CString& lpPrompt) {
        CString prePrompt = m_strPrompt;
        m_strPrompt = lpPrompt; 
        m_strCmd.Empty();    //Append((LPCTSTR)m_strPrompt);    return prePrompt;
    }// Default command interface.
    void ConsoleEdit::OnCommand() {
        xprintf(m_strCmd);
    }
      

  9.   

    今天改进了一些功能,增加了doskey功能接口。
      

  10.   

    这个问题很难回答了,实际上我做的只是一个类似CEdit的控件,当你的程序构造出这个控件后,程序的运行依赖于windows app的消息循环了,如果我的控件提供阻塞输入方式的话,你的程序也就被阻塞了,我做了一个完整的控制台功能的应用程序,类似vs2005的命令窗口功能,但是抱歉无法完全贴上来(公司规定)。