2

少し問題があります。テキスト(「ABC @」のようなもの)である編集コントロールが必要です。この文字列は、ユーザーが削除できないように編集できないようにする必要があります。ユーザーは、記号「@」の後にのみテキストを入力できる必要があります。編集ボックスでテキストを読み取り専用にする方法を知っています。EM_SETREADONLYメッセージを使用します

//global variables
 #define ID_TEXTBOX 1
 static HWND hwndTextBox;

//in WndProc function
  case WM_CREATE:
    {

      hwndTextBox = CreateWindow(TEXT("EDIT"),TEXT("abc@"),WS_VISIBLE | WS_CHILD | WS_BORDER   ,70,100, 200,25,hWnd,(HMENU)ID_TEXTBOX,NULL,NULL);

      if(!hwndTextBox )
        {
            MessageBox(hWnd,"Failed","Failed",MB_OK);
            return FALSE;
        }

      SendMessage(hwndTextBox,EM_SETREADONLY,TRUE ,NULL);

      break;

    }

しかし、コードは全文を読み取り専用にし、もちろん私の問題を解決しません。

4

2 に答える 2

2

エディット コントロールの代わりにリッチエディット コントロールを使用します。メッセージを使用して、EM_SETCHARFORMAT個々の文字または文字の範囲を「保護」としてマークします。EM_SETEVENTMASKメッセージを使用してEN_PROTECTED、RichEdit からの通知を登録します。こうすることで、ユーザーが何らかの理由で 1 つ以上の保護された文字を変更しようとすると、RichEdit は変更を許可する前に許可を求めます。

于 2012-12-14T22:12:28.500 に答える
2

これはおそらくあなたが探しているものではありませんが、コードのオーバーヘッドが少しあるだけで、必要な機能を模倣している可能性があります。

エディット コントロールをサブクラス化し、WM_CHAR メッセージを介して、エディット ボックスの内容を変更する可能性のあるユーザー入力をキャプチャできます。メッセージがプロシージャによって受信されると、編集ボックスで現在の選択 (つまり、キャレット位置) が検出され、それが最初の 4 文字内のどこかにある場合は、単に変更を許可しません。これは少し大雑把な方法ですが、うまくいくはずです。

アセンブリの例です。申し訳ありませんが、私は C に十分に精通しておらず、C は非常に厄介です :D

    invoke SetWindowLong,hEditBox,GWL_WNDPROC,offset EditProc
    mov DefEditProc,eax
    ...

EditProc proc hWnd:DWORD,uMsg:DWORD,wParam:DWORD,lParam:DWORD
    cmp uMsg,WM_CHAR
    je @WM_CHAR
    cmp uMsg,WM_KEYUP
    je @WM_KEYUP

@DEFAULT:
    invoke CallWindowProc,DefEditProc,hWnd,uMsg,wParam,lParam 
    ret
@EXIT:
    xor eax,eax
    ret

;=============
@WM_KEYUP:
    mov eax,wParam          ; you will need this if you want to process the delete key
    cmp ax,VK_DELETE
    je @VK_DELETE
    jmp @DEFAULT

;=============
@WM_CHAR:
    mov eax,wParam
    cmp ax,VK_BACK          ; this is for the backspace key
    je @BACKSPACE
    cmp ax,VK_0
    jb @EXIT                ; if null is returned, the char will not be passed to the edit box
    cmp ax,VK_9
    ja @EXIT
    jmp @NUMBER

;---
@VK_DELETE:
@NUMBER:
    invoke SendMessage,hWnd,EM_GETSEL,offset start,0        ; the caret position through text selection, we just need the starting position
    cmp start,3
    ja @DEFAULT     ; if the caret is placed somewhere past the 4th charater, allow user input
    jmp @EXIT

;---    
@BACKSPACE:
    invoke SendMessage,hWnd,EM_GETSEL,offset start,0
    cmp start,4
    ja @DEFAULT     ; since you're deleting one character to the left, you need to factor that in for backspace
    jmp @EXIT

EditProc endp

それは非常にカットされています。この例では、数字 (0 ~ 9)、DEL キー、および BACKSPACE キーのみを使用できます。ニーズに合わせて拡張できます。

よろしく

于 2012-12-14T21:30:38.623 に答える