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