X-Git-Url: http://git.cinelerra-gg.org/git/?p=goodguy%2Fhistory.git;a=blobdiff_plain;f=cinelerra-5.1%2Fguicast%2Fbcwindowbase.C;h=1ef0d5939cc8e697ae71ffe3a94b2bbcdc894b3b;hp=2ab508f2438ed85a1b3dd327fec95a611a33b487;hb=04031cc2a664d2a6d9d2a37954c55cc68742d78c;hpb=b55798fc64eee00c6fab3b4763e791befb7275f9 diff --git a/cinelerra-5.1/guicast/bcwindowbase.C b/cinelerra-5.1/guicast/bcwindowbase.C index 2ab508f2..1ef0d593 100644 --- a/cinelerra-5.1/guicast/bcwindowbase.C +++ b/cinelerra-5.1/guicast/bcwindowbase.C @@ -46,6 +46,7 @@ #include "mutex.h" #include "sizes.h" #include "vframe.h" +#include "workarounds.h" #ifdef HAVE_GL #include @@ -61,7 +62,6 @@ #include #include - BC_ResizeCall::BC_ResizeCall(int w, int h) { this->w = w; @@ -181,10 +181,12 @@ BC_WindowBase::~BC_WindowBase() for( int i=sizeof(xfont)/sizeof(xfont[0]); --i>=0; ) XFreeFont(display, this->*xfont[i]); -// past bug in X caused XRenderExtensionInfo to be damaged -// if this is done here. left to be done in XCloseDisplay by Xlib. -// works in more modern systems, and needed for leak testing. -#if defined(HAVE_XFT) && defined(VALGRIND) +#ifdef HAVE_XFT +// prevents a bug when Xft closes with unrefd fonts + FcPattern *defaults = FcPatternCreate(); + FcPatternAddInteger(defaults, "maxunreffonts", 0); + XftDefaultSet(display, defaults); + static void *BC_WindowBase::*xft_font[] = { &BC_WindowBase::smallfont_xft, &BC_WindowBase::mediumfont_xft, @@ -197,7 +199,7 @@ BC_WindowBase::~BC_WindowBase() }; for( int i=sizeof(xft_font)/sizeof(xft_font[0]); --i>=0; ) { XftFont *xft = (XftFont *)(this->*xft_font[i]); - if( xft ) XftFontClose (display, xft); + if( xft ) xftFontClose (display, xft); } #endif finit_im(); @@ -255,6 +257,7 @@ int BC_WindowBase::initialize() keys_return[0] = 0; is_deleting = 0; window_lock = 0; + resend_event_window = 0; x = 0; y = 0; w = 0; @@ -388,12 +391,8 @@ int BC_WindowBase::create_window(BC_WindowBase *parent_window, const char *title #endif id = get_resources()->get_id(); - int need_lock = 0; if(parent_window) top_level = parent_window->top_level; - if( top_level ) { // need this to avoid deadlock with Xlib's locks - need_lock = 1; - lock_window("BC_WindowBase::create_window"); - } + if( top_level ) lock_window("BC_WindowBase::create_window"); get_resources()->create_window_lock->lock("BC_WindowBase::create_window"); #ifdef HAVE_LIBXXF86VM @@ -443,6 +442,7 @@ int BC_WindowBase::create_window(BC_WindowBase *parent_window, const char *title if( shm_completion_event < 0 ) shm_completion_event = ShmCompletion + XShmGetEventBase(display); #endif + lock_window("BC_WindowBase::create_window 1"); screen = DefaultScreen(display); rootwin = RootWindow(display, screen); @@ -546,6 +546,7 @@ int BC_WindowBase::create_window(BC_WindowBase *parent_window, const char *title PropModeReplace, (unsigned char *)&XGroupLeader, true); } init_im(); + set_icon(get_resources()->default_icon); } #ifdef HAVE_LIBXXF86VM @@ -636,7 +637,7 @@ int BC_WindowBase::create_window(BC_WindowBase *parent_window, const char *title if(!hidden) show_window(); } get_resources()->create_window_lock->unlock(); - if(need_lock) unlock_window(); + unlock_window(); return 0; } @@ -996,7 +997,7 @@ locking_message = event->xclient.message_type; done = 1; } else { // We currently use X marshalling for xatom events, we can switch to something else later - recieve_custom_xatoms((xatom_event *)ptr); + receive_custom_xatoms((xatom_event *)ptr); } break; @@ -1254,6 +1255,20 @@ locking_message = event->xclient.message_type; case XK_KP_Insert: key_pressed = KPINS; break; case XK_KP_Decimal: case XK_KP_Delete: key_pressed = KPDEL; break; + + case XK_F1: key_pressed = KEY_F1; break; + case XK_F2: key_pressed = KEY_F2; break; + case XK_F3: key_pressed = KEY_F3; break; + case XK_F4: key_pressed = KEY_F4; break; + case XK_F5: key_pressed = KEY_F5; break; + case XK_F6: key_pressed = KEY_F6; break; + case XK_F7: key_pressed = KEY_F7; break; + case XK_F8: key_pressed = KEY_F8; break; + case XK_F9: key_pressed = KEY_F9; break; + case XK_F10: key_pressed = KEY_F10; break; + case XK_F11: key_pressed = KEY_F11; break; + case XK_F12: key_pressed = KEY_F12; break; + case XK_Menu: key_pressed = KPMENU; break; /* menu */ // remote control // above case XK_KP_Enter: key_pressed = KPENTER; break; /* check */ @@ -1323,19 +1338,26 @@ locking_message = event->xclient.message_type; break; case LeaveNotify: - if( cursor_entered && event->xcrossing.window == win ) { - cursor_entered = 0; - } + if( event->xcrossing.mode != NotifyNormal ) break; + cursor_entered = 0; event_win = event->xany.window; dispatch_cursor_leave(); break; case EnterNotify: - if( !cursor_entered && event->xcrossing.window == win ) { - if( !event->xcrossing.focus && get_resources()->grab_input_focus ) { - XSetInputFocus(display, win, RevertToParent, CurrentTime); + if( event->xcrossing.mode != NotifyNormal ) break; + + if( !cursor_entered ) { + for( int i=0; iwin == event->xcrossing.window ) + cursor_entered = 1; } - cursor_entered = 1; + if( !cursor_entered && get_resources()->grab_input_focus && + !event->xcrossing.focus && event->xcrossing.window == win ) { + cursor_entered = 1; + } + if( cursor_entered ) + focus(); } event_win = event->xany.window; cursor_x = event->xcrossing.x; @@ -1351,7 +1373,14 @@ locking_message = event->xclient.message_type; #ifndef SINGLE_THREAD unlock_window(); - if(event) delete event; + if(event) { + if( resend_event_window ) { + resend_event_window->put_event(event); + resend_event_window = 0; + } + else + delete event; + } #else // if(done) completion_lock->unlock(); #endif @@ -1956,7 +1985,7 @@ int BC_WindowBase::arm_repeat(int64_t duration) } #endif -int BC_WindowBase::recieve_custom_xatoms(xatom_event *event) +int BC_WindowBase::receive_custom_xatoms(xatom_event *event) { return 0; } @@ -2343,54 +2372,54 @@ static Mutex xft_init_lock("BC_WindowBase::xft_init_lock", 0); xft_init_lock.lock("BC_WindowBase::init_xft"); if(!(smallfont_xft = (resources.small_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.small_font_xft) : - XftFontOpenName(display, screen, resources.small_font_xft))) ) + xftFontOpenXlfd(display, screen, resources.small_font_xft) : + xftFontOpenName(display, screen, resources.small_font_xft))) ) if(!(smallfont_xft = - XftFontOpenXlfd(display, screen, resources.small_font_xft2))) - smallfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.small_font_xft2))) + smallfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(mediumfont_xft = (resources.medium_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.medium_font_xft) : - XftFontOpenName(display, screen, resources.medium_font_xft))) ) + xftFontOpenXlfd(display, screen, resources.medium_font_xft) : + xftFontOpenName(display, screen, resources.medium_font_xft))) ) if(!(mediumfont_xft = - XftFontOpenXlfd(display, screen, resources.medium_font_xft2))) - mediumfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.medium_font_xft2))) + mediumfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(largefont_xft = (resources.large_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.large_font_xft) : - XftFontOpenName(display, screen, resources.large_font_xft))) ) + xftFontOpenXlfd(display, screen, resources.large_font_xft) : + xftFontOpenName(display, screen, resources.large_font_xft))) ) if(!(largefont_xft = - XftFontOpenXlfd(display, screen, resources.large_font_xft2))) - largefont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.large_font_xft2))) + largefont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(bigfont_xft = (resources.big_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.big_font_xft) : - XftFontOpenName(display, screen, resources.big_font_xft))) ) + xftFontOpenXlfd(display, screen, resources.big_font_xft) : + xftFontOpenName(display, screen, resources.big_font_xft))) ) if(!(bigfont_xft = - XftFontOpenXlfd(display, screen, resources.big_font_xft2))) - bigfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.big_font_xft2))) + bigfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(clockfont_xft = (resources.clock_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.clock_font_xft) : - XftFontOpenName(display, screen, resources.clock_font_xft))) ) - clockfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.clock_font_xft) : + xftFontOpenName(display, screen, resources.clock_font_xft))) ) + clockfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(bold_smallfont_xft = (resources.small_b_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.small_b_font_xft) : - XftFontOpenName(display, screen, resources.small_b_font_xft))) ) - bold_smallfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.small_b_font_xft) : + xftFontOpenName(display, screen, resources.small_b_font_xft))) ) + bold_smallfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(bold_mediumfont_xft = (resources.medium_b_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.medium_b_font_xft) : - XftFontOpenName(display, screen, resources.medium_b_font_xft))) ) - bold_mediumfont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.medium_b_font_xft) : + xftFontOpenName(display, screen, resources.medium_b_font_xft))) ) + bold_mediumfont_xft = xftFontOpenXlfd(display, screen, "fixed"); if(!(bold_largefont_xft = (resources.large_b_font_xft[0] == '-' ? - XftFontOpenXlfd(display, screen, resources.large_b_font_xft) : - XftFontOpenName(display, screen, resources.large_b_font_xft))) ) - bold_largefont_xft = XftFontOpenXlfd(display, screen, "fixed"); + xftFontOpenXlfd(display, screen, resources.large_b_font_xft) : + xftFontOpenName(display, screen, resources.large_b_font_xft))) ) + bold_largefont_xft = xftFontOpenXlfd(display, screen, "fixed"); if( !smallfont_xft || !mediumfont_xft || !largefont_xft || !bigfont_xft || !bold_largefont_xft || !bold_mediumfont_xft || !bold_largefont_xft || @@ -2409,7 +2438,7 @@ xft_init_lock.lock("BC_WindowBase::init_xft"); exit(1); } // _XftDisplayInfo needs a lock. - XftDefaultHasRender(display); + xftDefaultHasRender(display); xft_init_lock.unlock(); #endif // HAVE_XFT } @@ -2862,7 +2891,7 @@ int BC_WindowBase::get_single_text_width(int font, const char *text, int length) #ifdef X_HAVE_UTF8_STRING if(get_resources()->locale_utf8) { - XftTextExtentsUtf8(top_level->display, + xftTextExtentsUtf8(top_level->display, get_xft_struct(font), (const XftChar8 *)text, length, @@ -2871,7 +2900,7 @@ int BC_WindowBase::get_single_text_width(int font, const char *text, int length) else #endif { - XftTextExtents8(top_level->display, + xftTextExtents8(top_level->display, get_xft_struct(font), (const XftChar8 *)text, length, @@ -3431,6 +3460,8 @@ BC_WindowBase::get_xinerama_info(int screen) return 0; } int top_x = get_x(), top_y = get_y(); + if( BC_DisplayInfo::left_border >= 0 ) top_x += BC_DisplayInfo::left_border; + if( BC_DisplayInfo::top_border >= 0 ) top_y += BC_DisplayInfo::top_border; for( int i=0; i= xinerama_info[i].height ) continue; @@ -3441,6 +3472,38 @@ BC_WindowBase::get_xinerama_info(int screen) return 0; } +void BC_WindowBase::get_fullscreen_geometry(int &wx, int &wy, int &ww, int &wh) +{ + XineramaScreenInfo *info = top_level->get_xinerama_info(-1); + if( info ) { + wx = info->x_org; wy = info->y_org; + ww = info->width; wh = info->height; + } + else { + wx = get_screen_x(0, -1); + wy = get_screen_y(0, -1); + int scr_w0 = get_screen_w(0, 0); + int root_w = get_root_w(0); + int root_h = get_root_h(0); + if( root_w > scr_w0 ) { // multi-headed + if( wx >= scr_w0 ) { + // assumes right side is the big one + ww = root_w - scr_w0; + wh = root_h; + } + else { + // use same aspect ratio to compute left height + ww = scr_w0; + wh = (w*root_h) / (root_w-scr_w0); + } + } + else { + ww = root_w; + wh = root_h; + } + } +} + int BC_WindowBase::get_screen_x(int lock_display, int screen) { int result = -1; @@ -3839,17 +3902,27 @@ int BC_WindowBase::match_window(Window win) int BC_WindowBase::get_cursor_over_window() { - if(top_level != this) return top_level->get_cursor_over_window(); - int abs_x, abs_y, win_x, win_y; - unsigned int temp_mask; + unsigned int mask_return; Window root_return, child_return; - int ret = XQueryPointer(display, win, + int ret = XQueryPointer(top_level->display, top_level->rootwin, &root_return, &child_return, &abs_x, &abs_y, - &win_x, &win_y, &temp_mask); - if( ret && child_return == None && win != root_return ) ret = 0; - if( ret && child_return != None ) ret = match_window(child_return); + &win_x, &win_y, &mask_return); + if( ret && child_return == None ) ret = 0; + if( ret && win != child_return ) + ret = top_level->match_window(child_return); +// query pointer can return a window manager window with this top_level as a child +// for kde this can be two levels deep + unsigned int nchildren_return = 0; + Window parent_return, *children_return = 0; + Window top_win = top_level->win; + while( !ret && top_win != top_level->rootwin && top_win != root_return && + XQueryTree(top_level->display, top_win, &root_return, + &parent_return, &children_return, &nchildren_return) ) { + if( children_return ) XFree(children_return); + if( (top_win=parent_return) == child_return ) ret = 1; + } return ret; } @@ -4461,6 +4534,20 @@ void BC_WindowBase::dequeue_events(Window win) event_lock->unlock(); } +int BC_WindowBase::resend_event(BC_WindowBase *window) +{ + if( resend_event_window ) return 1; + resend_event_window = window; + return 0; +} + +#else + +int BC_WindowBase::resend_event(BC_WindowBase *window) +{ + return 1; +} + #endif // SINGLE_THREAD int BC_WindowBase::get_id() @@ -4490,3 +4577,11 @@ void BC_WindowBase::flicker(int n, int ms) set_opaque(); } +void BC_WindowBase::focus() +{ + XWindowAttributes xwa; + XGetWindowAttributes(top_level->display, top_level->win, &xwa); + if( xwa.map_state == IsViewable ) + XSetInputFocus(top_level->display, top_level->win, RevertToParent, CurrentTime); +} +