guixwind.c

来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 1,469 行 · 第 1/3 页

C
1,469
字号
        }
    }
    hmenu = NULL;
    if( !GUISetupStruct( wnd, info, &pos, &size, parent_hwnd, &hmenu ) ) {
        return( FALSE );
    }
    if( !(wnd->style & GUI_NOFRAME) ) {
        if( info->text ) {
            style |= WS_CAPTION;
            wnd->flags |= HAS_CAPTION;
        } else {
            style |= WS_BORDER;
        }
    }
    if( info->style & GUI_RESIZEABLE ) {
        style |= WS_THICKFRAME;
    }
    if( info->scroll & GUI_HSCROLL ) {
        style |= WS_HSCROLL;
    }
    if( info->scroll & GUI_VSCROLL ) {
        style |= WS_VSCROLL;
    }
    if( wnd->flags & HAS_CAPTION ) {
        if( info->style & GUI_MAXIMIZE ) {
            style |= WS_MAXIMIZEBOX;
        }
        if( info->style & GUI_MINIMIZE ) {
            style |= WS_MINIMIZEBOX;
        }
        if( info->style & GUI_SYSTEM_MENU ) {
            style |= WS_SYSMENU;
        }
    } else {
        wnd->style &= ~(GUI_MAXIMIZE|GUI_MINIMIZE|GUI_SYSTEM_MENU);
        info->style &= ~(GUI_MAXIMIZE|GUI_MINIMIZE|GUI_SYSTEM_MENU);
    }
    if( info->style & GUI_POPUP ) {
        style |= WS_POPUP;
    }
    if( info->style & GUI_DIALOG_LOOK ) {
        style |= GUI_DIALOG_STYLE;
        class_name = GUIDialogClass;
    } else {
        class_name = GUIClass;
    }

    wnd->font = GUIGetSystemFont();
    GUIInitHint( wnd, info->num_menus, info->menu, MENU_HINT );
    GUISetGUIHint( wnd );
    wmcreateinfo.size = sizeof(wmcreate_info);
    wmcreateinfo.wnd  = wnd;
    wmcreateinfo.info = info;
    hwnd        = NULLHANDLE;
    frame_hwnd  = NULLHANDLE;
    client_hwnd = NULLHANDLE;
#ifdef __OS2_PM__
    /* frame */
    flags = FCF_TASKLIST | FCF_NOBYTEALIGN;
    frame_flags = 0;
    if( wnd->flags & HAS_CAPTION ) {
        flags |= FCF_TITLEBAR;
        if( info->style & GUI_SYSTEM_MENU ) {
            flags |= FCF_SYSMENU;
        }
        if( info->style & GUI_MAXIMIZE ) {
            flags |= FCF_MAXBUTTON;
        }
        if( info->style & GUI_MINIMIZE ) {
            flags |= FCF_MINBUTTON;
        }
        flags |= FCF_BORDER;
    } else {
        if( !(wnd->style & GUI_NOFRAME) ) {
            flags |= FCF_BORDER;
            frame_flags |= FS_BORDER;
        }
        wnd->style &= ~(GUI_MAXIMIZE|GUI_MINIMIZE|GUI_SYSTEM_MENU);
        info->style &= ~(GUI_MAXIMIZE|GUI_MINIMIZE|GUI_SYSTEM_MENU);
    }
    if( info->style & GUI_RESIZEABLE ) {
        flags |= FCF_SIZEBORDER;
    }
    if( parent_hwnd == HWND_DESKTOP ) {
        if( info->num_menus > 0 ) {
            //flags |= FCF_MENU;
        }
    }
    if( info->scroll & GUI_HSCROLL ) {
        flags |= FCF_HORZSCROLL;
    }
    if( info->scroll & GUI_VSCROLL ) {
        flags |= FCF_VERTSCROLL;
    }
    if( info->style & GUI_DIALOG_LOOK ) {
        flags |= FCF_DLGBORDER;
    }
    if( info->style & GUI_POPUP ) {
        flags |= FCF_NOMOVEWITHOWNER;
    }
    frame_hwnd = WinCreateStdWindow( parent_hwnd, frame_flags | WS_CLIPCHILDREN | WS_CLIPSIBLINGS, &flags,
                                     NULL, info->text,
                                     0, NULL, 0, NULL );
    if( frame_hwnd != NULLHANDLE ) {
        oldFrameProc = _wpi_subclasswindow( frame_hwnd, (WPI_PROC)GUIFrameProc );
        _wpi_setmenu( frame_hwnd, hmenu );
        _wpi_getclientrect( parent_hwnd, &parent_client );
        show_flags = SWP_SIZE | SWP_MOVE;
        WinSetWindowPos( frame_hwnd, HWND_TOP, pos.x, pos.y, size.x, size.y, show_flags );
        hwnd = frame_hwnd;
        if( parent_hwnd == HWND_DESKTOP ) {
            wnd->root_frame = frame_hwnd;
        } else {
            wnd->hwnd_frame = frame_hwnd;
        }
        _wpi_getclientrect( frame_hwnd, &rect );
        client_hwnd = WinCreateWindow( frame_hwnd, class_name, NULL,
                                       WS_VISIBLE | WS_CLIPCHILDREN | WS_CLIPSIBLINGS,
                                       rect.xLeft, rect.yBottom,
                                       rect.xRight-rect.xLeft,
                                       rect.yTop-rect.yBottom,
                                       frame_hwnd, HWND_TOP, FID_CLIENT,
                                       &wmcreateinfo, NULL );
        if( client_hwnd == NULLHANDLE ) {
            WinDestroyWindow( frame_hwnd );
            frame_hwnd = NULL;
            hwnd = NULL;
        }
    }
#else
        hwnd = _wpi_createwindow_ex( WS_EX_NOPARENTNOTIFY,
                   class_name, info->text, style, 0, 0, pos.x,
                   pos.y, size.x, size.y, parent_hwnd, hmenu,
                   GUIMainHInst, &wmcreateinfo, &frame_hwnd );
#endif
    if( hwnd == NULLHANDLE ) {
        return( FALSE );
    }

    GUISetIcon( wnd, info->icon );

    if( info->style & (GUI_INIT_MAXIMIZED|GUI_INIT_MINIMIZED) ) {
        GUISetRedraw( wnd, FALSE );
        if( info->style & GUI_INIT_MAXIMIZED ) {
            GUIMaximizeWindow( wnd );
        } else if( info->style & GUI_INIT_MINIMIZED ) {
            GUIMinimizeWindow( wnd );
        }
        GUISetRedraw( wnd, TRUE );
        if( wnd->style & GUI_INIT_INVISIBLE ) {
            _wpi_showwindow( hwnd, SW_HIDE );
        }
    }

    if( !(wnd->style & GUI_INIT_INVISIBLE ) ) {
        GUIShowWindowNA( wnd );
    }

    return( wnd != NULL );
}

bool SendPointEvent( WPI_PARAM1 wparam, WPI_PARAM2 lparam,
                     gui_window *wnd, gui_event gui_ev, bool force_current )
{
    WPI_POINT   currentpoint;
    gui_point   point;

    if( force_current || !EditControlHasFocus ) {
        wparam = wparam;
        lparam = lparam;
        currentpoint.x = GET_WM_MOUSEMOVE_POSX( wparam, lparam );
        currentpoint.y = GET_WM_MOUSEMOVE_POSY( wparam, lparam );
        if( force_current && ( GUICurrWnd != wnd ) && ( GUICurrWnd != NULL ) ) {
            //wnd = GUICurrWnd;
        }
        currentpoint.y = _wpi_cvtc_y( wnd->hwnd, currentpoint.y );
        _wpi_clienttoscreen( wnd->hwnd, &currentpoint );
        GUIMakeRelative( wnd, &currentpoint, &point );
        GUIEVENTWND( wnd, gui_ev, &point );
        return( TRUE );
    }
    return( FALSE );
}


void GUIResizeBackground( gui_window *wnd, bool force_msg )
{
    WPI_RECT    status;
    int         t_height, s_height;
    GUI_RECTDIM left, top, right, bottom;
    gui_coord   size;

    if( wnd->root == NULLHANDLE ) {
        if( wnd->hwnd != NULLHANDLE ) {
            _wpi_getclientrect( wnd->hwnd, &wnd->hwnd_client );
        }
        return;
    }

    t_height = 0;
    s_height = 0;

    if( ( wnd->toolbar != NULL ) && ( wnd->toolbar->info.is_fixed ) ) {
        t_height = _wpi_getheightrect( wnd->toolbar->fixedrect );
    }

    if( wnd->status != NULLHANDLE ) {
        _wpi_getwindowrect( wnd->status, &status );
        s_height = _wpi_getheightrect( status );
    }

    _wpi_getclientrect( wnd->root_frame, &wnd->root_client );
    _wpi_getrectvalues( wnd->root_client, &left, &top, &right, &bottom );
    bottom -= top;
    right  -= left;
    top = left = 0;

#ifdef __OS2_PM__
    top    += s_height;
    bottom -= t_height;
#else
    top    += t_height;
    bottom -= s_height;
#endif

    /* if the root client is a separate window resize it too */
    _wpi_movewindow( wnd->hwnd, left, top, right - left, bottom - top, TRUE );

    _wpi_getclientrect( wnd->hwnd, &wnd->hwnd_client );

    if( force_msg && ( wnd->flags & SENT_INIT ) ) {
        size.x = right - left;
        size.y = bottom - top;
        GUIScreenToScaleR( &size );
        GUIEVENTWND( wnd, GUI_RESIZE, &size );
    }
}

bool SetFocusToParent( void )
{
    HWND        curr_hwnd;

    // for a reason I do not yet comprehend, the MDI stuff should no longer
    // be a deterent to setting the focus to the top parent
    if( ( GUICurrWnd != NULL ) && !EditControlHasFocus /* && !GUIMDI */ &&
        !( GUICurrWnd->style & GUI_POPUP ) ) {
        curr_hwnd = GUIGetTopParentHWND( GUICurrWnd->hwnd );
        if( GUIGetCtrlWnd( curr_hwnd ) == NULL ) {
            if( _wpi_iswindow( GUIMainHInst, curr_hwnd ) ) {
                if( _wpi_getfocus() != curr_hwnd ) {
                    _wpi_setfocus( curr_hwnd );
                    _wpi_setactivewindow( curr_hwnd );
                    return( TRUE );
                }
            }
        }
    }
    return( FALSE );
}

void GUIDoResize( gui_window *wnd, HWND hwnd, gui_coord *size )
{
    hwnd = hwnd;
    if( wnd->style & GUI_CHANGEABLE_FONT ) {
        GUIEnableSysMenuItem( wnd, GUI_CHANGE_FONT, TRUE );
    }
    if( wnd->hwnd != NULLHANDLE ) {
        GUIResizeStatus( wnd );
        GUIResizeBackground( wnd, FALSE );
    }
    GUIResizeToolBar( wnd );
    if( !(wnd->flags & NEEDS_RESIZE_REDRAW ) ) {
        wnd->old_rows = wnd->num_rows;
    }
    GUISetRowCol( wnd, size );
    wnd->flags |= NEEDS_RESIZE_REDRAW;
    GUISetScroll( wnd );
    if( wnd->flags & SENT_INIT ) {
        GUIScreenToScaleR( size );
        GUIEVENTWND( wnd, GUI_RESIZE, size );
    }
    GUIInvalidatePaintHandles( wnd );
#ifdef __OS2_PM__
    //_wpi_invalidaterect( hwnd, NULL, TRUE );
#endif
    GUIInvalidateResize( wnd );
    //_wpi_updatewindow( hwnd );
}

static void ProcessMenu( gui_window *wnd, WORD param )
{
    if( param < GUI_LAST_MENU_ID ) {
        GUIEVENTWND( wnd, GUI_CLICKED, &param );
    } else {
        switch( param ) {
        case GUI_CHANGE_FONT :
            GUIChangeFont( wnd );
            break;
        }
    }
}

/*
 * CheckDoFront -- if not implementing MDI, always bring to front.  If MDI,
 *                 only bring the window to the front if it's not the MDI
 *                 parent.
 */

static void CheckDoFront( gui_window *wnd )
{
    if( !GUIMDI || wnd->parent  ) {
        GUIBringToFront( wnd );
    }
}

static void NextWndToFront( HWND hwnd )
{
    HWND        next;
    gui_window  *wnd;

    next = _wpi_getnextwindow( hwnd );
    if( next != NULLHANDLE ) {
        wnd = GUIGetWindow( next );
        if( wnd != NULL ) {
            GUIBringToFront( wnd );
        }
    }
}

static WPI_POINT prevpoint = { -1, -1 };

/*  Procedure to control windows */

WPI_MRESULT CALLBACK GUIWindowProc( HWND hwnd, WPI_MSG msg, WPI_PARAM1 wparam,
                                    WPI_PARAM2 lparam )
{
    gui_window          *wnd;
    gui_window          *root;
    WORD                param;
    WPI_POINT           currentpoint;
    gui_coord           point;
    gui_coord           size;
    WPI_MRESULT         ret;
    WPI_MINMAXINFO _W386FAR *info;
    WPI_RECT            rect;
    HWND                parent;
    CREATESTRUCT FAR    *lpcs;
    wmcreate_info _W386FAR *wmcreateinfo;
    gui_create_info     *createinfo;
    bool                use_defproc;
    unsigned            control_id;
    HWND                win;
#ifndef __OS2_PM__
    gui_key_state       key_state;
#endif

    root = NULL;
    ret = 0L;
    use_defproc = FALSE;
    if( msg == WM_CREATE ) {
        lpcs = ( CREATESTRUCT FAR * )MK_FP32( (void *)lparam );
        wmcreateinfo = (wmcreate_info _W386FAR *)MK_FP32( _wpi_getcreateparms( lpcs ) );
        if ( wmcreateinfo != NULL ) {
            wnd = wmcreateinfo->wnd;
            createinfo = wmcreateinfo->info;
            if( wnd->hwnd == NULLHANDLE ) {
#ifdef __OS2_PM__
                if( wnd->root_frame != NULLHANDLE && wnd->root == NULLHANDLE ) {
                    wnd->root = hwnd;
                } else {
                    wnd->hwnd = hwnd;
                }
#else
                if( _wpi_getparent( hwnd ) == HWND_DESKTOP ) {
                    wnd->root       = hwnd;
                    wnd->root_frame = hwnd;
                } else {
                    wnd->hwnd       = hwnd;
                    wnd->hwnd_frame = hwnd;
                }
#endif
            }
            DoSetWindowLong( hwnd, wnd );
        }
    }
    wnd = GUIGetWindow( hwnd );
    if( wnd == NULL ) {
        return( _wpi_defwindowproc( hwnd, msg, wparam, lparam ) );
    }

    if( GUIMDIProcessMessage( wnd, hwnd, msg, wparam, lparam, &ret ) ) {
        return( ret );
    }

    if( wnd->root == hwnd ) {
        /* message for root window */
        switch( msg ) {
        case WM_CREATE :
#ifdef __OS2_PM__
            wnd->root_pinfo.normal_pres =
                _wpi_createos2normpres( GUIMainHInst, hwnd );
#endif
            _wpi_getclientrect( wnd->root_frame, &wnd->root_client );
            if( CreateBackgroundWnd( wnd, createinfo ) ) {
                return( 0 );
            }
            return( (WPI_MRESULT)WPI_ERROR_ON_CREATE );
            break;
        case WM_DESTROY :
            wnd->flags |= DOING_DESTROY;
            GUICloseToolBar( wnd );
            //ret =  _wpi_defwindowproc( hwnd, msg, wparam, lparam );
            //wnd->root       = NULL;
            //wnd->root_frame = NULL;
            return( 0L );
        }
    } else if( ( wnd->root != NULLHANDLE ) && ( hwnd == wnd->hwnd ) ) {
        /* message for container window */
        switch( msg ) {
        case WM_SIZE :
            if( !_wpi_isiconic( _wpi_getframe( hwnd ) ) ) {
                size.x = _wpi_getwmsizex( wparam, lparam );
                size.y = _wpi_getwmsizey( wparam, lparam );
                GUIDoResize( wnd, hwnd, &size );
            }
            return( _wpi_defwindowproc( hwnd, msg, wparam, lparam ) );
            break;
        case WM_MOVE :
            return( _wpi_defwindowproc( hwnd, msg, wparam, lparam ) );
            break;
        case WM_VSCROLL :
        case WM_HSCROLL :
        case WM_CLOSE :
            return( _wpi_defwindowproc( hwnd, msg, wparam, lparam ) );
            break;
        }
    }

    switch( msg ) {
    case WM_CREATE :
#ifdef __OS2_PM__
        wnd->hwnd_pinfo.normal_pres =
            _wpi_createos2normpres( GUIMainHInst, hwnd );
#endif
        NumWindows++; // even if -1 is returned, window will get WM_DESTROY
        win = GUIGetParentFrameHWND( wnd );
        if( (  wnd->root_frame != NULLHANDLE ) ||
            ( createinfo->style & GUI_POPUP ) ) {
            if( !GUIAddToSystemMenu( wnd, win, 0, NULL,
                                     createinfo->style ) ) {
                return( (WPI_MRESULT)WPI_ERROR_ON_CREATE );
            }
        } else {
            if( !GUIAddToSystemMenu( wnd, win, createinfo->num_menus,
                                createinfo->menu, createinfo->style ) ) {
                return( (WPI_MRESULT)WPI_ERROR_ON_CREATE );
            }
        }
        _wpi_getclientrect( hwnd, &wnd->hwnd_client );
        GUISetRowCol( wnd, NULL );
        if( ( hwnd == wnd->hwnd ) && ( wnd->root == NULLHANDLE ) ) {
            GUIMDINewWindow( hwnd );
        }
        if( GUIEVENTWND( wnd, GUI_INIT_WINDOW, NULL ) ) {
            wnd->flags |= SENT_INIT;
            GUISetScroll( wnd ); /* initalize scroll ranges */
            GUIBringToFront( wnd );
            return( 0 );
        } else {
            /* app decided not to create window */
            return( (WPI_MRESULT)WPI_ERROR_ON_CREATE );
        }
        break;
#if defined(__NT__) || defined(WILLOWS)
    case WM_CTLCOLORBTN :
    case WM_CTLCOLORDLG :
    //case WM_CTLCOLORLISTBOX :
    case WM_CTLCOLORSTATIC :
    //case WM_CTLCOLOREDIT :
        ret = (WPI_MRESULT)GUICtl3dCtlColorEx( msg, wparam, lparam );
        if( ret == (HBRUSH)NULL ) {
            SetBkColor( (HDC)wparam, GetNearestColor( (HDC)wparam,
                        GUIGetBack( wnd, GUI_BACKGROUND ) ) );
            ret = (WPI_MRESULT)wnd->bk_brush;
        }
        return( ret );
#elif !defined( __OS2_PM__ )
    case WM_CTLCOLOR :
        switch( HIWORD( lparam ) ) {
        case CTLCOLOR_BTN :

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?