1 /* 2 * Copyright (c) 1996, 2016, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 #include "awt_Toolkit.h" 27 #include "awt_Frame.h" 28 #include "awt_MenuBar.h" 29 #include "awt_Dialog.h" 30 #include "awt_IconCursor.h" 31 #include "awt_Win32GraphicsDevice.h" 32 #include "ComCtl32Util.h" 33 34 #include <windowsx.h> 35 36 #include <java_lang_Integer.h> 37 #include <sun_awt_windows_WEmbeddedFrame.h> 38 #include <sun_awt_windows_WEmbeddedFramePeer.h> 39 40 41 /* IMPORTANT! Read the README.JNI file for notes on JNI converted AWT code. 42 */ 43 44 /***********************************************************************/ 45 // Struct for _SetState() method 46 struct SetStateStruct { 47 jobject frame; 48 jint state; 49 }; 50 // Struct for _SetMaximizedBounds() method 51 struct SetMaximizedBoundsStruct { 52 jobject frame; 53 jint x, y; 54 jint width, height; 55 }; 56 // Struct for _SetMenuBar() method 57 struct SetMenuBarStruct { 58 jobject frame; 59 jobject menubar; 60 }; 61 62 // Struct for _SetIMMOption() method 63 struct SetIMMOptionStruct { 64 jobject frame; 65 jstring option; 66 }; 67 // Struct for _SynthesizeWmActivate() method 68 struct SynthesizeWmActivateStruct { 69 jobject frame; 70 jboolean doActivate; 71 }; 72 // Struct for _NotifyModalBlocked() method 73 struct NotifyModalBlockedStruct { 74 jobject frame; 75 jobject peer; 76 jobject blockerPeer; 77 jboolean blocked; 78 }; 79 // Information about thread containing modal blocked embedded frames 80 struct BlockedThreadStruct { 81 int framesCount; 82 HHOOK mouseHook; 83 HHOOK modalHook; 84 }; 85 86 87 // Communication with plugin control 88 89 // The value must be the same as in AxControl.h 90 #define WM_AX_REQUEST_FOCUS_TO_EMBEDDER (WM_USER + 197) 91 92 static bool SetFocusToPluginControl(HWND hwndPlugin); 93 94 /************************************************************************ 95 * AwtFrame fields 96 */ 97 98 jfieldID AwtFrame::handleID; 99 100 jfieldID AwtFrame::undecoratedID; 101 jmethodID AwtFrame::getExtendedStateMID; 102 jmethodID AwtFrame::setExtendedStateMID; 103 104 jmethodID AwtFrame::activateEmbeddingTopLevelMID; 105 jfieldID AwtFrame::isEmbeddedInIEID; 106 107 Hashtable AwtFrame::sm_BlockedThreads("AWTBlockedThreads"); 108 109 /************************************************************************ 110 * AwtFrame methods 111 */ 112 113 AwtFrame::AwtFrame() { 114 m_parentWnd = NULL; 115 menuBar = NULL; 116 m_isEmbedded = FALSE; 117 m_isEmbeddedInIE = FALSE; 118 m_isLightweight = FALSE; 119 m_ignoreWmSize = FALSE; 120 m_isMenuDropped = FALSE; 121 m_isInputMethodWindow = FALSE; 122 m_isUndecorated = FALSE; 123 m_imeTargetComponent = NULL; 124 m_actualFocusedWindow = NULL; 125 m_iconic = FALSE; 126 m_zoomed = FALSE; 127 m_maxBoundsSet = FALSE; 128 m_forceResetZoomed = FALSE; 129 130 isInManualMoveOrSize = FALSE; 131 grabbedHitTest = 0; 132 } 133 134 AwtFrame::~AwtFrame() 135 { 136 } 137 138 void AwtFrame::Dispose() 139 { 140 AwtWindow::Dispose(); 141 } 142 143 LPCTSTR AwtFrame::GetClassName() { 144 return AWT_FRAME_WINDOW_CLASS_NAME; 145 } 146 147 /* 148 * Create a new AwtFrame object and window. 149 */ 150 AwtFrame* AwtFrame::Create(jobject self, jobject parent) 151 { 152 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 153 if (env->EnsureLocalCapacity(1) < 0) { 154 return NULL; 155 } 156 157 PDATA pData; 158 HWND hwndParent = NULL; 159 AwtFrame* frame = NULL; 160 jclass cls = NULL; 161 jclass inputMethodWindowCls = NULL; 162 jobject target = NULL; 163 164 try { 165 target = env->GetObjectField(self, AwtObject::targetID); 166 JNI_CHECK_NULL_GOTO(target, "target", done); 167 168 if (parent != NULL) { 169 JNI_CHECK_PEER_GOTO(parent, done); 170 { 171 AwtFrame* parent = (AwtFrame *)pData; 172 hwndParent = parent->GetHWnd(); 173 } 174 } 175 176 frame = new AwtFrame(); 177 178 { 179 /* 180 * A variation on Netscape's hack for embedded frames: the client 181 * area of the browser is a Java Frame for parenting purposes, but 182 * really a Windows child window 183 */ 184 BOOL isEmbeddedInstance = FALSE; 185 BOOL isEmbedded = FALSE; 186 cls = env->FindClass("sun/awt/EmbeddedFrame"); 187 188 if (cls) { 189 isEmbeddedInstance = env->IsInstanceOf(target, cls); 190 } else { 191 throw std::bad_alloc(); 192 } 193 INT_PTR handle; 194 if (isEmbeddedInstance) { 195 handle = static_cast<INT_PTR>(env->GetLongField(target, AwtFrame::handleID)); 196 if (handle != 0) { 197 isEmbedded = TRUE; 198 } 199 } 200 frame->m_isEmbedded = isEmbedded; 201 202 BOOL isLightweight = FALSE; 203 cls = env->FindClass("sun/awt/LightweightFrame"); 204 if (cls) { 205 isLightweight = env->IsInstanceOf(target, cls); 206 } else { 207 throw std::bad_alloc(); 208 } 209 frame->m_isLightweight = isLightweight; 210 211 if (isEmbedded) { 212 hwndParent = (HWND)handle; 213 214 // JDK-8056915: Handle focus communication between plugin and frame 215 frame->m_isEmbeddedInIE = IsEmbeddedInIE(hwndParent); 216 if (frame->m_isEmbeddedInIE) { 217 env->SetBooleanField(target, isEmbeddedInIEID, JNI_TRUE); 218 } 219 220 RECT rect; 221 ::GetClientRect(hwndParent, &rect); 222 //Fix for 6328675: SWT_AWT.new_Frame doesn't occupy client area under JDK6 223 frame->m_isUndecorated = true; 224 /* 225 * Fix for BugTraq ID 4337754. 226 * Initialize m_peerObject before the first call 227 * to AwtFrame::GetClassName(). 228 */ 229 frame->m_peerObject = env->NewGlobalRef(self); 230 frame->RegisterClass(); 231 DWORD exStyle = WS_EX_NOPARENTNOTIFY; 232 233 if (GetRTL()) { 234 exStyle |= WS_EX_RIGHT | WS_EX_LEFTSCROLLBAR; 235 if (GetRTLReadingOrder()) 236 exStyle |= WS_EX_RTLREADING; 237 } 238 239 frame->m_hwnd = ::CreateWindowEx(exStyle, 240 frame->GetClassName(), TEXT(""), 241 WS_CHILD | WS_CLIPCHILDREN, 242 0, 0, 243 rect.right, rect.bottom, 244 hwndParent, NULL, 245 AwtToolkit::GetInstance().GetModuleHandle(), 246 NULL); 247 frame->LinkObjects(env, self); 248 frame->SubclassHWND(); 249 250 // Update target's dimensions to reflect this embedded window. 251 ::GetClientRect(frame->m_hwnd, &rect); 252 ::MapWindowPoints(frame->m_hwnd, hwndParent, (LPPOINT)&rect, 2); 253 254 env->SetIntField(target, AwtComponent::xID, rect.left); 255 env->SetIntField(target, AwtComponent::yID, rect.top); 256 env->SetIntField(target, AwtComponent::widthID, 257 rect.right-rect.left); 258 env->SetIntField(target, AwtComponent::heightID, 259 rect.bottom-rect.top); 260 frame->InitPeerGraphicsConfig(env, self); 261 AwtToolkit::GetInstance().RegisterEmbedderProcessId(hwndParent); 262 } else if (isLightweight) { 263 frame->m_isUndecorated = true; 264 frame->m_peerObject = env->NewGlobalRef(self); 265 frame->RegisterClass(); 266 267 DWORD exStyle = 0; 268 DWORD style = WS_POPUP; 269 270 frame->CreateHWnd(env, L"", 271 style, 272 exStyle, 273 0, 0, 0, 0, 274 0, 275 NULL, 276 ::GetSysColor(COLOR_WINDOWTEXT), 277 ::GetSysColor(COLOR_WINDOWFRAME), 278 self); 279 } else { 280 jint state = env->CallIntMethod(self, AwtFrame::getExtendedStateMID); 281 DWORD exStyle; 282 DWORD style; 283 284 // for input method windows, use minimal decorations 285 inputMethodWindowCls = env->FindClass("sun/awt/im/InputMethodWindow"); 286 if (inputMethodWindowCls == NULL) { 287 throw std::bad_alloc(); 288 } 289 290 if (env->IsInstanceOf(target, inputMethodWindowCls)) { 291 //for below-the-spot composition window, use no decoration 292 if (env->GetBooleanField(target, AwtFrame::undecoratedID) == JNI_TRUE){ 293 exStyle = 0; 294 style = WS_POPUP|WS_CLIPCHILDREN; 295 frame->m_isUndecorated = TRUE; 296 } else { 297 exStyle = WS_EX_PALETTEWINDOW; 298 style = WS_CLIPCHILDREN; 299 } 300 frame->m_isInputMethodWindow = TRUE; 301 } else if (env->GetBooleanField(target, AwtFrame::undecoratedID) == JNI_TRUE) { 302 exStyle = 0; 303 style = WS_POPUP | WS_SYSMENU | WS_CLIPCHILDREN | 304 WS_MAXIMIZEBOX | WS_MINIMIZEBOX; 305 if (state & java_awt_Frame_ICONIFIED) { 306 frame->setIconic(TRUE); 307 } 308 frame->m_isUndecorated = TRUE; 309 } else { 310 exStyle = WS_EX_WINDOWEDGE; 311 style = WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN; 312 if (state & java_awt_Frame_ICONIFIED) { 313 frame->setIconic(TRUE); 314 } 315 } 316 317 if (GetRTL()) { 318 exStyle |= WS_EX_RIGHT | WS_EX_LEFTSCROLLBAR; 319 if (GetRTLReadingOrder()) 320 exStyle |= WS_EX_RTLREADING; 321 } 322 323 jint x = env->GetIntField(target, AwtComponent::xID); 324 jint y = env->GetIntField(target, AwtComponent::yID); 325 jint width = env->GetIntField(target, AwtComponent::widthID); 326 jint height = env->GetIntField(target, AwtComponent::heightID); 327 328 frame->CreateHWnd(env, L"", 329 style, 330 exStyle, 331 0, 0, 0, 0, 332 hwndParent, 333 NULL, 334 ::GetSysColor(COLOR_WINDOWTEXT), 335 ::GetSysColor(COLOR_WINDOWFRAME), 336 self); 337 /* 338 * Reshape here instead of during create, so that a 339 * WM_NCCALCSIZE is sent. 340 */ 341 frame->Reshape(x, y, width, height); 342 } 343 } 344 } catch (...) { 345 env->DeleteLocalRef(target); 346 env->DeleteLocalRef(cls); 347 env->DeleteLocalRef(inputMethodWindowCls); 348 throw; 349 } 350 351 done: 352 env->DeleteLocalRef(target); 353 env->DeleteLocalRef(cls); 354 env->DeleteLocalRef(inputMethodWindowCls); 355 356 return frame; 357 } 358 359 /* 360 * Returns true if the frame is embedded into Internet Explorer. 361 * The function checks the class name of the parent window of the embedded frame. 362 */ 363 BOOL AwtFrame::IsEmbeddedInIE(HWND hwndParent) 364 { 365 const char *pluginClass = "Java Plug-in Control Window"; 366 #define PARENT_CLASS_BUFFER_SIZE 64 367 char parentClass[PARENT_CLASS_BUFFER_SIZE]; 368 369 return (::GetClassNameA(hwndParent, parentClass, PARENT_CLASS_BUFFER_SIZE) > 0) 370 && (strncmp(parentClass, pluginClass, PARENT_CLASS_BUFFER_SIZE) == 0); 371 } 372 373 374 LRESULT AwtFrame::ProxyWindowProc(UINT message, WPARAM wParam, LPARAM lParam, MsgRouting &mr) 375 { 376 LRESULT retValue = 0L; 377 378 AwtComponent *focusOwner = NULL; 379 AwtComponent *imeTargetComponent = NULL; 380 381 // IME and input language related messages need to be sent to a window 382 // which has the Java input focus 383 switch (message) { 384 case WM_IME_STARTCOMPOSITION: 385 case WM_IME_ENDCOMPOSITION: 386 case WM_IME_COMPOSITION: 387 case WM_IME_SETCONTEXT: 388 case WM_IME_NOTIFY: 389 case WM_IME_CONTROL: 390 case WM_IME_COMPOSITIONFULL: 391 case WM_IME_SELECT: 392 case WM_IME_CHAR: 393 case WM_IME_REQUEST: 394 case WM_IME_KEYDOWN: 395 case WM_IME_KEYUP: 396 case WM_INPUTLANGCHANGEREQUEST: 397 case WM_INPUTLANGCHANGE: 398 if (message == WM_IME_STARTCOMPOSITION) { 399 SetImeTargetComponent(sm_focusOwner); 400 } 401 imeTargetComponent = AwtComponent::GetComponent(GetImeTargetComponent()); 402 if (imeTargetComponent != NULL && 403 imeTargetComponent != this) // avoid recursive calls 404 { 405 retValue = imeTargetComponent->WindowProc(message, wParam, lParam); 406 mr = mrConsume; 407 } 408 if (message == WM_IME_ENDCOMPOSITION) { 409 SetImeTargetComponent(NULL); 410 } 411 break; 412 case WM_SETFOCUS: 413 if (sm_inSynthesizeFocus) break; // pass it up the WindowProc chain 414 415 if (!sm_suppressFocusAndActivation) { 416 if (IsLightweightFrame() || IsEmbeddedFrame()) { 417 AwtSetActiveWindow(); 418 } 419 } 420 mr = mrConsume; 421 break; 422 case WM_KILLFOCUS: 423 if (sm_inSynthesizeFocus) break; // pass it up the WindowProc chain 424 425 if (!sm_suppressFocusAndActivation) { 426 if (IsLightweightFrame() || IsEmbeddedFrame()) { 427 HWND oppositeToplevelHWnd = AwtComponent::GetTopLevelParentForWindow((HWND)wParam); 428 if (oppositeToplevelHWnd != AwtComponent::GetFocusedWindow()) { 429 AwtWindow::SynthesizeWmActivate(FALSE, GetHWnd(), NULL); 430 } 431 } 432 } else if (sm_restoreFocusAndActivation) { 433 if (AwtComponent::GetFocusedWindow() != NULL) { 434 AwtWindow *focusedWindow = (AwtWindow*)GetComponent(AwtComponent::GetFocusedWindow()); 435 if (focusedWindow != NULL) { 436 // Will just silently restore native focus & activation. 437 focusedWindow->AwtSetActiveWindow(); 438 } 439 } 440 } 441 mr = mrConsume; 442 break; 443 case 0x0127: // WM_CHANGEUISTATE 444 case 0x0128: // WM_UPDATEUISTATE 445 mr = mrConsume; 446 break; 447 } 448 449 return retValue; 450 } 451 452 LRESULT AwtFrame::WindowProc(UINT message, WPARAM wParam, LPARAM lParam) 453 { 454 MsgRouting mr = mrDoDefault; 455 LRESULT retValue = 0L; 456 457 retValue = ProxyWindowProc(message, wParam, lParam, mr); 458 459 if (mr != mrConsume) { 460 retValue = AwtWindow::WindowProc(message, wParam, lParam); 461 } 462 return retValue; 463 } 464 465 MsgRouting AwtFrame::WmShowWindow(BOOL show, UINT status) 466 { 467 /* 468 * Fix for 6492970. 469 * When a non-focusable toplevel is shown alone the Java process 470 * is not foreground. If one shows another (focusable) toplevel 471 * the native platform not always makes it foreground (see the CR). 472 * Even worse, sometimes it sends the newly shown toplevel WM_ACTIVATE 473 * message. This breaks Java focus. To workaround the problem we 474 * set the toplevel being shown foreground programmatically. 475 * The fix is localized to non-foreground process case only. 476 * (See also: 6599270) 477 */ 478 if (!IsEmbeddedFrame() && show == TRUE && status == 0) { 479 HWND fgHWnd = ::GetForegroundWindow(); 480 if (fgHWnd != NULL) { 481 DWORD fgProcessID; 482 ::GetWindowThreadProcessId(fgHWnd, &fgProcessID); 483 484 if (fgProcessID != ::GetCurrentProcessId()) { 485 AwtWindow* window = (AwtWindow*)GetComponent(GetHWnd()); 486 487 if (window != NULL && 488 window->IsFocusableWindow() && 489 window->IsAutoRequestFocus() && 490 !::IsWindowVisible(GetHWnd()) && // the window is really showing 491 !::IsWindow(GetModalBlocker(GetHWnd()))) 492 { 493 // When the Java process is not allowed to set the foreground window 494 // (see MSDN) the request below will just have no effect. 495 ::SetForegroundWindow(GetHWnd()); 496 } 497 } 498 } 499 } 500 return AwtWindow::WmShowWindow(show, status); 501 } 502 503 MsgRouting AwtFrame::WmMouseUp(UINT flags, int x, int y, int button) { 504 if (isInManualMoveOrSize) { 505 isInManualMoveOrSize = FALSE; 506 ::ReleaseCapture(); 507 return mrConsume; 508 } 509 return AwtWindow::WmMouseUp(flags, x, y, button); 510 } 511 512 MsgRouting AwtFrame::WmMouseMove(UINT flags, int x, int y) { 513 /** 514 * If this Frame is non-focusable then we should implement move and size operation for it by 515 * ourselfves because we don't dispatch appropriate mouse messages to default window procedure. 516 */ 517 if (!IsFocusableWindow() && isInManualMoveOrSize) { 518 DWORD curPos = ::GetMessagePos(); 519 x = GET_X_LPARAM(curPos); 520 y = GET_Y_LPARAM(curPos); 521 RECT r; 522 ::GetWindowRect(GetHWnd(), &r); 523 POINT mouseLoc = {x, y}; 524 mouseLoc.x -= savedMousePos.x; 525 mouseLoc.y -= savedMousePos.y; 526 savedMousePos.x = x; 527 savedMousePos.y = y; 528 if (grabbedHitTest == HTCAPTION) { 529 ::SetWindowPos(GetHWnd(), NULL, r.left+mouseLoc.x, r.top+mouseLoc.y, 530 r.right-r.left, r.bottom-r.top, 531 SWP_NOACTIVATE | SWP_NOSIZE | SWP_NOZORDER); 532 } else { 533 switch (grabbedHitTest) { 534 case HTTOP: 535 r.top += mouseLoc.y; 536 break; 537 case HTBOTTOM: 538 r.bottom += mouseLoc.y; 539 break; 540 case HTRIGHT: 541 r.right += mouseLoc.x; 542 break; 543 case HTLEFT: 544 r.left += mouseLoc.x; 545 break; 546 case HTTOPLEFT: 547 r.left += mouseLoc.x; 548 r.top += mouseLoc.y; 549 break; 550 case HTTOPRIGHT: 551 r.top += mouseLoc.y; 552 r.right += mouseLoc.x; 553 break; 554 case HTBOTTOMLEFT: 555 r.left += mouseLoc.x; 556 r.bottom += mouseLoc.y; 557 break; 558 case HTBOTTOMRIGHT: 559 case HTSIZE: 560 r.right += mouseLoc.x; 561 r.bottom += mouseLoc.y; 562 break; 563 } 564 565 ::SetWindowPos(GetHWnd(), NULL, r.left, r.top, 566 r.right-r.left, r.bottom-r.top, 567 SWP_NOACTIVATE | SWP_NOZORDER | 568 SWP_NOCOPYBITS | SWP_DEFERERASE); 569 } 570 return mrConsume; 571 } else { 572 return AwtWindow::WmMouseMove(flags, x, y); 573 } 574 } 575 576 MsgRouting AwtFrame::WmNcMouseUp(WPARAM hitTest, int x, int y, int button) { 577 if (!IsFocusableWindow() && (button & LEFT_BUTTON)) { 578 /* 579 * Fix for 6399659. 580 * The native system shouldn't activate the next window in z-order 581 * when minimizing non-focusable window. 582 */ 583 if (hitTest == HTMINBUTTON) { 584 ::ShowWindow(GetHWnd(), SW_SHOWMINNOACTIVE); 585 return mrConsume; 586 } 587 /** 588 * If this Frame is non-focusable then we should implement move and size operation for it by 589 * ourselfves because we don't dispatch appropriate mouse messages to default window procedure. 590 */ 591 if ((button & DBL_CLICK) && hitTest == HTCAPTION) { 592 // Double click on caption - maximize or restore Frame. 593 if (IsResizable()) { 594 if (::IsZoomed(GetHWnd())) { 595 ::ShowWindow(GetHWnd(), SW_SHOWNOACTIVATE); 596 } else { 597 ::ShowWindow(GetHWnd(), SW_MAXIMIZE); 598 } 599 } 600 return mrConsume; 601 } 602 switch (hitTest) { 603 case HTMAXBUTTON: 604 if (IsResizable()) { 605 if (::IsZoomed(GetHWnd())) { 606 ::ShowWindow(GetHWnd(), SW_SHOWNOACTIVATE); 607 } else { 608 ::ShowWindow(GetHWnd(), SW_MAXIMIZE); 609 } 610 } 611 return mrConsume; 612 default: 613 return mrDoDefault; 614 } 615 } 616 return AwtWindow::WmNcMouseUp(hitTest, x, y, button); 617 } 618 619 MsgRouting AwtFrame::WmNcMouseDown(WPARAM hitTest, int x, int y, int button) { 620 // By Swing request, click on the Frame's decorations (even on 621 // grabbed Frame) should generate UngrabEvent 622 if (m_grabbedWindow != NULL/* && !m_grabbedWindow->IsOneOfOwnersOf(this)*/) { 623 m_grabbedWindow->Ungrab(); 624 } 625 if (!IsFocusableWindow() && (button & LEFT_BUTTON)) { 626 switch (hitTest) { 627 case HTTOP: 628 case HTBOTTOM: 629 case HTLEFT: 630 case HTRIGHT: 631 case HTTOPLEFT: 632 case HTTOPRIGHT: 633 case HTBOTTOMLEFT: 634 case HTBOTTOMRIGHT: 635 case HTSIZE: 636 // Zoomed or non-resizable unfocusable frames should not be resizable. 637 if (isZoomed() || !IsResizable()) { 638 return mrConsume; 639 } 640 case HTCAPTION: 641 // We are going to perform default mouse action on non-client area of this window 642 // Grab mouse for this purpose and store coordinates for motion vector calculation 643 savedMousePos.x = x; 644 savedMousePos.y = y; 645 ::SetCapture(GetHWnd()); 646 isInManualMoveOrSize = TRUE; 647 grabbedHitTest = hitTest; 648 return mrConsume; 649 default: 650 return mrDoDefault; 651 } 652 } 653 return AwtWindow::WmNcMouseDown(hitTest, x, y, button); 654 } 655 656 // Override AwtWindow::Reshape() to handle minimized/maximized 657 // frames (see 6525850, 4065534) 658 void AwtFrame::Reshape(int x, int y, int width, int height) 659 { 660 if (isIconic()) { 661 // normal AwtComponent::Reshape will not work for iconified windows so... 662 WINDOWPLACEMENT wp; 663 POINT ptMinPosition = {x,y}; 664 POINT ptMaxPosition = {0,0}; 665 RECT rcNormalPosition = {x,y,x+width,y+height}; 666 RECT rcWorkspace; 667 HWND hWndDesktop = GetDesktopWindow(); 668 HWND hWndSelf = GetHWnd(); 669 670 // SetWindowPlacement takes workspace coordinates, but 671 // if taskbar is at top of screen, workspace coords != 672 // screen coords, so offset by workspace origin 673 VERIFY(::SystemParametersInfo(SPI_GETWORKAREA, 0, (PVOID)&rcWorkspace, 0)); 674 ::OffsetRect(&rcNormalPosition, -rcWorkspace.left, -rcWorkspace.top); 675 676 // set the window size for when it is not-iconified 677 wp.length = sizeof(wp); 678 wp.flags = WPF_SETMINPOSITION; 679 wp.showCmd = IsVisible() ? SW_SHOWMINIMIZED : SW_HIDE; 680 wp.ptMinPosition = ptMinPosition; 681 wp.ptMaxPosition = ptMaxPosition; 682 wp.rcNormalPosition = rcNormalPosition; 683 684 // If the call is not guarded with ignoreWmSize, 685 // a regression for bug 4851435 appears. 686 // Having this call guarded also prevents 687 // changing the iconified state of the frame 688 // while calling the Frame.setBounds() method. 689 m_ignoreWmSize = TRUE; 690 ::SetWindowPlacement(hWndSelf, &wp); 691 m_ignoreWmSize = FALSE; 692 693 return; 694 } 695 696 if (isZoomed()) { 697 // setting size of maximized window, we remove the 698 // maximized state bit (matches Motif behaviour) 699 // (calling ShowWindow(SW_RESTORE) would fire an 700 // activation event which we don't want) 701 LONG style = GetStyle(); 702 DASSERT(style & WS_MAXIMIZE); 703 style ^= WS_MAXIMIZE; 704 SetStyle(style); 705 } 706 707 AwtWindow::Reshape(x, y, width, height); 708 } 709 710 711 /* Show the frame in it's current state */ 712 void 713 AwtFrame::Show() 714 { 715 m_visible = true; 716 HWND hwnd = GetHWnd(); 717 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 718 719 if (IsLightweightFrame()) { 720 return; 721 } 722 723 DTRACE_PRINTLN3("AwtFrame::Show:%s%s%s", 724 m_iconic ? " iconic" : "", 725 m_zoomed ? " zoomed" : "", 726 m_iconic || m_zoomed ? "" : " normal"); 727 728 BOOL locationByPlatform = env->GetBooleanField(GetTarget(env), AwtWindow::locationByPlatformID); 729 730 if (locationByPlatform) { 731 moveToDefaultLocation(); 732 } 733 EnableTranslucency(TRUE); 734 735 BOOL autoRequestFocus = IsAutoRequestFocus(); 736 737 if (m_iconic) { 738 if (m_zoomed) { 739 // This whole function could probably be rewritten to use 740 // ::SetWindowPlacement but MS docs doesn't tell if 741 // ::SetWindowPlacement is a proper superset of 742 // ::ShowWindow. So let's be conservative and only use it 743 // here, where we really do need it. 744 DTRACE_PRINTLN("AwtFrame::Show(SW_SHOWMINIMIZED, WPF_RESTORETOMAXIMIZED"); 745 WINDOWPLACEMENT wp; 746 ::ZeroMemory(&wp, sizeof(WINDOWPLACEMENT)); 747 wp.length = sizeof(WINDOWPLACEMENT); 748 ::GetWindowPlacement(hwnd, &wp); 749 if (!IsFocusableWindow() || !autoRequestFocus) { 750 wp.showCmd = SW_SHOWMINNOACTIVE; 751 } else { 752 wp.showCmd = SW_SHOWMINIMIZED; 753 } 754 wp.flags |= WPF_RESTORETOMAXIMIZED; 755 ::SetWindowPlacement(hwnd, &wp); 756 } 757 else { 758 DTRACE_PRINTLN("AwtFrame::Show(SW_SHOWMINIMIZED)"); 759 if (!IsFocusableWindow() || !autoRequestFocus) { 760 ::ShowWindow(hwnd, SW_SHOWMINNOACTIVE); 761 } else { 762 ::ShowWindow(hwnd, SW_SHOWMINIMIZED); 763 } 764 } 765 } 766 else if (m_zoomed) { 767 DTRACE_PRINTLN("AwtFrame::Show(SW_SHOWMAXIMIZED)"); 768 if (!autoRequestFocus) { 769 770 m_filterFocusAndActivation = TRUE; 771 ::ShowWindow(hwnd, SW_MAXIMIZE); 772 m_filterFocusAndActivation = FALSE; 773 774 } else if (!IsFocusableWindow()) { 775 ::ShowWindow(hwnd, SW_MAXIMIZE); 776 } else { 777 ::ShowWindow(hwnd, SW_SHOWMAXIMIZED); 778 } 779 } 780 else if (m_isInputMethodWindow) { 781 // Don't activate input methow window 782 DTRACE_PRINTLN("AwtFrame::Show(SW_SHOWNA)"); 783 ::ShowWindow(hwnd, SW_SHOWNA); 784 785 // After the input method window shown, we have to adjust the 786 // IME candidate window position. Here is why. 787 // Usually, when IMM opens the candidate window, it sends WM_IME_NOTIFY w/ 788 // IMN_OPENCANDIDATE message to the awt component window. The 789 // awt component makes a Java call to acquire the text position 790 // in order to show the candidate window just below the input method window. 791 // However, by the time it acquires the position, the input method window 792 // hasn't been displayed yet, the position returned is just below 793 // the composed text and when the input method window is shown, it 794 // will hide part of the candidate list. To fix this, we have to 795 // adjust the candidate window position after the input method window 796 // is shown. See bug 5012944. 797 AdjustCandidateWindowPos(); 798 } 799 else { 800 // Nor iconic, nor zoomed (handled above) - so use SW_RESTORE 801 // to show in "normal" state regardless of whatever stale 802 // state might the invisible window still has. 803 DTRACE_PRINTLN("AwtFrame::Show(SW_RESTORE)"); 804 if (!IsFocusableWindow() || !autoRequestFocus) { 805 ::ShowWindow(hwnd, SW_SHOWNOACTIVATE); 806 } else { 807 ::ShowWindow(hwnd, SW_RESTORE); 808 } 809 } 810 } 811 812 void 813 AwtFrame::SendWindowStateEvent(int oldState, int newState) 814 { 815 SendWindowEvent(java_awt_event_WindowEvent_WINDOW_STATE_CHANGED, 816 NULL, oldState, newState); 817 } 818 819 void 820 AwtFrame::ClearMaximizedBounds() 821 { 822 m_maxBoundsSet = FALSE; 823 } 824 825 void AwtFrame::AdjustCandidateWindowPos() 826 { 827 // This method should only be called if the current frame 828 // is the input method window frame. 829 if (!m_isInputMethodWindow) { 830 return; 831 } 832 833 RECT inputWinRec, focusWinRec; 834 AwtComponent *comp = AwtComponent::GetComponent(AwtComponent::sm_focusOwner); 835 if (comp == NULL) { 836 return; 837 } 838 839 ::GetWindowRect(GetHWnd(), &inputWinRec); 840 ::GetWindowRect(sm_focusOwner, &focusWinRec); 841 842 LPARAM candType = comp->GetCandidateType(); 843 HWND defaultIMEWnd = ::ImmGetDefaultIMEWnd(GetHWnd()); 844 if (defaultIMEWnd == NULL) { 845 return; 846 } 847 UINT bits = 1; 848 // adjusts the candidate window position 849 for (int iCandType = 0; iCandType < 32; iCandType++, bits<<=1) { 850 if (candType & bits) { 851 CANDIDATEFORM cf; 852 cf.dwIndex = iCandType; 853 cf.dwStyle = CFS_CANDIDATEPOS; 854 // Since the coordinates are relative to the containing window, 855 // we have to calculate the coordinates as below. 856 cf.ptCurrentPos.x = inputWinRec.left - focusWinRec.left; 857 cf.ptCurrentPos.y = inputWinRec.bottom - focusWinRec.top; 858 859 // sends IMC_SETCANDIDATEPOS to IMM to move the candidate window. 860 ::SendMessage(defaultIMEWnd, WM_IME_CONTROL, IMC_SETCANDIDATEPOS, (LPARAM)&cf); 861 } 862 } 863 } 864 865 void 866 AwtFrame::SetMaximizedBounds(int x, int y, int w, int h) 867 { 868 m_maxPos.x = x; 869 m_maxPos.y = y; 870 m_maxSize.x = w; 871 m_maxSize.y = h; 872 m_maxBoundsSet = TRUE; 873 } 874 875 MsgRouting AwtFrame::WmGetMinMaxInfo(LPMINMAXINFO lpmmi) 876 { 877 //Firstly call AwtWindow's function 878 MsgRouting r = AwtWindow::WmGetMinMaxInfo(lpmmi); 879 880 //Then replace maxPos & maxSize if necessary 881 if (!m_maxBoundsSet) { 882 return r; 883 } 884 885 if (m_maxPos.x != java_lang_Integer_MAX_VALUE) 886 lpmmi->ptMaxPosition.x = m_maxPos.x; 887 if (m_maxPos.y != java_lang_Integer_MAX_VALUE) 888 lpmmi->ptMaxPosition.y = m_maxPos.y; 889 if (m_maxSize.x != java_lang_Integer_MAX_VALUE) 890 lpmmi->ptMaxSize.x = m_maxSize.x; 891 if (m_maxSize.y != java_lang_Integer_MAX_VALUE) 892 lpmmi->ptMaxSize.y = m_maxSize.y; 893 return mrConsume; 894 } 895 896 MsgRouting AwtFrame::WmSize(UINT type, int w, int h) 897 { 898 currentWmSizeState = type; 899 if (currentWmSizeState == SIZE_MINIMIZED) { 900 UpdateSecurityWarningVisibility(); 901 } 902 903 if (m_ignoreWmSize) { 904 return mrDoDefault; 905 } 906 907 DTRACE_PRINTLN6("AwtFrame::WmSize: %dx%d,%s visible, state%s%s%s", 908 w, h, 909 ::IsWindowVisible(GetHWnd()) ? "" : " not", 910 m_iconic ? " iconic" : "", 911 m_zoomed ? " zoomed" : "", 912 m_iconic || m_zoomed ? "" : " normal"); 913 914 BOOL iconify = type == SIZE_MINIMIZED; 915 916 // Note that zoom may be set to TRUE in several cases: 917 // 1. type == SIZE_MAXIMIZED means that either the user or 918 // the developer (via setExtendedState(MAXIMIZED_BOTH) 919 // maximizes the frame. 920 // 2. type == SIZE_MINIMIZED && isZoomed() means that a maximized 921 // frame is to be minimized. If the user minimizes a maximized 922 // frame, we need to keep the zoomed property TRUE. However, 923 // if the developer calls setExtendedState(ICONIFIED), i.e. 924 // w/o combining the ICONIFIED state with the MAXIMIZED state, 925 // we MUST RESET the zoomed property. 926 // The flag m_forceResetZoomed identifies the latter case. 927 BOOL zoom = 928 ( 929 type == SIZE_MAXIMIZED 930 || 931 (type == SIZE_MINIMIZED && isZoomed()) 932 ) 933 && !m_forceResetZoomed; 934 935 // Set the new state and send appropriate Java event 936 jint oldState = java_awt_Frame_NORMAL; 937 if (isIconic()) { 938 oldState |= java_awt_Frame_ICONIFIED; 939 } 940 if (isZoomed()) { 941 oldState |= java_awt_Frame_MAXIMIZED_BOTH; 942 } 943 944 jint newState = java_awt_Frame_NORMAL; 945 if (iconify) { 946 newState |= java_awt_Frame_ICONIFIED; 947 } 948 if (zoom) { 949 newState |= java_awt_Frame_MAXIMIZED_BOTH; 950 } 951 952 setIconic(iconify); 953 setZoomed(zoom); 954 955 jint changed = oldState ^ newState; 956 if (changed != 0) { 957 DTRACE_PRINTLN2("AwtFrame::WmSize: reporting state change %x -> %x", 958 oldState, newState); 959 960 // sync target with peer 961 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 962 env->CallVoidMethod(GetPeer(env), AwtFrame::setExtendedStateMID, newState); 963 964 // report (de)iconification to old clients 965 if (changed & java_awt_Frame_ICONIFIED) { 966 if (newState & java_awt_Frame_ICONIFIED) { 967 SendWindowEvent(java_awt_event_WindowEvent_WINDOW_ICONIFIED); 968 } else { 969 SendWindowEvent(java_awt_event_WindowEvent_WINDOW_DEICONIFIED); 970 } 971 } 972 973 // New (since 1.4) state change event 974 SendWindowStateEvent(oldState, newState); 975 } 976 977 // If window is in iconic state, do not send COMPONENT_RESIZED event 978 if (isIconic()) { 979 return mrDoDefault; 980 } 981 982 return AwtWindow::WmSize(type, w, h); 983 } 984 985 MsgRouting AwtFrame::WmActivate(UINT nState, BOOL fMinimized, HWND opposite) 986 { 987 jint type; 988 989 if (nState != WA_INACTIVE) { 990 if (::IsWindow(AwtWindow::GetModalBlocker(GetHWnd())) || 991 CheckActivateActualFocusedWindow(opposite)) 992 { 993 return mrConsume; 994 } 995 type = java_awt_event_WindowEvent_WINDOW_GAINED_FOCUS; 996 AwtComponent::SetFocusedWindow(GetHWnd()); 997 998 } else { 999 if (::IsWindow(AwtWindow::GetModalBlocker(opposite))) { 1000 return mrConsume; 1001 } else { 1002 // If deactivation happens because of press on grabbing 1003 // window - this is nonsense, since grabbing window is 1004 // assumed to have focus and watch for deactivation. But 1005 // this can happen - if grabbing window is proxied Window, 1006 // with Frame keeping real focus for it. 1007 if (m_grabbedWindow != NULL) { 1008 if (m_grabbedWindow->GetHWnd() == opposite) { 1009 // Do nothing 1010 } else { 1011 // Normally, we would rather check that this == 1012 // grabbed window, and focus is leaving it - 1013 // ungrab. But since we know about proxied 1014 // windows, we simply assume this is one of the 1015 // known cases. 1016 if (!m_grabbedWindow->IsOneOfOwnersOf((AwtWindow*)AwtComponent::GetComponent(opposite))) { 1017 m_grabbedWindow->Ungrab(); 1018 } 1019 } 1020 } 1021 CheckRetainActualFocusedWindow(opposite); 1022 1023 type = java_awt_event_WindowEvent_WINDOW_LOST_FOCUS; 1024 AwtComponent::SetFocusedWindow(NULL); 1025 sm_focusOwner = NULL; 1026 } 1027 } 1028 1029 SendWindowEvent(type, opposite); 1030 return mrConsume; 1031 } 1032 1033 BOOL AwtFrame::CheckActivateActualFocusedWindow(HWND deactivatedOpositeHWnd) 1034 { 1035 if (m_actualFocusedWindow != NULL) { 1036 HWND hwnd = m_actualFocusedWindow->GetHWnd(); 1037 if (hwnd != NULL && ::IsWindowVisible(hwnd)) { 1038 SynthesizeWmActivate(TRUE, hwnd, deactivatedOpositeHWnd); 1039 return TRUE; 1040 } 1041 m_actualFocusedWindow = NULL; 1042 } 1043 return FALSE; 1044 } 1045 1046 void AwtFrame::CheckRetainActualFocusedWindow(HWND activatedOpositeHWnd) 1047 { 1048 // If actual focused window is not this Frame 1049 if (AwtComponent::GetFocusedWindow() != GetHWnd()) { 1050 // Make sure the actual focused window is an owned window of this frame 1051 AwtWindow *focusedWindow = (AwtWindow *)AwtComponent::GetComponent(AwtComponent::GetFocusedWindow()); 1052 if (focusedWindow != NULL && focusedWindow->GetOwningFrameOrDialog() == this) { 1053 1054 // Check that the opposite window is not this frame, nor an owned window of this frame 1055 if (activatedOpositeHWnd != NULL) { 1056 AwtWindow *oppositeWindow = (AwtWindow *)AwtComponent::GetComponent(activatedOpositeHWnd); 1057 if (oppositeWindow && oppositeWindow != this && 1058 oppositeWindow->GetOwningFrameOrDialog() != this) 1059 { 1060 m_actualFocusedWindow = focusedWindow; 1061 } 1062 } else { 1063 m_actualFocusedWindow = focusedWindow; 1064 } 1065 } 1066 } 1067 } 1068 1069 BOOL AwtFrame::AwtSetActiveWindow(BOOL isMouseEventCause, UINT hittest) 1070 { 1071 if (hittest == HTCLIENT) { 1072 // Don't let the actualFocusedWindow to steal focus if: 1073 // a) the frame is clicked in its client area; 1074 // b) focus is requested to some of the frame's child. 1075 m_actualFocusedWindow = NULL; 1076 } 1077 if (IsLightweightFrame()) { 1078 return TRUE; 1079 } 1080 if (isMouseEventCause && IsEmbeddedFrame() && m_isEmbeddedInIE) { 1081 HWND hwndProxy = GetProxyFocusOwner(); 1082 // Do nothing if this frame is focused already 1083 if (::GetFocus() != hwndProxy) { 1084 // Fix for JDK-8056915: 1085 // If window activated with mouse, set focus to plugin control window 1086 // first to preserve focus owner inside browser window 1087 if (SetFocusToPluginControl(::GetParent(GetHWnd()))) { 1088 return TRUE; 1089 } 1090 // Plugin control window is already focused, so do normal processing 1091 } 1092 } 1093 return AwtWindow::AwtSetActiveWindow(isMouseEventCause); 1094 } 1095 1096 MsgRouting AwtFrame::WmEnterMenuLoop(BOOL isTrackPopupMenu) 1097 { 1098 if ( !isTrackPopupMenu ) { 1099 m_isMenuDropped = TRUE; 1100 } 1101 return mrDoDefault; 1102 } 1103 1104 MsgRouting AwtFrame::WmExitMenuLoop(BOOL isTrackPopupMenu) 1105 { 1106 if ( !isTrackPopupMenu ) { 1107 m_isMenuDropped = FALSE; 1108 } 1109 return mrDoDefault; 1110 } 1111 1112 AwtMenuBar* AwtFrame::GetMenuBar() 1113 { 1114 return menuBar; 1115 } 1116 1117 void AwtFrame::SetMenuBar(AwtMenuBar* mb) 1118 { 1119 if (menuBar) { 1120 menuBar->SetFrame(NULL); 1121 } 1122 menuBar = mb; 1123 if (mb == NULL) { 1124 // Remove existing menu bar, if any. 1125 ::SetMenu(GetHWnd(), NULL); 1126 } else { 1127 AwtFrame* oldFrame = menuBar->GetFrame(); 1128 if (oldFrame && oldFrame != this) { 1129 oldFrame->SetMenuBar(NULL); 1130 } 1131 menuBar->SetFrame(this); 1132 if (menuBar->GetHMenu() != NULL) { 1133 ::SetMenu(GetHWnd(), menuBar->GetHMenu()); 1134 } 1135 } 1136 } 1137 1138 MsgRouting AwtFrame::WmDrawItem(UINT ctrlId, DRAWITEMSTRUCT& drawInfo) 1139 { 1140 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1141 1142 // if the item to be redrawn is the menu bar, then do it 1143 AwtMenuBar* awtMenubar = GetMenuBar(); 1144 if (drawInfo.CtlType == ODT_MENU && (awtMenubar != NULL) && 1145 (::GetMenu( GetHWnd() ) == (HMENU)drawInfo.hwndItem) ) 1146 { 1147 awtMenubar->DrawItem(drawInfo); 1148 return mrConsume; 1149 } 1150 1151 return AwtComponent::WmDrawItem(ctrlId, drawInfo); 1152 } 1153 1154 MsgRouting AwtFrame::WmMeasureItem(UINT ctrlId, MEASUREITEMSTRUCT& measureInfo) 1155 { 1156 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1157 AwtMenuBar* awtMenubar = GetMenuBar(); 1158 if ((measureInfo.CtlType == ODT_MENU) && (awtMenubar != NULL)) 1159 { 1160 // AwtMenu instance is stored in itemData. Use it to check if this 1161 // menu is the menu bar. 1162 AwtMenu * pMenu = (AwtMenu *) measureInfo.itemData; 1163 DASSERT(pMenu != NULL); 1164 if ( pMenu == awtMenubar ) 1165 { 1166 HWND hWnd = GetHWnd(); 1167 HDC hDC = ::GetDC(hWnd); 1168 DASSERT(hDC != NULL); 1169 awtMenubar->MeasureItem(hDC, measureInfo); 1170 VERIFY(::ReleaseDC(hWnd, hDC)); 1171 return mrConsume; 1172 } 1173 } 1174 1175 return AwtComponent::WmMeasureItem(ctrlId, measureInfo); 1176 } 1177 1178 MsgRouting AwtFrame::WmGetIcon(WPARAM iconType, LRESULT& retVal) 1179 { 1180 //Workaround windows bug: 1181 //when reseting from specific icon to class icon 1182 //taskbar is not updated 1183 if (iconType <= 2 /*ICON_SMALL2*/) { 1184 retVal = (LRESULT)GetEffectiveIcon(iconType); 1185 return mrConsume; 1186 } else { 1187 return mrDoDefault; 1188 } 1189 } 1190 1191 void AwtFrame::DoUpdateIcon() 1192 { 1193 //Workaround windows bug: 1194 //when reseting from specific icon to class icon 1195 //taskbar is not updated 1196 HICON hIcon = GetEffectiveIcon(ICON_BIG); 1197 HICON hIconSm = GetEffectiveIcon(ICON_SMALL); 1198 SendMessage(WM_SETICON, ICON_BIG, (LPARAM)hIcon); 1199 SendMessage(WM_SETICON, ICON_SMALL, (LPARAM)hIconSm); 1200 } 1201 1202 HICON AwtFrame::GetEffectiveIcon(int iconType) 1203 { 1204 BOOL smallIcon = ((iconType == ICON_SMALL) || (iconType == 2/*ICON_SMALL2*/)); 1205 HICON hIcon = (smallIcon) ? GetHIconSm() : GetHIcon(); 1206 if (hIcon == NULL) { 1207 hIcon = (smallIcon) ? AwtToolkit::GetInstance().GetAwtIconSm() : 1208 AwtToolkit::GetInstance().GetAwtIcon(); 1209 } 1210 return hIcon; 1211 } 1212 1213 static BOOL keepOnMinimize(jobject peer) { 1214 static BOOL checked = FALSE; 1215 static BOOL keep = FALSE; 1216 if (!checked) { 1217 keep = (JNU_GetStaticFieldByName(AwtToolkit::GetEnv(), NULL, 1218 "sun/awt/windows/WFramePeer", "keepOnMinimize", "Z").z) == JNI_TRUE; 1219 checked = TRUE; 1220 } 1221 return keep; 1222 } 1223 1224 MsgRouting AwtFrame::WmSysCommand(UINT uCmdType, int xPos, int yPos) 1225 { 1226 // ignore any WM_SYSCOMMAND if this window is blocked by modal dialog 1227 if (::IsWindow(AwtWindow::GetModalBlocker(GetHWnd()))) { 1228 return mrConsume; 1229 } 1230 1231 if (uCmdType == (SYSCOMMAND_IMM & 0xFFF0)){ 1232 JNIEnv* env = AwtToolkit::GetEnv(); 1233 JNU_CallMethodByName(env, NULL, m_peerObject, 1234 "notifyIMMOptionChange", "()V"); 1235 DASSERT(!safe_ExceptionOccurred(env)); 1236 return mrConsume; 1237 } 1238 if ((uCmdType == SC_MINIMIZE) && keepOnMinimize(m_peerObject)) { 1239 ::ShowWindow(GetHWnd(),SW_SHOWMINIMIZED); 1240 return mrConsume; 1241 } 1242 return AwtWindow::WmSysCommand(uCmdType, xPos, yPos); 1243 } 1244 1245 LRESULT AwtFrame::WinThreadExecProc(ExecuteArgs * args) 1246 { 1247 switch( args->cmdId ) { 1248 case FRAME_SETMENUBAR: 1249 { 1250 jobject mbPeer = (jobject)args->param1; 1251 1252 // cancel any currently dropped down menus 1253 if (m_isMenuDropped) { 1254 SendMessage(WM_CANCELMODE); 1255 } 1256 1257 if (mbPeer == NULL) { 1258 // Remove existing menu bar, if any 1259 SetMenuBar(NULL); 1260 } else { 1261 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1262 AwtMenuBar* menuBar = (AwtMenuBar *)JNI_GET_PDATA(mbPeer); 1263 SetMenuBar(menuBar); 1264 } 1265 DrawMenuBar(); 1266 break; 1267 } 1268 1269 default: 1270 AwtWindow::WinThreadExecProc(args); 1271 break; 1272 } 1273 1274 return 0L; 1275 } 1276 1277 void AwtFrame::_SynthesizeWmActivate(void *param) 1278 { 1279 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1280 1281 SynthesizeWmActivateStruct *sas = (SynthesizeWmActivateStruct *)param; 1282 jobject self = sas->frame; 1283 jboolean doActivate = sas->doActivate; 1284 1285 AwtFrame *frame = NULL; 1286 1287 PDATA pData; 1288 JNI_CHECK_PEER_GOTO(self, ret); 1289 frame = (AwtFrame *)pData; 1290 1291 SynthesizeWmActivate(doActivate, frame->GetHWnd(), NULL); 1292 ret: 1293 env->DeleteGlobalRef(self); 1294 1295 delete sas; 1296 } 1297 1298 jobject AwtFrame::_GetBoundsPrivate(void *param) 1299 { 1300 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1301 1302 jobject self = (jobject)param; 1303 1304 jobject result = NULL; 1305 AwtFrame *f = NULL; 1306 1307 PDATA pData; 1308 JNI_CHECK_PEER_GOTO(self, ret); 1309 f = (AwtFrame *)pData; 1310 if (::IsWindow(f->GetHWnd())) 1311 { 1312 RECT rect; 1313 ::GetWindowRect(f->GetHWnd(), &rect); 1314 HWND parent = ::GetParent(f->GetHWnd()); 1315 if (::IsWindow(parent)) 1316 { 1317 POINT zero; 1318 zero.x = 0; 1319 zero.y = 0; 1320 ::ClientToScreen(parent, &zero); 1321 ::OffsetRect(&rect, -zero.x, -zero.y); 1322 } 1323 1324 result = JNU_NewObjectByName(env, "java/awt/Rectangle", "(IIII)V", 1325 rect.left, rect.top, rect.bottom-rect.top, rect.right-rect.left); 1326 } 1327 ret: 1328 env->DeleteGlobalRef(self); 1329 1330 if (result != NULL) 1331 { 1332 jobject resultGlobalRef = env->NewGlobalRef(result); 1333 env->DeleteLocalRef(result); 1334 return resultGlobalRef; 1335 } 1336 else 1337 { 1338 return NULL; 1339 } 1340 } 1341 1342 void AwtFrame::_SetState(void *param) 1343 { 1344 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1345 1346 SetStateStruct *sss = (SetStateStruct *)param; 1347 jobject self = sss->frame; 1348 jint state = sss->state; 1349 1350 AwtFrame *f = NULL; 1351 1352 PDATA pData; 1353 JNI_CHECK_PEER_GOTO(self, ret); 1354 f = (AwtFrame *)pData; 1355 HWND hwnd = f->GetHWnd(); 1356 if (::IsWindow(hwnd)) 1357 { 1358 DASSERT(!IsBadReadPtr(f, sizeof(AwtFrame))); 1359 1360 BOOL iconify = (state & java_awt_Frame_ICONIFIED) != 0; 1361 BOOL zoom = (state & java_awt_Frame_MAXIMIZED_BOTH) 1362 == java_awt_Frame_MAXIMIZED_BOTH; 1363 1364 DTRACE_PRINTLN4("WFramePeer.setState:%s%s ->%s%s", 1365 f->isIconic() ? " iconic" : "", 1366 f->isZoomed() ? " zoomed" : "", 1367 iconify ? " iconic" : "", 1368 zoom ? " zoomed" : ""); 1369 1370 if (::IsWindowVisible(hwnd)) { 1371 BOOL focusable = f->IsFocusableWindow(); 1372 1373 WINDOWPLACEMENT wp; 1374 ::ZeroMemory(&wp, sizeof(wp)); 1375 wp.length = sizeof(wp); 1376 ::GetWindowPlacement(hwnd, &wp); 1377 1378 // Iconify first. 1379 // If both iconify & zoom are TRUE, handle this case 1380 // with wp.flags field below. 1381 if (iconify) { 1382 wp.showCmd = focusable ? SW_MINIMIZE : SW_SHOWMINNOACTIVE; 1383 } else if (zoom) { 1384 wp.showCmd = focusable ? SW_SHOWMAXIMIZED : SW_MAXIMIZE; 1385 } else { // zoom == iconify == FALSE 1386 wp.showCmd = focusable ? SW_RESTORE : SW_SHOWNOACTIVATE; 1387 } 1388 if (zoom && iconify) { 1389 wp.flags |= WPF_RESTORETOMAXIMIZED; 1390 } else { 1391 wp.flags &= ~WPF_RESTORETOMAXIMIZED; 1392 } 1393 1394 if (!zoom) { 1395 f->m_forceResetZoomed = TRUE; 1396 } 1397 1398 // The SetWindowPlacement() causes the WmSize() invocation 1399 // which, in turn, actually updates the m_iconic & m_zoomed flags 1400 // as well as sends Java event (WINDOW_STATE_CHANGED.) 1401 ::SetWindowPlacement(hwnd, &wp); 1402 1403 f->m_forceResetZoomed = FALSE; 1404 } else { 1405 DTRACE_PRINTLN(" not visible, just recording the requested state"); 1406 1407 f->setIconic(iconify); 1408 f->setZoomed(zoom); 1409 } 1410 } 1411 ret: 1412 env->DeleteGlobalRef(self); 1413 1414 delete sss; 1415 } 1416 1417 jint AwtFrame::_GetState(void *param) 1418 { 1419 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1420 1421 jobject self = (jobject)param; 1422 1423 jint result = java_awt_Frame_NORMAL; 1424 AwtFrame *f = NULL; 1425 1426 PDATA pData; 1427 JNI_CHECK_PEER_GOTO(self, ret); 1428 f = (AwtFrame *)pData; 1429 if (::IsWindow(f->GetHWnd())) 1430 { 1431 DASSERT(!::IsBadReadPtr(f, sizeof(AwtFrame))); 1432 if (f->isIconic()) { 1433 result |= java_awt_Frame_ICONIFIED; 1434 } 1435 if (f->isZoomed()) { 1436 result |= java_awt_Frame_MAXIMIZED_BOTH; 1437 } 1438 1439 DTRACE_PRINTLN2("WFramePeer.getState:%s%s", 1440 f->isIconic() ? " iconic" : "", 1441 f->isZoomed() ? " zoomed" : ""); 1442 } 1443 ret: 1444 env->DeleteGlobalRef(self); 1445 1446 return result; 1447 } 1448 1449 void AwtFrame::_SetMaximizedBounds(void *param) 1450 { 1451 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1452 1453 SetMaximizedBoundsStruct *smbs = (SetMaximizedBoundsStruct *)param; 1454 jobject self = smbs->frame; 1455 int x = smbs->x; 1456 int y = smbs->y; 1457 int width = smbs->width; 1458 int height = smbs->height; 1459 1460 AwtFrame *f = NULL; 1461 1462 PDATA pData; 1463 JNI_CHECK_PEER_GOTO(self, ret); 1464 f = (AwtFrame *)pData; 1465 if (::IsWindow(f->GetHWnd())) 1466 { 1467 DASSERT(!::IsBadReadPtr(f, sizeof(AwtFrame))); 1468 f->SetMaximizedBounds(x, y, width, height); 1469 } 1470 ret: 1471 env->DeleteGlobalRef(self); 1472 1473 delete smbs; 1474 } 1475 1476 void AwtFrame::_ClearMaximizedBounds(void *param) 1477 { 1478 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1479 1480 jobject self = (jobject)param; 1481 1482 AwtFrame *f = NULL; 1483 1484 PDATA pData; 1485 JNI_CHECK_PEER_GOTO(self, ret); 1486 f = (AwtFrame *)pData; 1487 if (::IsWindow(f->GetHWnd())) 1488 { 1489 DASSERT(!::IsBadReadPtr(f, sizeof(AwtFrame))); 1490 f->ClearMaximizedBounds(); 1491 } 1492 ret: 1493 env->DeleteGlobalRef(self); 1494 } 1495 1496 void AwtFrame::_SetMenuBar(void *param) 1497 { 1498 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1499 1500 SetMenuBarStruct *smbs = (SetMenuBarStruct *)param; 1501 jobject self = smbs->frame; 1502 jobject menubar = smbs->menubar; 1503 1504 AwtFrame *f = NULL; 1505 1506 PDATA pData; 1507 JNI_CHECK_PEER_GOTO(self, ret); 1508 f = (AwtFrame *)pData; 1509 if (::IsWindow(f->GetHWnd())) 1510 { 1511 ExecuteArgs args; 1512 args.cmdId = FRAME_SETMENUBAR; 1513 args.param1 = (LPARAM)menubar; 1514 f->WinThreadExecProc(&args); 1515 } 1516 ret: 1517 env->DeleteGlobalRef(self); 1518 env->DeleteGlobalRef(menubar); 1519 1520 delete smbs; 1521 } 1522 1523 void AwtFrame::_SetIMMOption(void *param) 1524 { 1525 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1526 1527 SetIMMOptionStruct *sios = (SetIMMOptionStruct *)param; 1528 jobject self = sios->frame; 1529 jstring option = sios->option; 1530 1531 int badAlloc = 0; 1532 LPCTSTR coption; 1533 LPCTSTR empty = TEXT("InputMethod"); 1534 AwtFrame *f = NULL; 1535 1536 PDATA pData; 1537 JNI_CHECK_PEER_GOTO(self, ret); 1538 JNI_CHECK_NULL_GOTO(option, "IMMOption argument", ret); 1539 1540 f = (AwtFrame *)pData; 1541 if (::IsWindow(f->GetHWnd())) 1542 { 1543 coption = JNU_GetStringPlatformChars(env, option, NULL); 1544 if (coption == NULL) 1545 { 1546 badAlloc = 1; 1547 } 1548 if (!badAlloc) 1549 { 1550 HMENU hSysMenu = ::GetSystemMenu(f->GetHWnd(), FALSE); 1551 ::AppendMenu(hSysMenu, MF_STRING, SYSCOMMAND_IMM, coption); 1552 1553 if (coption != empty) 1554 { 1555 JNU_ReleaseStringPlatformChars(env, option, coption); 1556 } 1557 } 1558 } 1559 ret: 1560 env->DeleteGlobalRef(self); 1561 env->DeleteGlobalRef(option); 1562 1563 delete sios; 1564 1565 if (badAlloc) 1566 { 1567 throw std::bad_alloc(); 1568 } 1569 } 1570 1571 void AwtFrame::_NotifyModalBlocked(void *param) 1572 { 1573 JNIEnv *env = (JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2); 1574 1575 NotifyModalBlockedStruct *nmbs = (NotifyModalBlockedStruct *)param; 1576 jobject self = nmbs->frame; 1577 jobject peer = nmbs->peer; 1578 jobject blockerPeer = nmbs->blockerPeer; 1579 jboolean blocked = nmbs->blocked; 1580 1581 PDATA pData; 1582 1583 pData = JNI_GET_PDATA(peer); 1584 AwtFrame *f = (AwtFrame *)pData; 1585 1586 // dialog here may be NULL, for example, if the blocker is a native dialog 1587 // however, we need to install/unistall modal hooks anyway 1588 pData = JNI_GET_PDATA(blockerPeer); 1589 AwtDialog *d = (AwtDialog *)pData; 1590 1591 if ((f != NULL) && ::IsWindow(f->GetHWnd())) 1592 { 1593 // get an HWND of the toplevel window this embedded frame is within 1594 HWND fHWnd = f->GetHWnd(); 1595 while (::GetParent(fHWnd) != NULL) { 1596 fHWnd = ::GetParent(fHWnd); 1597 } 1598 // we must get a toplevel hwnd here, however due to some strange 1599 // behaviour of Java Plugin (a bug?) when running in IE at 1600 // this moment the embedded frame hasn't been placed into the 1601 // browser yet and fHWnd is not a toplevel, so we shouldn't install 1602 // the hook here 1603 if ((::GetWindowLong(fHWnd, GWL_STYLE) & WS_CHILD) == 0) { 1604 // if this toplevel is created in another thread, we should install 1605 // the modal hook into it to track window activation and mouse events 1606 DWORD fThread = ::GetWindowThreadProcessId(fHWnd, NULL); 1607 if (fThread != AwtToolkit::GetInstance().MainThread()) { 1608 // check if this thread has been already blocked 1609 BlockedThreadStruct *blockedThread = (BlockedThreadStruct *)sm_BlockedThreads.get((void *)fThread); 1610 if (blocked) { 1611 if (blockedThread == NULL) { 1612 blockedThread = new BlockedThreadStruct; 1613 blockedThread->framesCount = 1; 1614 blockedThread->modalHook = ::SetWindowsHookEx(WH_CBT, (HOOKPROC)AwtDialog::ModalFilterProc, 1615 0, fThread); 1616 blockedThread->mouseHook = ::SetWindowsHookEx(WH_MOUSE, (HOOKPROC)AwtDialog::MouseHookProc_NonTT, 1617 0, fThread); 1618 sm_BlockedThreads.put((void *)fThread, blockedThread); 1619 } else { 1620 blockedThread->framesCount++; 1621 } 1622 } else { 1623 // see the comment above: if Java Plugin behaviour when running in IE 1624 // was right, blockedThread would be always not NULL here 1625 if (blockedThread != NULL) { 1626 DASSERT(blockedThread->framesCount > 0); 1627 if ((blockedThread->framesCount) == 1) { 1628 ::UnhookWindowsHookEx(blockedThread->modalHook); 1629 ::UnhookWindowsHookEx(blockedThread->mouseHook); 1630 sm_BlockedThreads.remove((void *)fThread); 1631 delete blockedThread; 1632 } else { 1633 blockedThread->framesCount--; 1634 } 1635 } 1636 } 1637 } 1638 } 1639 } 1640 1641 env->DeleteGlobalRef(self); 1642 env->DeleteGlobalRef(peer); 1643 env->DeleteGlobalRef(blockerPeer); 1644 1645 delete nmbs; 1646 } 1647 1648 /************************************************************************ 1649 * WFramePeer native methods 1650 */ 1651 1652 extern "C" { 1653 1654 /* 1655 * Class: java_awt_Frame 1656 * Method: initIDs 1657 * Signature: ()V 1658 */ 1659 JNIEXPORT void JNICALL 1660 Java_java_awt_Frame_initIDs(JNIEnv *env, jclass cls) 1661 { 1662 TRY; 1663 1664 AwtFrame::undecoratedID = env->GetFieldID(cls,"undecorated","Z"); 1665 DASSERT(AwtFrame::undecoratedID != NULL); 1666 1667 CATCH_BAD_ALLOC; 1668 } 1669 1670 /* 1671 * Class: sun_awt_windows_WFramePeer 1672 * Method: initIDs 1673 * Signature: ()V 1674 */ 1675 JNIEXPORT void JNICALL 1676 Java_sun_awt_windows_WFramePeer_initIDs(JNIEnv *env, jclass cls) 1677 { 1678 TRY; 1679 1680 AwtFrame::setExtendedStateMID = env->GetMethodID(cls, "setExtendedState", "(I)V"); 1681 DASSERT(AwtFrame::setExtendedStateMID); 1682 CHECK_NULL(AwtFrame::setExtendedStateMID); 1683 1684 AwtFrame::getExtendedStateMID = env->GetMethodID(cls, "getExtendedState", "()I"); 1685 DASSERT(AwtFrame::getExtendedStateMID); 1686 1687 CATCH_BAD_ALLOC; 1688 } 1689 1690 /* 1691 * Class: sun_awt_windows_WFramePeer 1692 * Method: setState 1693 * Signature: (I)V 1694 */ 1695 JNIEXPORT void JNICALL 1696 Java_sun_awt_windows_WFramePeer_setState(JNIEnv *env, jobject self, 1697 jint state) 1698 { 1699 TRY; 1700 1701 SetStateStruct *sss = new SetStateStruct; 1702 sss->frame = env->NewGlobalRef(self); 1703 sss->state = state; 1704 1705 AwtToolkit::GetInstance().SyncCall(AwtFrame::_SetState, sss); 1706 // global ref and sss are deleted in _SetState() 1707 1708 CATCH_BAD_ALLOC; 1709 } 1710 1711 /* 1712 * Class: sun_awt_windows_WFramePeer 1713 * Method: getState 1714 * Signature: ()I 1715 */ 1716 JNIEXPORT jint JNICALL 1717 Java_sun_awt_windows_WFramePeer_getState(JNIEnv *env, jobject self) 1718 { 1719 TRY; 1720 1721 jobject selfGlobalRef = env->NewGlobalRef(self); 1722 1723 return static_cast<jint>(reinterpret_cast<INT_PTR>(AwtToolkit::GetInstance().SyncCall( 1724 (void*(*)(void*))AwtFrame::_GetState, 1725 (void *)selfGlobalRef))); 1726 // selfGlobalRef is deleted in _GetState() 1727 1728 CATCH_BAD_ALLOC_RET(java_awt_Frame_NORMAL); 1729 } 1730 1731 1732 /* 1733 * Class: sun_awt_windows_WFramePeer 1734 * Method: setMaximizedBounds 1735 * Signature: (IIII)V 1736 */ 1737 JNIEXPORT void JNICALL 1738 Java_sun_awt_windows_WFramePeer_setMaximizedBounds(JNIEnv *env, jobject self, 1739 jint x, jint y, jint width, jint height) 1740 { 1741 TRY; 1742 1743 SetMaximizedBoundsStruct *smbs = new SetMaximizedBoundsStruct; 1744 smbs->frame = env->NewGlobalRef(self); 1745 smbs->x = x; 1746 smbs->y = y; 1747 smbs->width = width; 1748 smbs->height = height; 1749 1750 AwtToolkit::GetInstance().SyncCall(AwtFrame::_SetMaximizedBounds, smbs); 1751 // global ref and smbs are deleted in _SetMaximizedBounds() 1752 1753 CATCH_BAD_ALLOC; 1754 } 1755 1756 1757 /* 1758 * Class: sun_awt_windows_WFramePeer 1759 * Method: clearMaximizedBounds 1760 * Signature: ()V 1761 */ 1762 JNIEXPORT void JNICALL 1763 Java_sun_awt_windows_WFramePeer_clearMaximizedBounds(JNIEnv *env, jobject self) 1764 { 1765 TRY; 1766 1767 jobject selfGlobalRef = env->NewGlobalRef(self); 1768 1769 AwtToolkit::GetInstance().SyncCall(AwtFrame::_ClearMaximizedBounds, 1770 (void *)selfGlobalRef); 1771 // selfGlobalRef is deleted in _ClearMaximizedBounds() 1772 1773 CATCH_BAD_ALLOC; 1774 } 1775 1776 1777 /* 1778 * Class: sun_awt_windows_WFramePeer 1779 * Method: setMenuBar0 1780 * Signature: (Lsun/awt/windows/WMenuBarPeer;)V 1781 */ 1782 JNIEXPORT void JNICALL 1783 Java_sun_awt_windows_WFramePeer_setMenuBar0(JNIEnv *env, jobject self, 1784 jobject mbPeer) 1785 { 1786 TRY; 1787 1788 SetMenuBarStruct *smbs = new SetMenuBarStruct; 1789 smbs->frame = env->NewGlobalRef(self); 1790 smbs->menubar = env->NewGlobalRef(mbPeer); 1791 1792 AwtToolkit::GetInstance().SyncCall(AwtFrame::_SetMenuBar, smbs); 1793 // global refs ans smbs are deleted in _SetMenuBar() 1794 1795 CATCH_BAD_ALLOC; 1796 } 1797 1798 /* 1799 * Class: sun_awt_windows_WFramePeer 1800 * Method: create 1801 * Signature: (Lsun/awt/windows/WComponentPeer;)V 1802 */ 1803 JNIEXPORT void JNICALL 1804 Java_sun_awt_windows_WFramePeer_createAwtFrame(JNIEnv *env, jobject self, 1805 jobject parent) 1806 { 1807 TRY; 1808 1809 AwtToolkit::CreateComponent(self, parent, 1810 (AwtToolkit::ComponentFactory) 1811 AwtFrame::Create); 1812 PDATA pData; 1813 JNI_CHECK_PEER_CREATION_RETURN(self); 1814 1815 CATCH_BAD_ALLOC; 1816 } 1817 1818 /* 1819 * Class: sun_awt_windows_WFramePeer 1820 * Method: getSysMenuHeight 1821 * Signature: ()I 1822 */ 1823 JNIEXPORT jint JNICALL 1824 Java_sun_awt_windows_WFramePeer_getSysMenuHeight(JNIEnv *env, jclass self) 1825 { 1826 TRY; 1827 1828 return ::GetSystemMetrics(SM_CYMENUSIZE); 1829 1830 CATCH_BAD_ALLOC_RET(0); 1831 } 1832 1833 /* 1834 * Class: sun_awt_windows_WFramePeer 1835 * Method: pSetIMMOption 1836 * Signature: (Ljava/lang/String;)V 1837 */ 1838 JNIEXPORT void JNICALL 1839 Java_sun_awt_windows_WFramePeer_pSetIMMOption(JNIEnv *env, jobject self, 1840 jstring option) 1841 { 1842 TRY; 1843 1844 SetIMMOptionStruct *sios = new SetIMMOptionStruct; 1845 sios->frame = env->NewGlobalRef(self); 1846 sios->option = (jstring)env->NewGlobalRef(option); 1847 1848 AwtToolkit::GetInstance().SyncCall(AwtFrame::_SetIMMOption, sios); 1849 // global refs and sios are deleted in _SetIMMOption() 1850 1851 CATCH_BAD_ALLOC; 1852 } 1853 1854 } /* extern "C" */ 1855 1856 1857 /************************************************************************ 1858 * WEmbeddedFrame native methods 1859 */ 1860 1861 extern "C" { 1862 1863 /* 1864 * Class: sun_awt_windows_WFramePeer 1865 * Method: initIDs 1866 * Signature: (Lsun/awt/windows/WMenuBarPeer;)V 1867 */ 1868 JNIEXPORT void JNICALL 1869 Java_sun_awt_windows_WEmbeddedFrame_initIDs(JNIEnv *env, jclass cls) 1870 { 1871 TRY; 1872 1873 AwtFrame::handleID = env->GetFieldID(cls, "handle", "J"); 1874 DASSERT(AwtFrame::handleID != NULL); 1875 CHECK_NULL(AwtFrame::handleID); 1876 1877 AwtFrame::activateEmbeddingTopLevelMID = env->GetMethodID(cls, "activateEmbeddingTopLevel", "()V"); 1878 DASSERT(AwtFrame::activateEmbeddingTopLevelMID != NULL); 1879 CHECK_NULL(AwtFrame::activateEmbeddingTopLevelMID); 1880 1881 AwtFrame::isEmbeddedInIEID = env->GetFieldID(cls, "isEmbeddedInIE", "Z"); 1882 DASSERT(AwtFrame::isEmbeddedInIEID != NULL); 1883 1884 CATCH_BAD_ALLOC; 1885 } 1886 1887 JNIEXPORT void JNICALL 1888 Java_sun_awt_windows_WEmbeddedFrame_notifyModalBlockedImpl(JNIEnv *env, 1889 jobject self, 1890 jobject peer, 1891 jobject blockerPeer, 1892 jboolean blocked) 1893 { 1894 TRY; 1895 1896 NotifyModalBlockedStruct *nmbs = new NotifyModalBlockedStruct; 1897 nmbs->frame = env->NewGlobalRef(self); 1898 nmbs->peer = env->NewGlobalRef(peer); 1899 nmbs->blockerPeer = env->NewGlobalRef(blockerPeer); 1900 nmbs->blocked = blocked; 1901 1902 AwtToolkit::GetInstance().SyncCall(AwtFrame::_NotifyModalBlocked, nmbs); 1903 // global refs and nmbs are deleted in _NotifyModalBlocked() 1904 1905 CATCH_BAD_ALLOC; 1906 } 1907 1908 } /* extern "C" */ 1909 1910 1911 /************************************************************************ 1912 * WEmbeddedFramePeer native methods 1913 */ 1914 1915 extern "C" { 1916 1917 JNIEXPORT void JNICALL 1918 Java_sun_awt_windows_WEmbeddedFramePeer_create(JNIEnv *env, jobject self, 1919 jobject parent) 1920 { 1921 TRY; 1922 1923 JNI_CHECK_NULL_RETURN(self, "peer"); 1924 AwtToolkit::CreateComponent(self, parent, 1925 (AwtToolkit::ComponentFactory) 1926 AwtFrame::Create); 1927 PDATA pData; 1928 JNI_CHECK_PEER_CREATION_RETURN(self); 1929 1930 CATCH_BAD_ALLOC; 1931 } 1932 1933 JNIEXPORT jobject JNICALL 1934 Java_sun_awt_windows_WEmbeddedFramePeer_getBoundsPrivate(JNIEnv *env, jobject self) 1935 { 1936 TRY; 1937 1938 jobject result = (jobject)AwtToolkit::GetInstance().SyncCall( 1939 (void *(*)(void *))AwtFrame::_GetBoundsPrivate, 1940 env->NewGlobalRef(self)); 1941 // global ref is deleted in _GetBoundsPrivate 1942 1943 if (result != NULL) 1944 { 1945 jobject resultLocalRef = env->NewLocalRef(result); 1946 env->DeleteGlobalRef(result); 1947 return resultLocalRef; 1948 } 1949 else 1950 { 1951 return NULL; 1952 } 1953 1954 CATCH_BAD_ALLOC_RET(NULL); 1955 } 1956 1957 JNIEXPORT void JNICALL 1958 Java_sun_awt_windows_WFramePeer_synthesizeWmActivate(JNIEnv *env, jobject self, jboolean doActivate) 1959 { 1960 TRY; 1961 1962 SynthesizeWmActivateStruct *sas = new SynthesizeWmActivateStruct; 1963 sas->frame = env->NewGlobalRef(self); 1964 sas->doActivate = doActivate; 1965 1966 /* 1967 * WARNING: invoking this function without synchronization by m_Sync CriticalSection. 1968 * Taking this lock results in a deadlock. 1969 */ 1970 AwtToolkit::GetInstance().InvokeFunction(AwtFrame::_SynthesizeWmActivate, sas); 1971 // global ref and sas are deleted in _SynthesizeWmActivate() 1972 1973 CATCH_BAD_ALLOC; 1974 } 1975 1976 } /* extern "C" */ 1977 1978 static bool SetFocusToPluginControl(HWND hwndPlugin) 1979 { 1980 HWND hwndFocus = ::GetFocus(); 1981 1982 if (hwndFocus == hwndPlugin) { 1983 return false; 1984 } 1985 1986 ::SetFocus(hwndPlugin); 1987 DWORD dwError = ::GetLastError(); 1988 if (dwError != ERROR_SUCCESS) { 1989 // If direct call failed, use a special message to set focus 1990 return (::SendMessage(hwndPlugin, WM_AX_REQUEST_FOCUS_TO_EMBEDDER, 0, 0) == 0); 1991 } 1992 return true; 1993 }