wxMac(Carbon)でのキーボード・テキスト入力のイベント処理の流れ

wxMac(Carbon)でのキーボード・テキスト入力のイベント処理の流れ

wxWidgets 2.8系

src/mac/carbon/app.cpp,toplevel.cpp,window.cppが関係ありそう

window.cpp:

static const EventTypeSpec eventList[] =
{
    (中略)
    { kEventClassTextInput, kEventTextInputUnicodeForKeyEvent } ,
    { kEventClassTextInput, kEventTextInputUpdateActiveInputArea } ,

pascal OSStatus wxMacUnicodeTextEventHandler( EventHandlerCallRef handler , EventRef event , void *data )
{
    (中略)
    switch ( GetEventKind( event ) )
    {
        case kEventTextInputUpdateActiveInputArea :
            {
                (中略)
                    if ( wxTheApp->MacSendCharEvent((wxWindow*)
                                                    focus , message , 0 , when , 0 , 0 , uniChars[pos] ) )
                    {
                        result = noErr ;
                    }
                (中略)
        case kEventTextInputUnicodeForKeyEvent :
            {
                (中略)
                    if ( wxTheApp->MacSendCharEvent((wxWindow*)
                        focus , message , modifiers , when , point.h , point.v , uniChars[pos] ) )
                    {
                        result = noErr ;
                    }
                (中略)

toplevel.cpp:

static const EventTypeSpec eventList[] =
{
    // TODO: remove control related event like key and mouse (except for WindowLeave events)

    { kEventClassKeyboard, kEventRawKeyDown } ,
    { kEventClassKeyboard, kEventRawKeyRepeat } ,
    { kEventClassKeyboard, kEventRawKeyUp } ,
    { kEventClassKeyboard, kEventRawKeyModifiersChanged } ,

    { kEventClassTextInput, kEventTextInputUnicodeForKeyEvent } ,
    { kEventClassTextInput, kEventTextInputUpdateActiveInputArea } ,
kEventClassKeyboardはKeyboardEventHandler、kEventClassTextInputはwindow.cppのwxMacUnicodeTextEventHandlerで処理される。
static pascal OSStatus KeyboardEventHandler( EventHandlerCallRef handler , EventRef event , void *data )
{
    (中略)
    switch ( GetEventKind( event ) )
    {
        case kEventRawKeyRepeat :
        case kEventRawKeyDown :
            {
                (中略)
                if ( /* focus && */ wxTheApp->MacSendKeyDownEvent(
                    focus , message , modifiers , when , point.h , point.v , uniChar[0] ) )
                {
                    result = noErr ;
                }
                wxTheApp->MacSetCurrentEvent( formerEvent , formerHandler ) ;
            }
            break ;

        case kEventRawKeyUp :
            if ( /* focus && */ wxTheApp->MacSendKeyUpEvent(
                focus , message , modifiers , when , point.h , point.v , uniChar[0] ) )
            {
                result = noErr ;
            }
            break ;

        case kEventRawKeyModifiersChanged :
            {
                wxKeyEvent event(wxEVT_KEY_DOWN);
                (中略)
                if ( /* focus && */ (modifiers ^ wxApp::s_lastModifiers ) & (contral|shift|option|cmd)Key )
                {
                    event.m_keyCode = WXK_(CONTRAL|SHIFT|OPTION|COMMAND) ;
                    event.SetEventType( ( modifiers & (contral|shift|option|cmd)Key ) ? wxEVT_KEY_DOWN : wxEVT_KEY_UP ) ;
                    focus->GetEventHandler()->ProcessEvent( event ) ;
                }

app.cpp

bool wxApp::MacSendKeyDownEvent( wxWindow* focus , long keymessage , long modifiers , long when , short wherex , short wherey , wxChar uniChar )
{
    if ( !focus )
        return false ;

    bool handled;
    wxKeyEvent event(wxEVT_KEY_DOWN) ;
    MacCreateKeyEvent( event, focus , keymessage , modifiers , when , wherex , wherey , uniChar ) ;

    handled = focus->GetEventHandler()->ProcessEvent( event ) ;
    if ( handled && event.GetSkipped() )
        handled = false ;

#if wxUSE_ACCEL
    (中略)
#endif // wxUSE_ACCEL

    return handled ;
}

bool wxApp::MacSendKeyUpEvent( wxWindow* focus , long keymessage , long modifiers , long when , short wherex , short wherey , wxChar uniChar )
{
    if ( !focus )
        return false ;

    bool handled;
    wxKeyEvent event( wxEVT_KEY_UP ) ;
    MacCreateKeyEvent( event, focus , keymessage , modifiers , when , wherex , wherey , uniChar ) ;
    handled = focus->GetEventHandler()->ProcessEvent( event ) ;

    return handled ;
}

bool wxApp::MacSendCharEvent( wxWindow* focus , long keymessage , long modifiers , long when , short wherex , short wherey , wxChar uniChar )
{
    if ( !focus )
        return false ;

    wxKeyEvent event(wxEVT_CHAR) ;
    MacCreateKeyEvent( event, focus , keymessage , modifiers , when , wherex , wherey , uniChar ) ;
    long keyval = event.m_keyCode ;

    bool handled = false ;

    wxTopLevelWindowMac *tlw = focus->MacGetTopLevelWindow() ;

    if (tlw)
    {
        event.SetEventType( wxEVT_CHAR_HOOK );
        handled = tlw->GetEventHandler()->ProcessEvent( event );
        if ( handled && event.GetSkipped() )
            handled = false ;
    }

    if ( !handled )
    {
        event.SetEventType( wxEVT_CHAR );
        event.Skip( false ) ;
        handled = focus->GetEventHandler()->ProcessEvent( event ) ;
    }

    if ( !handled && (keyval == WXK_TAB) )
    {
        (中略)
    }

    // backdoor handler for default return and command escape
    if ( !handled && (!focus->IsKindOf(CLASSINFO(wxControl) ) || !focus->MacCanFocus() ) )
    {
        (中略)
    }
    return handled ;
}

NewTSMDocumentを呼んでいないのにkEventTextInputUpdateActiveInputAreaって飛んでくるのか? このコード書いた人はkEventTextInputUpdateActiveInputAreaが何か分かってるのか?

タグ:

+ タグ編集
  • タグ:
最終更新:2010年04月25日 20:14