home *** CD-ROM | disk | FTP | other *** search
/ Tools / WinSN5.0Ver.iso / NETSCAP.50 / WIN1998.ZIP / ns / cmd / macfe / gui / CBrowserWindow.cp < prev    next >
Encoding:
Text File  |  1998-04-08  |  78.6 KB  |  2,557 lines

  1. /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
  2.  *
  3.  * The contents of this file are subject to the Netscape Public License
  4.  * Version 1.0 (the "NPL"); you may not use this file except in
  5.  * compliance with the NPL.  You may obtain a copy of the NPL at
  6.  * http://www.mozilla.org/NPL/
  7.  *
  8.  * Software distributed under the NPL is distributed on an "AS IS" basis,
  9.  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
  10.  * for the specific language governing rights and limitations under the
  11.  * NPL.
  12.  *
  13.  * The Initial Developer of this code under the NPL is Netscape
  14.  * Communications Corporation.  Portions created by Netscape are
  15.  * Copyright (C) 1998 Netscape Communications Corporation.  All Rights
  16.  * Reserved.
  17.  */
  18.  
  19. #include "Netscape_Constants.h"
  20. #include "CBrowserWindow.h"
  21.  
  22. #include "CAutoPtrXP.h"
  23.  
  24. #include "CBevelView.h"
  25. #include "CApplicationEventAttachment.h"
  26. #include "CHTMLView.h"
  27. #include "CBrowserContext.h"
  28. #include "CHistoryMenu.h"
  29. #include "mimages.h"
  30. #include "mversion.h"
  31. #include "CURLEditField.h"
  32. #include "CURLCaption.h"
  33. #include "CProxyPane.h"
  34.  
  35. //#include "CEditView.h"                // need for SetWindowContext, using CEditView::class_ID
  36. #include "CEditorWindow.h"
  37. // need these for dynamic window modification - mjc
  38. #include "CDragBar.h"                // need for GetChromeInfo
  39. #include "CDragBarContainer.h"        // need for SetChromeInfo, using CDragBarContainer::class_ID
  40. #include "CHyperScroller.h" // need for SetChromeInfo
  41. #include "CPaneEnabler.h"
  42.  
  43. #include "CSpinningN.h"
  44. #include "CBrowserSecurityButton.h"
  45. #include "CMiniSecurityButton.h"
  46.  
  47. #include "CRDFCoordinator.h"
  48.  
  49.     // stuff added by deeje
  50. #include "macutil.h"
  51. #include "xp.h"
  52. #include "uerrmgr.h"    // GetPString prototype
  53. #include "shist.h"
  54. #include "resgui.h"
  55. #include "CURLDispatcher.h"
  56. #include "prefapi.h"
  57. #include "CPrefsDialog.h"
  58. #include "xp_ncent.h"    // for XP_SetLastActiveContext
  59.  
  60.  
  61. #include "libi18n.h"
  62. #include "ufilemgr.h"
  63.  
  64.     // stuff for AppleEvent support
  65. #include "CAppleEventHandler.h"
  66. #include "resae.h"
  67. #include "uapp.h"
  68.  
  69. #include "CMochaHacks.h" // for SendMoveEvent, SendResizeEvent, and RemoveDependents 1997-02-26 mjc
  70.  
  71. #include "RandomFrontEndCrap.h" // for IsSpecialBrowserWindow
  72.  
  73. #include <UReanimator.h>
  74. #include <UMemoryMgr.h>
  75. #include <Sound.h>
  76.  
  77. // pane id constants - for SetChromeInfo and GetChromeInfo - mjc
  78. const PaneIDT HTML_Container_PaneID = 'HtCt';
  79. const PaneIDT Button_Bar_PaneID = 'NBar';
  80. const PaneIDT Location_Bar_PaneID = 'LBar';
  81. const PaneIDT Directory_Bar_PaneID = 'DBar';
  82. const PaneIDT PersonalToolbar_PaneID = 'PBar';
  83. const PaneIDT SWatch_View_PaneID = 'SwBv';
  84. const PaneIDT Hyper_Scroller_PaneID = 1005;
  85. const PaneIDT Status_Bar_PaneID = 'StBv';
  86. const PaneIDT CoBrandLogo_PaneID = 'Bnet';
  87.  
  88. const char* Pref_ShowToolbar = "browser.chrome.show_toolbar";
  89. const char* Pref_ShowLocationBar = "browser.chrome.show_url_bar";
  90. const char* Pref_ShowPersonalToolbar = "browser.chrome.show_personal_toolbar";    // is this right?
  91.  
  92.  
  93. enum {  eNavigationBar,
  94.         eLocationBar,
  95.         eStatusBar,
  96.         ePersonalToolbar };
  97.                 
  98. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  99. //    Ñ    
  100. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  101.  
  102. CBrowserWindow::CBrowserWindow(LStream* inStream)
  103.     :    CNetscapeWindow(inStream, WindowType_Browser),
  104.         CSaveWindowStatus(this)
  105. {
  106.     mProgressListener = NULL;
  107.     mContext = NULL;
  108.     mAlwaysOnBottom = false; // javascript alwaysLowered window property - mjc
  109.     mZLocked = false;
  110.     mMenubarMode = BrWn_Menubar_Default;
  111.     mCommandsDisabled = false;
  112.     fCloseNotifier = MakeNoProcessPSN();
  113.     mSupportsPageServices = false;
  114.     mAllowSubviewPopups = true;
  115.     mIsRootDocInfo = false;
  116.     mIsViewSource = false;
  117.     mIsHTMLHelp = false;
  118.     mHTMLView = nil;
  119.     mNavCenterParent = nil;
  120. }
  121.  
  122. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  123. //    Ñ    
  124. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  125.  
  126. CBrowserWindow::~CBrowserWindow()
  127. {
  128.     delete mProgressListener;
  129.     if (mContext != NULL) CMochaHacks::RemoveDependents(*mContext); // close windows declared as dependents in Javascript - 1997-02-26 mjc
  130.     SetWindowContext(NULL);
  131.     
  132.     RemoveAllAttachments();
  133.         // Kludgy, but prevents crash in LUndoer caused by view being destroyed before
  134.         // attachments.  This happens if a form element which is a text field exists.
  135.  
  136.     // there is no need to save the state of the selector widget or the nav center shelf
  137.     // because the prefs are always correctly updated on a state change.
  138. }
  139.  
  140. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  141. //    Ñ    
  142. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  143.  
  144. void CBrowserWindow::FinishCreateSelf(void)
  145. {
  146.     CNetscapeWindow::FinishCreateSelf();
  147.     
  148.     mHTMLView = dynamic_cast<CHTMLView*>(FindPaneByID(CHTMLView::pane_ID));
  149.     ThrowIfNil_(mHTMLView);
  150.     
  151.     mNavCenterParent = dynamic_cast<CRDFCoordinator*>(FindPaneByID(CRDFCoordinator::pane_ID));
  152.         
  153.     if (HasAttribute(windAttr_Regular) && HasAttribute(windAttr_Resizable))
  154.     {
  155.         FinishCreateWindow();
  156.         
  157.         Rect structureBounds = UWindows::GetWindowStructureRect(mMacWindowP);
  158.         
  159.         GDHandle windowDevice = UWindows::FindDominantDevice(structureBounds);
  160.         GDHandle mainDevice = ::GetMainDevice();
  161.         
  162.         Rect staggerBounds;
  163.         
  164.         if (windowDevice && (windowDevice != mainDevice))
  165.             staggerBounds = (*windowDevice)->gdRect;
  166.         else
  167.         {
  168.             staggerBounds = (*mainDevice)->gdRect;
  169.             staggerBounds.top += LMGetMBarHeight();
  170.         }
  171.         ::InsetRect(&staggerBounds, 4, 4);    //    Same as zoom limit
  172.         
  173.         Rect contentBounds = UWindows::GetWindowContentRect(mMacWindowP);
  174.         
  175.         Rect windowBorder;
  176.         windowBorder.top = contentBounds.top - structureBounds.top;
  177.         windowBorder.left = contentBounds.left - structureBounds.left;
  178.         windowBorder.bottom = structureBounds.bottom - contentBounds.bottom;
  179.         windowBorder.right = structureBounds.right - contentBounds.right;
  180.         
  181.         Point maxTopLeft;
  182.         maxTopLeft.v = staggerBounds.bottom
  183.             - (windowBorder.top + mMinMaxSize.top + windowBorder.bottom);
  184.         maxTopLeft.h = staggerBounds.right
  185.             - (windowBorder.left + mMinMaxSize.left + windowBorder.right);
  186.         
  187.         UInt16 vStaggerOffset = windowBorder.top;
  188.         
  189.         if (vStaggerOffset > 12)
  190.             vStaggerOffset -= 4;    //    Tweak it up
  191.         
  192.         const int maxStaggerPositionsCount = 10;
  193.         Point staggerPositions[maxStaggerPositionsCount];
  194.         UInt16 usedStaggerPositions[maxStaggerPositionsCount];
  195.         int staggerPositionsCount;
  196.         
  197.         for (    staggerPositionsCount = 0;
  198.                 staggerPositionsCount < maxStaggerPositionsCount;
  199.                 ++staggerPositionsCount)
  200.         {
  201.             staggerPositions[staggerPositionsCount].v
  202.                 = staggerBounds.top + (vStaggerOffset * staggerPositionsCount);
  203.             staggerPositions[staggerPositionsCount].h
  204.                 = staggerBounds.left + (4 * staggerPositionsCount);
  205.             
  206.             if ((staggerPositions[staggerPositionsCount].v > maxTopLeft.v)
  207.                 || (staggerPositions[staggerPositionsCount].h > maxTopLeft.h))
  208.                 break;
  209.             
  210.             usedStaggerPositions[staggerPositionsCount] = 0;
  211.         }
  212.         unsigned int windowCount = 0;
  213.         CMediatedWindow *foundWindow = NULL;
  214.         CWindowIterator windowIterator(WindowType_Browser);
  215.         
  216.         for (windowIterator.Next(foundWindow); foundWindow; windowIterator.Next(foundWindow))
  217.         {
  218.             CBrowserWindow *browserWindow = dynamic_cast<CBrowserWindow*>(foundWindow);
  219.             
  220.             if (browserWindow && (browserWindow != this)
  221.                 && browserWindow->HasAttribute(windAttr_Regular))
  222.             {
  223.                 ++windowCount;
  224.                 Rect bounds = UWindows::GetWindowStructureRect(browserWindow->mMacWindowP);
  225.                 
  226.                 for (int index = 0; index < staggerPositionsCount; ++index)
  227.                 {
  228.                     Boolean matchTop = (bounds.top == staggerPositions[index].v);
  229.                     Boolean matchLeft = (bounds.left == staggerPositions[index].h);
  230.                     
  231.                     if ((matchTop) && (matchLeft))
  232.                         usedStaggerPositions[index] += 1;
  233.                     
  234.                     if ((matchTop) || (matchLeft))
  235.                         break;
  236.                 }
  237.             }
  238.         }
  239.         Point structureSize;
  240.         structureSize.v = structureBounds.bottom - structureBounds.top;
  241.         structureSize.h = structureBounds.right - structureBounds.left;
  242.         
  243.         if (windowCount)
  244.         {
  245.             Boolean foundStaggerPosition = false;
  246.             
  247.             for (UInt16 minCount = 0; (minCount < 100) && !foundStaggerPosition; ++minCount)
  248.             {
  249.                 for (int index = 0; index < staggerPositionsCount; ++index)
  250.                 {
  251.                     if (usedStaggerPositions[index] == minCount)
  252.                     {
  253.                         structureBounds.top = staggerPositions[index].v;
  254.                         structureBounds.left = staggerPositions[index].h;
  255.                         foundStaggerPosition = true;
  256.                         break;
  257.                     }
  258.                 }
  259.             }
  260.             if (!foundStaggerPosition)
  261.             {
  262.                 structureBounds.top = staggerBounds.top;
  263.                 structureBounds.left = staggerBounds.left;
  264.             }
  265.             structureBounds.bottom = structureBounds.top + structureSize.v;
  266.             structureBounds.right = structureBounds.left + structureSize.h;
  267.         }
  268.         if ((structureBounds.top > maxTopLeft.v) || (structureBounds.left > maxTopLeft.h))
  269.         {
  270.             structureBounds.top = staggerBounds.top;
  271.             structureBounds.left = staggerBounds.left;
  272.             structureBounds.bottom = structureBounds.top + structureSize.v;
  273.             structureBounds.right = structureBounds.left + structureSize.h;
  274.         }
  275.         if (structureBounds.bottom > staggerBounds.bottom)
  276.             structureBounds.bottom = staggerBounds.bottom;
  277.         
  278.         if (structureBounds.right > staggerBounds.right)
  279.             structureBounds.right = staggerBounds.right;
  280.         
  281.         contentBounds.top = structureBounds.top + windowBorder.top;
  282.         contentBounds.left = structureBounds.left + windowBorder.left;
  283.         contentBounds.bottom = structureBounds.bottom - windowBorder.bottom;
  284.         contentBounds.right = structureBounds.right - windowBorder.right;
  285.         
  286.         DoSetBounds(contentBounds);
  287.     }
  288.     UReanimator::LinkListenerToControls(this, this, mPaneID);
  289.     
  290.     // Show/hide toolbars based on preference settings
  291.     XP_Bool    value;
  292.     PREF_GetBoolPref(Pref_ShowToolbar, &value);
  293.     mToolbarShown[eNavigationBar] = value;
  294.     ShowOneDragBar(Button_Bar_PaneID, value);
  295.     PREF_GetBoolPref(Pref_ShowLocationBar, &value);
  296.     mToolbarShown[eLocationBar] = value;
  297.     ShowOneDragBar(Location_Bar_PaneID, value);
  298.     PREF_GetBoolPref(Pref_ShowPersonalToolbar, &value);
  299.     mToolbarShown[ePersonalToolbar] = value;
  300.     ShowOneDragBar(PersonalToolbar_PaneID, value);
  301.     mToolbarShown[eStatusBar] = TRUE; // no pref for status bar
  302.  
  303.     // Handle NavCenter pane. There are two separate prefs here: one to control showing/hiding the
  304.     // selector widget, the other for the shelf itself. Recall that Composer doesn't have a nav center...
  305.     if ( mNavCenterParent ) {
  306.         if ( PREF_GetBoolPref(CRDFCoordinator::Pref_ShowNavCenterSelector, &value) == PREF_ERROR )
  307.             value = true;
  308.         mNavCenterParent->NavCenterSelector().SetShelfState ( value );
  309.  
  310.         // don't worry about showing the shelf if the selector is not visible. Otherwise do
  311.         // what the pref says.
  312.         if ( value ) {
  313.             // if the pref is missing, close it by default. If the pref exists, use whatever is
  314.             // stored there. There is no need to set the current view because HT handles that.
  315.             if ( PREF_GetBoolPref(CRDFCoordinator::Pref_ShowNavCenterShelf, &value) == PREF_ERROR )
  316.                 value = false;
  317.             mNavCenterParent->NavCenterShelf().SetShelfState ( value );
  318.         } // if selector visible
  319.         
  320.     } // if there is a navcenter
  321.             
  322.     // Delete the Admin Kit co-brand button if a
  323.     // custom animation has not been installed
  324.     if ( !CPrefs::HasCoBrand() ) {
  325.         LPane* button = FindPaneByID(CoBrandLogo_PaneID);
  326.         if (button) {
  327.             RemoveSubPane(button);
  328.             delete button;
  329.         }
  330.     }
  331.  
  332.     /*
  333.         // the HTML view handles many of the buttons in the tool bar
  334.     LListener*        theHTMLView = (LListener*) FindPaneByID(CHTMLView::pane_ID);
  335.     if (theHTMLView != nil)
  336.     {
  337.         UReanimator::LinkListenerToControls(theHTMLView, this, mPaneID);
  338.     }
  339.     */
  340.     
  341.     // Make the tab group the latent sub commander
  342.     
  343.     CURLEditField* theURLEditField = dynamic_cast<CURLEditField*>(FindPaneByID(CURLEditField::class_ID));
  344.     if (theURLEditField)
  345.     {
  346.         // Find the tab group which is a super commander of the edit field and make it
  347.         // the latent sub commander which should rotate the target to the first target.
  348.         
  349.         LCommander* theCommander    = theURLEditField->GetSuperCommander();
  350.         LTabGroup*    theTabGroup        = nil;
  351.         while (theCommander && !(theTabGroup = dynamic_cast<LTabGroup*>(theCommander)))
  352.         {
  353.             theCommander = theCommander->GetSuperCommander();
  354.         }
  355.         
  356.         if (theTabGroup)
  357.         {
  358.             SetLatentSub(theTabGroup);
  359.         }
  360.     }
  361. }
  362.  
  363. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  364. //    Ñ    
  365. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  366. // NOTE: This will handle registering/unregistering the embedded navCenter
  367. //       for sitemap info. When the context is cleared (by passing NULL), 
  368. //       it will unregister so we don't need to do it elsewhere.
  369. void CBrowserWindow::SetWindowContext(CBrowserContext* inContext)
  370. {
  371.     if (mContext != NULL) {
  372.         if ( mNavCenterParent )
  373.             mNavCenterParent->UnregisterNavCenter();
  374.         mContext->RemoveUser(this);
  375.     }
  376.     
  377.     mContext = inContext;
  378.     
  379.     if (mContext != NULL)
  380.     {
  381.         mContext->SetRequiresClone(true);
  382.         mContext->AddListener(this);
  383.         try {
  384.             // Let there be a progress listener, placed in my firmament,
  385.             // which shall listen to the context
  386.             mProgressListener = new CProgressListener(this, inContext);
  387.         } catch (...) {
  388.             mProgressListener = NULL;
  389.         }
  390.         mContext->AddUser(this);
  391.         // now hook up CProxyPane to listen to context
  392.         CProxyPane* browserPageProxy = dynamic_cast<CProxyPane*>(FindPaneByID(CProxyPane::class_ID));
  393.         if (browserPageProxy)
  394.             mContext->AddListener(browserPageProxy);
  395.         // now hook up CURLCaption to listen to context
  396.         CURLCaption* urlCaption = dynamic_cast<CURLCaption*>(FindPaneByID(CURLCaption::class_ID));
  397.         if (urlCaption)
  398.             mContext->AddListener(urlCaption);
  399.         // now hook up CURLEditField to listen to context
  400.         CURLEditField* urlField = dynamic_cast<CURLEditField*>(FindPaneByID(CURLEditField::class_ID));
  401.         if (urlField)
  402.             {
  403.             mContext->AddListener(urlField);
  404.             urlField->AddListener(this);
  405.             if (urlCaption)
  406.                 urlField->AddListener(urlCaption);
  407.             }
  408.         CSpinningN* theN = dynamic_cast<CSpinningN*>(FindPaneByID(CSpinningN::class_ID));
  409.         if (theN)
  410.             mContext->AddListener(theN);
  411.  
  412.         CBrowserSecurityButton* securityButton =
  413.             dynamic_cast<CBrowserSecurityButton*>(FindPaneByID(CBrowserSecurityButton::class_ID));
  414.         if (securityButton)
  415.             mContext->AddListener(securityButton);
  416.  
  417.         CMiniSecurityButton* miniSecurityButton =
  418.             dynamic_cast<CMiniSecurityButton*>(FindPaneByID(CMiniSecurityButton::class_ID));
  419.         if (miniSecurityButton)
  420.             mContext->AddListener(miniSecurityButton);
  421.         
  422.         // setup navCenter for sitemaps
  423.         if ( mNavCenterParent && !HasAttribute(windAttr_Floating))
  424.             mNavCenterParent->RegisterNavCenter ( *inContext );
  425.  
  426.     }
  427.         
  428.     GetHTMLView()->SetContext(mContext);
  429.     
  430.     // This call links up the model object hierarchy for any potential
  431.     // sub model that gets created within the scope of the html view.
  432.     GetHTMLView()->SetFormElemBaseModel(this);
  433.     
  434. }
  435.  
  436. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  437. //    Ñ    
  438. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  439.  
  440. CNSContext* CBrowserWindow::GetWindowContext() const
  441. {
  442.     return mContext;
  443. }
  444.  
  445. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  446. //    Ñ    
  447. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  448.  
  449. void CBrowserWindow::FindCommandStatus(
  450.     CommandT            inCommand,
  451.     Boolean                &outEnabled,
  452.     Boolean                &outUsesMark,
  453.     Char16                &outMark,
  454.     Str255                outName)
  455. {
  456.     outUsesMark = false;
  457.     
  458.     if (mIsHTMLHelp && UDesktop::FrontWindowIsModal() && inCommand != cmd_About)
  459.     {
  460.         outEnabled = false;
  461.         return;
  462.     }
  463.     // Floating browser windows whose commands have been disabled should only disable the
  464.     // commands that apply to the floating window.
  465.     if (mCommandsDisabled)
  466.         if (HasAttribute(windAttr_Floating))
  467.         {
  468.             if (    
  469.                 inCommand == cmd_GoBack ||
  470.                 inCommand == cmd_GoForward ||
  471.                 inCommand == cmd_Home ||
  472.                 inCommand == cmd_Close ||
  473.                 inCommand == cmd_ToggleToolbar ||
  474.                 inCommand == cmd_ToggleURLField ||
  475.                 inCommand == cmd_Reload ||
  476.                 inCommand == cmd_LoadImages ||
  477.                 inCommand == cmd_Stop
  478. #ifdef EDITOR
  479.                 ||
  480.                 inCommand == cmd_EditFrameSet ||
  481.                 inCommand == cmd_EditDocument
  482. #endif // EDITOR
  483.                 )
  484.             {
  485.                 outEnabled = false;
  486.                 return;
  487.             }
  488.         }
  489.         // Commands may be disabled from javascript. The motivation for this is to prevent
  490.         // users from loading new content into windows that have a special purpose (i.e. Constellation).
  491.         // Don't disable Apple Menu Items or Quit menu item.
  492.         // NOTE: it appears that the Apple Menu Items will be disabled unless I enable
  493.         // the About command. Assume for now that menubar hiding will be implemented, so the
  494.         // user won't be able to access the About menu item.
  495.         else if (
  496.                 inCommand != cmd_Quit &&
  497.                 inCommand != cmd_SecurityInfo &&
  498.                 inCommand != cmd_About)
  499.             {
  500.                 outEnabled = false;
  501.                 return;
  502.             }
  503.  
  504.     // 
  505.     // Handle the remainder of commands
  506.     //
  507.     switch (inCommand)
  508.     {
  509.         case cmd_DocumentInfo:
  510.         case cmd_ViewSource:
  511.             if (mContext && (mIsRootDocInfo || mIsViewSource || mIsHTMLHelp))
  512.             {
  513.                 outEnabled = false;
  514.                 break;
  515.             }
  516.         case cmd_PageSetup:
  517.         case cmd_Print:
  518.         case cmd_PrintOne:
  519.         case cmd_AddToBookmarks:
  520.         case cmd_SaveAs:
  521.         case cmd_SecurityInfo:
  522.         case cmd_FTPUpload:
  523.         case cmd_Find:
  524.         case cmd_MailDocument:
  525.         case cmd_LoadImages:
  526.         case cmd_Reload:
  527.         {
  528.             // Delegate this to the view.
  529.             GetHTMLView()->FindCommandStatus(inCommand, outEnabled, outUsesMark, outMark, outName);
  530.             break;
  531.         }
  532.         case cmd_GoForward:
  533.             if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey))
  534.             {
  535.                 LString::CopyPStr(::GetPString(MENU_FORWARD_ONE_HOST), outName);
  536.             }
  537.             else
  538.             {
  539.                 LString::CopyPStr(::GetPString(MENU_FORWARD), outName);
  540.             }
  541.  
  542.             if (mContext != NULL)
  543.             {
  544.                 outEnabled = mContext->CanGoForward() && !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp);
  545.                 
  546.             }
  547.             break;
  548.         case cmd_GoBack:
  549.             if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey))
  550.             {
  551.                 LString::CopyPStr(::GetPString(MENU_BACK_ONE_HOST), outName);
  552.             }
  553.             else
  554.             {
  555.                 LString::CopyPStr(::GetPString(MENU_BACK), outName);
  556.             }
  557.         
  558.             if (mContext != NULL)
  559.             {
  560.                 outEnabled = mContext->CanGoBack() && !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp);
  561.                 
  562.             }
  563.             break;
  564.         case cmd_Home:
  565.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp) : true;
  566.             break;
  567.  
  568.         case cmd_ToggleToolbar:
  569.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp || PREF_PrefIsLocked(Pref_ShowToolbar)) : true;
  570.             ::GetIndString(outName, BROWSER_MENU_TOGGLE_STRINGS_ID, (mToolbarShown[eNavigationBar] ? HIDE_NAVIGATION_TOOLBAR_STRING : SHOW_NAVIGATION_TOOLBAR_STRING));
  571.             break;
  572.         
  573.         case cmd_ToggleURLField:
  574.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp || PREF_PrefIsLocked(Pref_ShowLocationBar)) : true;
  575.             ::GetIndString(outName, BROWSER_MENU_TOGGLE_STRINGS_ID, (mToolbarShown[eLocationBar] ? HIDE_LOCATION_TOOLBAR_STRING : SHOW_LOCATION_TOOLBAR_STRING));
  576.             break;
  577.  
  578.         case cmd_TogglePersonalToolbar:
  579.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp || PREF_PrefIsLocked(Pref_ShowPersonalToolbar)) : true;
  580.             ::GetIndString(outName, BROWSER_MENU_TOGGLE_STRINGS_ID, (mToolbarShown[ePersonalToolbar] ? HIDE_PERSONAL_TOOLBAR_STRING : SHOW_PERSONAL_TOOLBAR_STRING));
  581.             break;
  582.         
  583.         case cmd_NCToggle:
  584.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp || PREF_PrefIsLocked(CRDFCoordinator::Pref_ShowNavCenterSelector)) : true;
  585.             ::GetIndString(outName, BROWSER_MENU_TOGGLE_STRINGS_ID, (mNavCenterParent->NavCenterSelector().IsShelfOpen() ? HIDE_NAVCENTER_STRING : SHOW_NAVCENTER_STRING));
  586.             break;
  587.             
  588.         case cmd_NetSearch:
  589.             outEnabled = (mContext) ? !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp) : true;
  590.             break;
  591.         
  592.         case cmd_Stop:
  593.         {
  594.             // Default name is STOP_LOADING_INDEX
  595.                 
  596.             ::GetIndString(outName, STOP_STRING_LIST, STOP_LOADING_INDEX );
  597.             
  598.             if (mContext)
  599.             {
  600.                 if (XP_IsContextStoppable((MWContext*) (*mContext)))
  601.                 {
  602.                     outEnabled = true;
  603.                 }
  604.                 else if (mContext->IsContextLooping())
  605.                 {
  606.                     outEnabled = true;
  607.                 
  608.                     ::GetIndString(outName, STOP_STRING_LIST, STOP_ANIMATIONS_INDEX );
  609.                 }
  610.             }
  611.             break;
  612.         }
  613.         
  614. #ifdef EDITOR
  615.         case cmd_EditFrameSet:
  616.         case cmd_EditDocument:
  617.         {
  618.             if ((mContext != nil) && !(XP_IsContextBusy(*mContext)) && !Memory_MemoryIsLow())
  619.                 outEnabled = !(mIsRootDocInfo || mIsViewSource || mIsHTMLHelp);
  620.             break;
  621.         }
  622. #endif // EDITOR
  623.         
  624.         case cmd_PageServices:
  625.             outEnabled = mSupportsPageServices;
  626.             break;
  627.         
  628.         default:
  629.         {
  630.             if(inCommand >= ENCODING_BASE && inCommand < ENCODING_CEILING)
  631.             {
  632.                 // Delegate this to the view.
  633.                 GetHTMLView()->FindCommandStatus(inCommand, outEnabled, outUsesMark, outMark, outName);
  634.             }
  635.             else
  636.                 CNetscapeWindow::FindCommandStatus(inCommand, outEnabled, outUsesMark, outMark, outName);
  637.         }
  638.     }
  639. }
  640.  
  641. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  642. //    Ñ    
  643. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  644.  
  645. // Revised to handle back, forward, home, reload through AppleEvents - 1997-02-26 mjc
  646. Boolean    CBrowserWindow::ObeyCommand(
  647.     CommandT            inCommand,
  648.     void                *ioParam)
  649. {
  650.     LCommander    *target;
  651.     Boolean        cmdHandled = false;
  652.     // check for synthetic commands from history items
  653.     if (CHistoryMenu::IsHistoryMenuSyntheticCommandID(inCommand) && mContext != NULL)
  654.     {
  655.         // Compute correct history list index.
  656.         // Menu item number - last non-dynamic menu item number is
  657.         // index to history entry starting from the *END* of history list --
  658.         // because we list history entries in menu bar starting with the most
  659.         // recent history entry at the top which is at the end of the history list in the
  660.         // MWContext. Therefore, compute correct history list index before calling
  661.         // CNSContext::LoadHistoryEntry
  662.         Int32 histIndex = mContext->GetHistoryListCount() -
  663.                           (CHistoryMenu::GetFirstSyntheticCommandID() - inCommand);
  664.         // histIndex should now be the one-based index to the history entry we want
  665.         // starting from the beginning of the list.
  666.         mContext->LoadHistoryEntry(histIndex);
  667.         cmdHandled = true;
  668.     }
  669.     else
  670.     {
  671.         switch (inCommand)
  672.         {
  673.             case cmd_Print:
  674.             case cmd_PrintOne:
  675.                 // if the current target happens to be a subview of our main HTMLView, let it
  676.                 // handle the command.  else, hand it to our main HTML view.
  677.                 target = LCommander::GetTarget();
  678.                 while (target && target != GetHTMLView())
  679.                     target = target->GetSuperCommander();
  680.                 if (target == GetHTMLView())
  681.                     LCommander::GetTarget()->ObeyCommand (inCommand, ioParam);
  682.                 else
  683.                     GetHTMLView()->ObeyCommand (inCommand, ioParam);
  684.                 break;
  685.             case cmd_ViewSource:
  686.             case cmd_Find:
  687.             case cmd_AddToBookmarks:
  688.             case cmd_SaveAs:
  689.             case cmd_SecurityInfo:
  690.             case cmd_DocumentInfo:
  691.             case cmd_MailDocument:
  692.             case cmd_LoadImages:
  693.             case cmd_FTPUpload:
  694.                 {
  695.                     // Delegate this to the view.
  696.                     GetHTMLView()->ObeyCommand(inCommand, ioParam);
  697.                 }
  698.                 break;
  699.                 
  700.             case cmd_GoForward:
  701.                 if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey))
  702.                 {
  703.                     if (mContext)
  704.                     {
  705.                         mContext->GoForwardOneHost();
  706.                     }
  707.                 }
  708.                 else
  709.                 {
  710.                     SendAEGo(kAENext);
  711.                 }
  712.                 cmdHandled = true;
  713.                 break;
  714.                 
  715.             case cmd_GoBack:
  716.                 if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey))
  717.                 {
  718.                     if (mContext)
  719.                     {
  720.                         mContext->GoBackOneHost();
  721.                     }
  722.                 }
  723.                 else
  724.                 {
  725.                     SendAEGo(kAEPrevious);
  726.                 }
  727.                 cmdHandled = true;
  728.                 break;
  729.                 
  730.             case cmd_Home:
  731.                 SendAEGo(AE_www_go_home);
  732.                 
  733.                 // ÑÑÑ what the hell is this?    deeje 97-03-06
  734.                 // cmdHandled = CNetscapeWindow::ObeyCommand(inCommand, ioParam);
  735.                 break;
  736.                 
  737.             case cmd_NetSearch:
  738.                 HandleNetSearchCommand();
  739.                 break;
  740.                             
  741.             case cmd_ToggleToolbar:
  742.                 ToggleDragBar(Button_Bar_PaneID, eNavigationBar, Pref_ShowToolbar);
  743.                 cmdHandled = true;
  744.                 break;
  745.             
  746.             case cmd_ToggleURLField:
  747.                 ToggleDragBar(Location_Bar_PaneID, eLocationBar, Pref_ShowLocationBar);
  748.                 cmdHandled = true;
  749.                 break;
  750.  
  751.             case cmd_TogglePersonalToolbar:
  752.                 ToggleDragBar(PersonalToolbar_PaneID, ePersonalToolbar, Pref_ShowPersonalToolbar);
  753.                 cmdHandled = true;
  754.                 break;
  755.                 
  756.             case cmd_NCToggle:
  757.                 // Note that this allows the user to hide the selector while the shelf is 
  758.                 // still open. This isn't the end of the world, at least, because the closebox
  759.                 // is there so the user can still figure out how to get rid of it and
  760.                 // close it if they want.
  761.                 mNavCenterParent->NavCenterSelector().ToggleShelf();
  762.                 cmdHandled = true;
  763.                 break;
  764.                                 
  765.             case cmd_Reload:
  766.             {
  767.                 if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey) ||
  768.                     CApplicationEventAttachment::CurrentEventHasModifiers(shiftKey))
  769.                 {
  770.                     SendAEGo(AE_www_super_reload);
  771.                 }
  772.                 else
  773.                 {
  774.                     SendAEGo(AE_www_go_again);
  775.                 }
  776.                 cmdHandled = true;
  777.                 break;
  778.             }
  779.             
  780.             case cmd_Stop:
  781.             {
  782.                 TrySetCursor(watchCursor);
  783.                 XP_InterruptContext(*mContext);
  784.                 SetCursor( &qd.arrow );
  785.                 cmdHandled = true;
  786.                 break;
  787.             }
  788.             
  789. #ifdef EDITOR
  790.             case cmd_EditFrameSet:
  791.             case cmd_EditDocument:
  792.                 MWContext *frontWindowMWContext;
  793.                 frontWindowMWContext = XP_GetNonGridContext( GetWindowContext()->operator MWContext*() );
  794.                 CEditorWindow::MakeEditWindowFromBrowser( frontWindowMWContext );
  795.                 cmdHandled = true;
  796.             break;
  797. #endif // EDITOR
  798.  
  799.             case cmd_SaveDefaultCharset:
  800.             {
  801.                 Int32 default_csid = GetDefaultCSID();
  802.                 CPrefs::SetLong(default_csid, CPrefs::DefaultCharSetID);
  803.             }
  804.             break;
  805.                         
  806.             case cmd_PageServices:
  807.             {
  808.                 char* url = SHIST_GetCurrentPageServicesURL(*mContext);
  809.                 if (url)
  810.                 {
  811.                     URL_Struct* newURL = NET_CreateURLStruct(url, NET_DONT_RELOAD);
  812.                     if (newURL)
  813.                         mContext->SwitchLoadURL(newURL, FO_CACHE_AND_PRESENT);
  814.                 }
  815.             }
  816.             break;
  817.  
  818.             default:
  819.             {
  820.                 if ( inCommand > ENCODING_BASE && inCommand < ENCODING_CEILING )
  821.                 {
  822.                     // Delegate this to the view.
  823.                     GetHTMLView()->SetDefaultCSID(CPrefs::CmdNumToDocCsid(inCommand));
  824.                     cmdHandled = true;
  825.                 }
  826.                 else
  827.                     cmdHandled = CNetscapeWindow::ObeyCommand(inCommand, ioParam);
  828.                 break;
  829.             }
  830.             
  831.         } // case of which command
  832.     } // else not a history command
  833.  
  834.     return cmdHandled;
  835. }
  836.  
  837. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  838. //    Ñ    
  839. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  840.  
  841. void CBrowserWindow::ListenToMessage(MessageT inMessage, void* ioParam)
  842. {
  843.     switch (inMessage)
  844.         {
  845.         case msg_NSCDocTitleChanged:
  846.             NoteDocTitleChanged((const char*)ioParam);
  847.             break;
  848.         
  849.         case msg_NSCLayoutNewDocument:
  850.             NoteBeginLayout();
  851.             break;
  852.         
  853.         case msg_NSCFinishedLayout:
  854.             NoteFinishedLayout();
  855.             break;
  856.         
  857.         case msg_NSCAllConnectionsComplete:
  858.             NoteAllConnectionsComplete();
  859.             break;
  860.         
  861.         case msg_UserSubmittedURL:
  862.             // user hit enter or return in URL edit field
  863.             CStr255* urlString = (CStr255*)ioParam;
  864.             if (urlString && mContext)
  865.             {
  866.             /*        old way
  867.                 URL_Struct* theURL =
  868.                     NET_CreateURLStruct(*urlString, NET_DONT_RELOAD);
  869.                 mContext->SwitchLoadURL(theURL, FO_CACHE_AND_PRESENT);
  870.             */
  871.                 if (!urlString->IsEmpty())
  872.                     SendAEGetURL(*urlString);
  873.             }
  874.             break;
  875.         
  876.         case cmd_GoForward:
  877.         case cmd_GoBack:
  878.         case cmd_Home:
  879.         case cmd_Reload:
  880.         case cmd_Stop:
  881.         case cmd_LoadImages:
  882.         case cmd_Print:
  883.         case cmd_CoBrandLogo:
  884.         case cmd_NetSearch:
  885.         case cmd_SecurityInfo:
  886.         case LOGO_BUTTON:
  887.             ObeyCommand(inMessage, ioParam);
  888.             break;
  889.         }
  890. }
  891.  
  892.  
  893.  
  894.  
  895.  
  896. void CBrowserWindow::AttemptClose()
  897. {
  898.     if (HasProcess(fCloseNotifier))    // If someone has registered for window closing, notify them
  899.     Try_
  900.     {
  901.         AEAddressDesc     closeApp;
  902.         AppleEvent         closeEvent;
  903.         Int32            aWindowID = mContext->GetContextUniqueID();
  904.         
  905.         OSErr err = ::AECreateDesc(typeProcessSerialNumber, &fCloseNotifier, 
  906.                              sizeof(fCloseNotifier), &closeApp);
  907.         ThrowIfOSErr_(err);
  908.         err = ::AECreateAppleEvent(AE_spy_send_suite, AE_spy_winClosed,
  909.                                     &closeApp,
  910.                                     kAutoGenerateReturnID,
  911.                                     kAnyTransactionID,
  912.                                     &closeEvent);
  913.         ThrowIfOSErr_(err);
  914.         
  915.             // windowID is the direct object
  916.         err = ::AEPutParamPtr(&closeEvent, keyDirectObject,
  917.                     typeLongInteger, &aWindowID, sizeof(aWindowID));
  918.         ThrowIfOSErr_(err);
  919.         
  920.         // Are we quitting is another parameter
  921.         Boolean quitting = (CFrontApp::GetApplication()->GetState() == programState_Quitting);
  922.         err =::AEPutParamPtr(&closeEvent, AE_spy_winClosedExiting, typeBoolean,
  923.                 &quitting, sizeof(quitting));
  924.         ThrowIfOSErr_(err);
  925.         
  926.             // send the event
  927.         AppleEvent reply;
  928.         ::AESend(&closeEvent,&reply,kAENoReply,kAENormalPriority,0,nil, nil);
  929.     }
  930.     Catch_(inErr){}
  931.     EndCatch_
  932.  
  933.     AttemptCloseWindow();
  934.     CMediatedWindow::AttemptClose();
  935. }
  936.  
  937.  
  938. // modified so z-locked window will not automatically be selected - mjc
  939. void
  940. CBrowserWindow::Select()
  941. {
  942.     if (!mZLocked)
  943.     {
  944.         SendSelfAE(kAEMiscStandards, kAESelect, false);
  945.         UDesktop::SelectDeskWindow(this);
  946.     }
  947. }
  948.  
  949.  
  950. //
  951. // ActivateSelf
  952. //
  953. // When this window comes to the front, we want to make sure that RDF knows about this window's
  954. // context so that navCenter windows can display the site map info correctly for this window.
  955. //
  956. // Make sure not to do this for floating windows or for editor windows.
  957. //
  958. void
  959. CBrowserWindow::ActivateSelf ( )
  960. {
  961.     super::ActivateSelf();
  962.     if ( mNavCenterParent && !HasAttribute(windAttr_Floating) )
  963.         XP_SetLastActiveContext ( *GetWindowContext() );
  964. }
  965.  
  966.  
  967. // ClickInDrag modified so z-locked window will not automatically be selected - mjc
  968. void    
  969. CBrowserWindow::ClickInDrag(const EventRecord &inMacEvent)
  970. {
  971.     if (mZLocked) 
  972.     {
  973.         EventRecord filterMacEvent = inMacEvent;
  974.         filterMacEvent.modifiers = filterMacEvent.modifiers | cmdKey; // command-key modifier disables select
  975.         super::ClickInDrag(filterMacEvent);
  976.     }
  977.     else super::ClickInDrag(inMacEvent);
  978. }
  979.  
  980. // Allow us to restrict user from growing the window by setting the Resizable attribute,
  981. // even if there is a grow box.
  982. void            
  983. CBrowserWindow::ClickInGrow(const EventRecord &inMacEvent)
  984. {
  985.     if (HasAttribute(windAttr_Resizable))
  986.         super::ClickInGrow(inMacEvent);
  987. }
  988.  
  989. // Return the window for the top-level context of the one passed in.
  990. CBrowserWindow*    
  991. CBrowserWindow::WindowForContext(CBrowserContext* inContext)
  992. {
  993.     if (inContext == NULL) return NULL;
  994.     
  995.     CMediatedWindow* theIterWindow = NULL;
  996.     DataIDT windowType = WindowType_Browser;
  997.     CWindowIterator theWindowIterator(windowType);
  998.     
  999.     CBrowserContext* theTopContext = inContext->GetTopContext();
  1000.     
  1001.     while (theWindowIterator.Next(theIterWindow))
  1002.         {
  1003.         CBrowserWindow* theBrowserWindow = dynamic_cast<CBrowserWindow*>(theIterWindow);
  1004.         CNSContext* theCurrentContext = theBrowserWindow->GetWindowContext();
  1005.         if (theBrowserWindow->GetWindowContext() == theTopContext)
  1006.             {
  1007.                 return theBrowserWindow;
  1008.             break;
  1009.             }
  1010.         }
  1011.     return NULL;
  1012. }
  1013.  
  1014. // Retrieve a window with the given Window ID
  1015. //        In : ID of window
  1016. //        Out: Pointer returned.        (ct hull)
  1017. //  GetWindowByID
  1018. // return the window for the context.
  1019. CBrowserWindow*    
  1020. CBrowserWindow::GetWindowByID(const Int32 windowID)
  1021. {
  1022.     CMediatedWindow* theIterWindow = NULL;
  1023.     DataIDT windowType = WindowType_Browser;
  1024.     CWindowIterator theWindowIterator(windowType);
  1025.     while (theWindowIterator.Next(theIterWindow))
  1026.         {
  1027.         CBrowserWindow* theBrowserWindow = dynamic_cast<CBrowserWindow*>(theIterWindow);
  1028.         CNSContext* theCurrentContext = theBrowserWindow->GetWindowContext();
  1029.         if (theCurrentContext->GetContextUniqueID() == windowID)
  1030.             {
  1031.                 return theBrowserWindow;
  1032.             break;
  1033.             }
  1034.         }
  1035.     return NULL;
  1036. }
  1037.  
  1038. Boolean
  1039. CBrowserWindow::IsRestrictedTarget(void)
  1040. {
  1041.     return mContext->IsRestrictedTarget();
  1042. }
  1043.  
  1044. // override to send javascript move, resize, and zoom events
  1045. void    
  1046. CBrowserWindow::DoSetPosition(Point inPosition)
  1047. {
  1048.     super::DoSetPosition(inPosition);
  1049.  
  1050.     if (mContext != NULL) 
  1051.     {
  1052.         Rect bounds;
  1053.         bounds = UWindows::GetWindowStructureRect(GetMacPort());
  1054.         CMochaHacks::SendMoveEvent(*mContext, bounds.left, bounds.top - ::GetMBarHeight());
  1055.     }
  1056. }
  1057.  
  1058. void    
  1059. CBrowserWindow::DoSetBounds(const Rect &inBounds)
  1060. {
  1061.                                     // inBounds is in global coordinates
  1062.                                     
  1063.                                     // Early exit if the bounds have not
  1064.                                     //   really changed.
  1065.     Rect bounds = UWindows::GetWindowContentRect(GetMacPort());
  1066.     
  1067.     if (::EqualRect(&bounds, &inBounds))
  1068.         return;
  1069.     
  1070.     Boolean didMove = (bounds.top != inBounds.top) || (bounds.left != inBounds.left);
  1071.     
  1072.                                     // Set size and location of Toolbox
  1073.                                     //   WindowRecord
  1074.     ::SizeWindow(mMacWindowP, inBounds.right - inBounds.left,
  1075.                 inBounds.bottom - inBounds.top, false);
  1076.     ::MoveWindow(mMacWindowP, inBounds.left, inBounds.top, false);
  1077.     
  1078.                                     // Set our Frame
  1079.     ResizeFrameTo(inBounds.right - inBounds.left,
  1080.                 inBounds.bottom - inBounds.top, true);
  1081.  
  1082.     SDimension16    frameSize;        // For Windows, Image is always the
  1083.     GetFrameSize(frameSize);        //   same size as its Frame
  1084.     ResizeImageTo(frameSize.width, frameSize.height, false);
  1085.     
  1086.                                     // Changing Bounds establishes a
  1087.                                     //   new User state for zooming
  1088.     CalcPortFrameRect(mUserBounds);
  1089.     PortToGlobalPoint(topLeft(mUserBounds));
  1090.     PortToGlobalPoint(botRight(mUserBounds));
  1091.     mMoveOnlyUserZoom = false;
  1092.  
  1093.  
  1094.     if (mContext != NULL) 
  1095.     {
  1096.         Rect structureBounds = UWindows::GetWindowStructureRect(GetMacPort());
  1097.         if (didMove)
  1098.             CMochaHacks::SendMoveEvent(*mContext, structureBounds.left, structureBounds.top - ::GetMBarHeight());
  1099.         //CMochaHacks::SendResizeEvent(*mContext, structureBounds.right - structureBounds.left, structureBounds.bottom - structureBounds.top);
  1100.     }
  1101. }
  1102.  
  1103. void    
  1104. CBrowserWindow::DoSetZoom(Boolean inZoomToStdState)
  1105. {
  1106.     if (!HasAttribute(windAttr_Zoomable)) {
  1107.         ThrowOSErr_(errAENotModifiable);
  1108.     }
  1109.  
  1110.     Rect    currBounds = UWindows::GetWindowContentRect(mMacWindowP);
  1111.     Rect    zoomBounds;
  1112.  
  1113.     if (CApplicationEventAttachment::CurrentEventHasModifiers(optionKey))
  1114.     {
  1115.         
  1116.         StValueChanger<Int16> changeStandardWidth(mStandardSize.width, max_Int16); 
  1117.         StValueChanger<Int16> changeStandardHeight(mStandardSize.height, max_Int16); 
  1118.  
  1119.         CalcStandardBounds(zoomBounds);
  1120.     
  1121.     
  1122.                                         // Changing bounds via option-zoom
  1123.                                         //   establishes a new User state
  1124.                                         //   for zooming
  1125.         mUserBounds = zoomBounds;
  1126.     }
  1127.     else
  1128.     {
  1129.         if (inZoomToStdState) {            // Zoom to Standard state
  1130.             if (CalcStandardBounds(zoomBounds)) {
  1131.                 return;                    // Already at Standard state
  1132.             }
  1133.             
  1134.         } else {                        // Zoom to User state
  1135.             zoomBounds = mUserBounds;
  1136.             
  1137.             if (mMoveOnlyUserZoom) {    // Special case for zooming a Window
  1138.                                         //   that is at standard size, but
  1139.                                         //   is partially offscreen
  1140.                 zoomBounds.right = zoomBounds.left +
  1141.                                     (currBounds.right - currBounds.left);
  1142.                 zoomBounds.bottom = zoomBounds.top +
  1143.                                     (currBounds.bottom - currBounds.top);
  1144.             }
  1145.         }
  1146.     }
  1147.     
  1148.     Int16    zoomWidth = zoomBounds.right - zoomBounds.left;
  1149.     Int16    zoomHeight = zoomBounds.bottom - zoomBounds.top;
  1150.     mMoveOnlyUserZoom = false;
  1151.     
  1152.         // To avoid unnecessary redraws, we check to see if the
  1153.         // current and zoom states are either the same size
  1154.         // or at the same location
  1155.         
  1156.     if ( ((currBounds.right - currBounds.left) == zoomWidth) &&
  1157.          ((currBounds.bottom - currBounds.top) == zoomHeight) ) {
  1158.                                     // Same size, just move
  1159.         ::MoveWindow(mMacWindowP, zoomBounds.left, zoomBounds.top, false);
  1160.         mMoveOnlyUserZoom = true;
  1161.     
  1162.     } else if (::EqualPt(topLeft(currBounds), topLeft(zoomBounds))) {
  1163.                                     // Same location, just resize
  1164.         ::SizeWindow(mMacWindowP, zoomWidth, zoomHeight, false);
  1165.         ResizeFrameTo(zoomWidth, zoomHeight, true);
  1166.         
  1167.     } else {                        // Different size and location
  1168.                                     // Zoom appropriately
  1169.         FocusDraw();
  1170.         ApplyForeAndBackColors();
  1171.         ::EraseRect(&mMacWindowP->portRect);
  1172.         if (inZoomToStdState) {
  1173.             SetWindowStandardState(mMacWindowP, &zoomBounds);
  1174.             ::ZoomWindow(mMacWindowP, inZoomOut, false);
  1175.         } else {
  1176.             SetWindowUserState(mMacWindowP, &zoomBounds);
  1177.             ::ZoomWindow(mMacWindowP, inZoomIn, false);
  1178.         }
  1179.         ResizeFrameTo(zoomWidth, zoomHeight, false);
  1180.     }
  1181.     
  1182.     if (mContext != NULL) 
  1183.     {
  1184.         Rect bounds;
  1185.         bounds = UWindows::GetWindowStructureRect(GetMacPort());
  1186.         CMochaHacks::SendMoveEvent(*mContext, bounds.left, bounds.top - ::GetMBarHeight());
  1187.         //CMochaHacks::SendResizeEvent(*mContext, bounds.right - bounds.left, bounds.bottom - bounds.top);
  1188.     }
  1189. }
  1190.  
  1191. // ---------------------------------------------------------------------------
  1192. //        Ñ CalcStandardBoundsForScreen
  1193. // ---------------------------------------------------------------------------
  1194.  
  1195. void
  1196. CBrowserWindow::CalcStandardBoundsForScreen(
  1197.     const Rect&    inScreenBounds,
  1198.     Rect&        outStdBounds) const
  1199. {
  1200.     CHTMLView*            theHTMLView = nil;
  1201.     CBrowserContext*    theTopContext = nil;
  1202.     
  1203.     theTopContext = dynamic_cast<CBrowserContext*>(mContext->GetTopContext());
  1204.     if (theTopContext)
  1205.     {
  1206.         theHTMLView = ::ExtractHyperView((MWContext*)(*theTopContext));
  1207.     }
  1208.  
  1209.     StValueChanger<Int16> saveStandardWidth(const_cast<CBrowserWindow*>(this)->mStandardSize.width, max_Int16); 
  1210.     StValueChanger<Int16> saveStandardHeight(const_cast<CBrowserWindow*>(this)->mStandardSize.height, max_Int16); 
  1211.  
  1212.     CHTMLView::CalcStandardSizeForWindowForScreen(
  1213.                                         theHTMLView,
  1214.                                         *this,
  1215.                                         inScreenBounds,
  1216.                                         const_cast<CBrowserWindow*>(this)->mStandardSize);
  1217.     
  1218.     // Calculate standard bounds given standard size
  1219.     
  1220.     super::CalcStandardBoundsForScreen(inScreenBounds, outStdBounds);
  1221. }
  1222.  
  1223. // dynamically show/hide the status bar - mjc
  1224. void            
  1225. CBrowserWindow::ShowStatus(Chrome* inChromeInfo)
  1226. {
  1227.     LPane*             theSWatchStuff = FindPaneByID(SWatch_View_PaneID);
  1228.     LPane*            theStatusBar = FindPaneByID(Status_Bar_PaneID);
  1229.     
  1230.     // Ñ show or hide status bar
  1231.     if (theStatusBar != nil && theSWatchStuff != nil)
  1232.     {
  1233.         if (!inChromeInfo->show_bottom_status_bar) // status=no
  1234.         {
  1235.             // FIXME grow box draws correctly?
  1236.             if (mToolbarShown[eStatusBar])
  1237.             {
  1238.                 SDimension16        theStatusSize = {0, 0};
  1239.                 theStatusBar->GetFrameSize(theStatusSize);
  1240.                 theStatusBar->Hide();
  1241.                 theSWatchStuff->ResizeFrameBy(0, theStatusSize.height, false);
  1242.                 mToolbarShown[eStatusBar] = false;
  1243.                 // 97-05-12 pkc -- have CHyperScroller handle grow icon if we're
  1244.                 // resizeable
  1245.                 // 97-06-05 pkc -- hide size box because it looks bad
  1246.                 ClearAttribute(windAttr_SizeBox);
  1247.                 if (inChromeInfo->allow_resize)
  1248.                 {
  1249.                     CHyperScroller* scroller = dynamic_cast<CHyperScroller*>(FindPaneByID(Hyper_Scroller_PaneID));
  1250.                     if (scroller)
  1251.                         scroller->SetHandleGrowIconManually(true);
  1252.                 }
  1253.             }
  1254.         }
  1255.         else if (!mToolbarShown[eStatusBar]) // status=yes
  1256.         {
  1257.             // we want to show status bar, but it's currently hidden
  1258.             SDimension16        theStatusSize = {0, 0};
  1259.             theStatusBar->Show();
  1260.             theStatusBar->GetFrameSize(theStatusSize);
  1261.             theSWatchStuff->ResizeFrameBy(0, -theStatusSize.height, false);
  1262.             mToolbarShown[eStatusBar] = true;
  1263.             // 97-05-12 pkc -- tell CHyperScroller not to handle grow icon if we're
  1264.             // resizeable
  1265.             if (inChromeInfo->allow_resize)
  1266.             {
  1267.                 CHyperScroller* scroller = dynamic_cast<CHyperScroller*>(FindPaneByID(Hyper_Scroller_PaneID));
  1268.                 if (scroller)
  1269.                 {
  1270.                     SetAttribute(windAttr_SizeBox);
  1271.                     scroller->SetHandleGrowIconManually(false);
  1272.                 }
  1273.                 // make sure we turn on bevelling of grow icon area
  1274.                 SetSystemGrowIconBevel();
  1275.             }
  1276.             else
  1277.                 ClearAttribute(windAttr_SizeBox);            
  1278.         }
  1279.         else if (!inChromeInfo->allow_resize)
  1280.         {
  1281.             // we want to show status bar, it's already showing, and we don't
  1282.             // want it resizeable
  1283.             ClearAttribute(windAttr_SizeBox);
  1284.             // also clear bevelling of grow icon area
  1285.             ClearSystemGrowIconBevel();
  1286.         }
  1287.     }
  1288. }
  1289.     
  1290. // dynamically show/hide the drag bars - mjc (without changing pref value)
  1291. // modified to synchronize with menu items by using ShowOneDragBar and mToolbarShown - 1997-02-27 mjc
  1292. void            
  1293. CBrowserWindow::ShowDragBars(Boolean inShowNavBar, Boolean inShowLocBar, Boolean inShowPersToolbar)
  1294. {
  1295.     ShowOneDragBar(Button_Bar_PaneID, inShowNavBar);
  1296.     mToolbarShown[eNavigationBar] = inShowNavBar;
  1297.  
  1298.     ShowOneDragBar(Location_Bar_PaneID, inShowLocBar);
  1299.     mToolbarShown[eLocationBar] = inShowLocBar;
  1300.     
  1301.     ShowOneDragBar(PersonalToolbar_PaneID, inShowPersToolbar);
  1302.     mToolbarShown[ePersonalToolbar] = inShowPersToolbar;    
  1303. }
  1304.  
  1305. void
  1306. CBrowserWindow::ClearSystemGrowIconBevel()
  1307. {
  1308.     CBevelView* statusArea = dynamic_cast<CBevelView*>(FindPaneByID('StBv'));
  1309.     if (statusArea)
  1310.         statusArea->DontBevelGrowIcon();
  1311. }
  1312.  
  1313. void
  1314. CBrowserWindow::SetSystemGrowIconBevel()
  1315. {
  1316.     CBevelView* statusArea = dynamic_cast<CBevelView*>(FindPaneByID('StBv'));
  1317.     if (statusArea)
  1318.         statusArea->BevelGrowIcon();
  1319. }
  1320.  
  1321. // set up the window based on the chrome structure
  1322. // this may be called more than once.
  1323. void CBrowserWindow::SetChromeInfo(Chrome* inChrome, Boolean inNotifyMenuBarModeChanged, Boolean inFirstTime)
  1324. {
  1325.     LPane*        theHTMLContainer = FindPaneByID(HTML_Container_PaneID);
  1326.     LPane* theSWatchStuff = FindPaneByID(SWatch_View_PaneID);
  1327.     CHyperScroller* theScroller = (CHyperScroller*)FindPaneByID(Hyper_Scroller_PaneID);
  1328.  
  1329.     if (inChrome != nil)
  1330.     {
  1331.         Assert_(mMacWindowP != NULL);
  1332.         Rect        windowBounds = {0, 0, 0, 0};
  1333.         Rect        contentBounds  = {0, 0, 0, 0};
  1334.         Rect        newWindowBounds = {0, 0, 0, 0};
  1335.         Rect        portRect = mMacWindowP->portRect;
  1336.         short         titlebarHeight, deltaWidth, deltaHeight;
  1337.         
  1338.         FocusDraw();
  1339.     
  1340.         // Ñ reposition bars based on chrome attributes. The "directory button" is really
  1341.         // the personal toolbar, though no one has thought to update the chrome structure yet.
  1342.         ShowDragBars(inChrome->show_button_bar, inChrome->show_url_bar, inChrome->show_directory_buttons);
  1343.         
  1344.         // Ñ show or hide scrollbars
  1345.         if (theScroller != nil)
  1346.         {
  1347.             if (inChrome->show_scrollbar)
  1348.                 GetHTMLView()->ResetScrollMode();
  1349.             else GetHTMLView()->SetScrollMode(LO_SCROLL_NEVER);
  1350.         }
  1351.         
  1352.         //ÑÑÑ This should be reflected in the Chrome data structure, but since I'm too scared to
  1353.         // touch it, we can hack it so that if the chrome says not to have a personal toolbar, then
  1354.         // we probably don't want the NavCenter showing up. Don't let this temporary setting of
  1355.         // the shelf states affect the global preference, however.
  1356.         if ( mNavCenterParent ) {
  1357.             if ( !inChrome->show_directory_buttons ) {
  1358.                 mNavCenterParent->NavCenterShelf().SetShelfState(CShelf::kClosed, false);
  1359.                 mNavCenterParent->NavCenterSelector().SetShelfState(CShelf::kClosed, false);
  1360.             }
  1361.             else
  1362.                 mNavCenterParent->NavCenterSelector().SetShelfState(CShelf::kOpen, false);
  1363.         }
  1364.         ShowStatus(inChrome);
  1365.         
  1366.         // w_hint and h_hint are inner dimensions (html view).
  1367.         // outw_hint and outh_hint are outer dimensions (window structure).
  1368.         // l_hint and t_hint are position of window structure.
  1369.         // location_is_chrome will always be set for positioning so that {0,0} 
  1370.         // positioning is possible (i.e. we know the chrome record is not just zeroed out).
  1371.         // ALERT: positioning applies menubar height regardless of multiple monitor situation.
  1372.         
  1373.         windowBounds = UWindows::GetWindowStructureRect(GetMacPort());
  1374.         contentBounds = UWindows::GetWindowContentRect(GetMacPort());
  1375.         // if the window is windowshaded then correct the windowBounds because height of content is zero.
  1376.         if (IsVisible() && HasAttribute(windAttr_TitleBar) && ::EmptyRgn(((WindowPeek)GetMacPort())->contRgn))
  1377.         {
  1378.             short lostHeight = portRect.bottom - portRect.top; // portRect is immune to windowshading
  1379.             windowBounds.bottom = windowBounds.bottom + lostHeight;
  1380.             contentBounds.bottom = contentBounds.bottom + lostHeight;
  1381.         }
  1382.         deltaWidth = (windowBounds.right - windowBounds.left) - (contentBounds.right - contentBounds.left); // difference of width of structure and content
  1383.         deltaHeight = (windowBounds.bottom - windowBounds.top) - (contentBounds.bottom - contentBounds.top); // difference of height of structure and content
  1384.         titlebarHeight = contentBounds.top - windowBounds.top;
  1385.         
  1386.         // convert newWindowBounds to the content rect suitable for passing to DoSetBounds().
  1387.         if ((inChrome->outw_hint && inChrome->outh_hint) ||
  1388.             (inChrome->w_hint && inChrome->h_hint) ||
  1389.             (inChrome->location_is_chrome)) // reposition is intended
  1390.         {
  1391.             RgnHandle desktopRgnH = ::GetGrayRgn(); // max size of window is size of desktop region
  1392.             short maxWidth = MAX((**desktopRgnH).rgnBBox.right - (**desktopRgnH).rgnBBox.left, 100);
  1393.             short maxHeight = MAX((**desktopRgnH).rgnBBox.bottom - (**desktopRgnH).rgnBBox.top, 100);
  1394.  
  1395.             if (inChrome->location_is_chrome) { // position if specified
  1396.                 newWindowBounds.left = inChrome->l_hint + contentBounds.left - windowBounds.left;
  1397.                 newWindowBounds.top = inChrome->t_hint + titlebarHeight + ::GetMBarHeight();
  1398.             }
  1399.             else {
  1400.                 newWindowBounds.left = contentBounds.left;
  1401.                 newWindowBounds.top = contentBounds.top;
  1402.             }
  1403.  
  1404.             // set outer dimensions if specified or inner dimensions. Prevent a non-resizable
  1405.             // window from being resized unless it's the first time we're setting chrome info.
  1406.             if ((inChrome->outw_hint > 0) && 
  1407.                 (inChrome->outh_hint > 0) && 
  1408.                 (inChrome->allow_resize || inFirstTime)) // outer dimensions both > 0
  1409.             {
  1410.                 // pin the window dimensions specified in the chrome to the maximum dimensions
  1411.                 inChrome->outw_hint = MIN(maxWidth, inChrome->outw_hint);
  1412.                 inChrome->outh_hint = MIN(maxHeight, inChrome->outh_hint);
  1413.                 newWindowBounds.right = MIN(SHRT_MAX, newWindowBounds.left + inChrome->outw_hint - deltaWidth);
  1414.                 newWindowBounds.bottom = MIN(SHRT_MAX, newWindowBounds.top + inChrome->outh_hint - deltaHeight);
  1415.             }
  1416.             else if ((inChrome->w_hint > 0) && 
  1417.                         (inChrome->h_hint > 0) && 
  1418.                         (inChrome->allow_resize || inFirstTime)) // inner dimensions both > 0
  1419.             {
  1420.                 SDimension16 theInnerSize;
  1421.                 /* if (theScroller != nil) theScroller->GetFrameSize(theInnerSize);
  1422.                 else */ GetHTMLView()->GetFrameSize(theInnerSize);
  1423.                 // pin the window dimensions specified in the chrome to the maximum dimensions
  1424.                 inChrome->w_hint = MIN(maxWidth, inChrome->w_hint);
  1425.                 inChrome->h_hint = MIN(maxHeight, inChrome->h_hint);
  1426.                 newWindowBounds.right = MIN(SHRT_MAX, newWindowBounds.left + portRect.right - portRect.left + (inChrome->w_hint - theInnerSize.width));
  1427.                 newWindowBounds.bottom = MIN(SHRT_MAX, newWindowBounds.top + portRect.bottom - portRect.top + (inChrome->h_hint - theInnerSize.height));    
  1428.             }
  1429.             else // no dimensions specified, so get default dimensions from port rect.
  1430.             {
  1431.                 newWindowBounds.right = newWindowBounds.left + portRect.right - portRect.left;
  1432.                 newWindowBounds.bottom = newWindowBounds.top + portRect.bottom - portRect.top;
  1433.             }
  1434.             if (!::EqualRect(&newWindowBounds, &contentBounds)) 
  1435.                 DoSetBounds(newWindowBounds);
  1436.         }
  1437.         
  1438.         // Ñ set window attributes
  1439.         // the layout's window attributes don't necessarily specify floating so set it here.
  1440.         // z-lock means that the window cannot move in front of other windows in its layer.
  1441.         ClearAttribute(windAttr_Floating); // clear all the layer bits before we set again - 1997-02-28 mjc
  1442.         ClearAttribute(windAttr_Regular);
  1443.         ClearAttribute(windAttr_Modal);
  1444.         if (inChrome->topmost) // alwaysRaised=yes                
  1445.             SetAttribute(windAttr_Floating); // javascript under windows doesn't hide a topmost window so we won't either
  1446.         else SetAttribute(windAttr_Regular);
  1447.         
  1448.         if (inChrome->z_lock)
  1449.         {
  1450.             mZLocked = true;
  1451.             ClearAttribute(windAttr_DelaySelect);
  1452.             // z-locked window must be able to get the select click because it isn't selectable.
  1453.             SetAttribute(windAttr_GetSelectClick); 
  1454.         }
  1455.         else 
  1456.         {
  1457.             mZLocked = false;
  1458.             SetAttribute(windAttr_DelaySelect);
  1459.         }
  1460.         
  1461.         if (inChrome->bottommost && !inChrome->topmost)
  1462.         {
  1463.             // a bottommost window has to be in the regular layer.
  1464.             // if there is more than one regular window, we'll have to send it to the back.
  1465.             if (CWindowMediator::GetWindowMediator()->CountOpenWindows(
  1466.                                                             WindowType_Browser,
  1467.                                                             regularLayerType) > 1)
  1468.             {
  1469.                 if (UDesktop::FetchTopRegular() == this)
  1470.                     Deactivate();
  1471.                 ::SendBehind(GetMacPort(), NULL); // send to the back
  1472.                 // The following hack is based on UDesktop::Resume() and fixes a case where the
  1473.                 // window just sent to the back would be activated, when there is a floating
  1474.                 // window present.
  1475.                 LWindow* theTopWindow = UDesktop::FetchTopRegular();
  1476.                 if (theTopWindow != NULL)
  1477.                 {
  1478.                     theTopWindow->Activate();
  1479.                     LMSetCurActivate(nil);     // Suppress any Activate event
  1480.                 }
  1481.             }
  1482.             mAlwaysOnBottom = true;
  1483.             mZLocked = true; // bottommost implies z-lock
  1484.             ClearAttribute(windAttr_DelaySelect); // see z_lock for explanation
  1485.             SetAttribute(windAttr_GetSelectClick); 
  1486.         }
  1487.         else
  1488.         {
  1489.             mAlwaysOnBottom = false;
  1490.             if (mZLocked == false) SetAttribute(windAttr_DelaySelect);            
  1491.         }
  1492.         
  1493.         if (inChrome->hide_title_bar)
  1494.         { 
  1495.             // a titlebar-less window must get the click that selected it because there is 
  1496.             // little feedback that window is selected.
  1497.             SetAttribute(windAttr_GetSelectClick);
  1498.         }
  1499.         else if (!HasAttribute(windAttr_Floating))
  1500.         {
  1501.             SetAttribute(windAttr_Targetable); // window which has titlebar and is non-floating, is targetable.
  1502.         }
  1503.         
  1504.         // 97-05-08 pkc -- set windAttr_Modal flag appropriately
  1505.         if (inChrome->type == MWContextDialog)
  1506.         {
  1507.             AllowSubviewPopups (false);
  1508.             if (!mContext->IsSpecialBrowserContext())
  1509.                 SetAttribute(windAttr_Modal);
  1510.         }
  1511.         
  1512.         mIsRootDocInfo = mContext->IsRootDocInfoContext();
  1513.         mIsViewSource = mContext->IsViewSourceContext();
  1514.         
  1515.         // ÑÑÑ TODO: if we have the right security we should be able to set menubar mode to BrWn_Menubar_None
  1516.         if (inChrome->show_menu || mIsRootDocInfo || mIsViewSource)
  1517.             mMenubarMode = BrWn_Menubar_Default;
  1518.         else
  1519.             mMenubarMode = BrWn_Menubar_Minimal;
  1520.         
  1521.         // Ñ Broadcast that the menubar mode has changed
  1522.         if (inNotifyMenuBarModeChanged)
  1523.             NoteWindowMenubarModeChanged();
  1524.  
  1525.         mIsHTMLHelp = (inChrome->type == MWContextHTMLHelp);
  1526.         mCommandsDisabled = inChrome->disable_commands && !mIsHTMLHelp;
  1527.  
  1528.         if (inChrome->allow_resize && !HasAttribute(windAttr_Resizable))
  1529.         {
  1530.             Str255 desc;
  1531.             SetAttribute(windAttr_Resizable);
  1532.             if (!HasAttribute(windAttr_Floating))
  1533.             {
  1534.                 ((WindowPeek)GetMacPort())->spareFlag = true;     // enable zoom box
  1535.                 GetDescriptor(desc);                             // force titlebar update
  1536.                 SetDescriptor(desc);
  1537.             }
  1538.         } else if (!inChrome->allow_resize && HasAttribute(windAttr_Resizable))
  1539.         {
  1540.             Str255 desc;
  1541.             ClearAttribute(windAttr_Resizable);
  1542.             if (!HasAttribute(windAttr_Floating))
  1543.             {
  1544.                 ((WindowPeek)GetMacPort())->spareFlag = false;     // disable zoom box
  1545.                 GetDescriptor(desc);                             // force titlebar update
  1546.                 SetDescriptor(desc);
  1547.             }
  1548.         }
  1549.         
  1550.         Refresh();
  1551.     }
  1552.     else
  1553.     {
  1554.         // reset the window... but how?
  1555.     }
  1556. }
  1557.  
  1558. // Set the chrome structure based on window state - mjc
  1559. void CBrowserWindow::GetChromeInfo(Chrome* inChrome)
  1560. {
  1561.     // Ñ controls
  1562.     // modified to modified to synchronize with menu items by using mToolbarShown - 1997-02-27 mjc
  1563.     // The directory button bar is really the personal toolbar, though the chrome struct has yet to
  1564.     // be updated to reflect this change.
  1565.     inChrome->show_button_bar            = mToolbarShown[eNavigationBar];
  1566.     inChrome->show_url_bar               = mToolbarShown[eLocationBar];
  1567.     inChrome->show_directory_buttons     = mToolbarShown[ePersonalToolbar];
  1568.     inChrome->show_bottom_status_bar     = mToolbarShown[eStatusBar];
  1569.     inChrome->show_menu                  = mMenubarMode == BrWn_Menubar_Default;
  1570.     inChrome->show_security_bar          = FALSE; // ÑÑÑ always false in javascript?
  1571.     
  1572.     inChrome->hide_title_bar            = !HasAttribute(windAttr_TitleBar);
  1573.  
  1574.     // ÑÑÑ NEED SOMETHING HERE FOR THE NAV CENTER
  1575.     
  1576.     // Ñ position and size use window structure bounds
  1577.     Rect windowBounds = UWindows::GetWindowStructureRect(GetMacPort());
  1578.     // if the window is windowshaded then correct the windowBounds because height of content is zero.
  1579.     if (IsVisible() && HasAttribute(windAttr_TitleBar) && ::EmptyRgn(((WindowPeek)GetMacPort())->contRgn))
  1580.         windowBounds.bottom = windowBounds.bottom + mMacWindowP->portRect.bottom - mMacWindowP->portRect.top;
  1581.     
  1582.     inChrome->outw_hint                    = windowBounds.right - windowBounds.left;
  1583.     inChrome->outh_hint                    = windowBounds.bottom - windowBounds.top;
  1584.     inChrome->l_hint                      = windowBounds.left;
  1585.     inChrome->t_hint                      = windowBounds.top - ::GetMBarHeight();
  1586.     inChrome->location_is_chrome        = TRUE; // set to insure these coordinates are used.
  1587.     
  1588.     // Ñ window properties
  1589.     inChrome->topmost                      = this->HasAttribute(windAttr_Floating);
  1590.     //inChrome->bottommost              = 
  1591.     inChrome->z_lock                    = mZLocked;
  1592.     
  1593.     inChrome->is_modal                   = FALSE; // always FALSE in javascript
  1594.     inChrome->allow_resize               = HasAttribute(windAttr_Resizable);
  1595.     inChrome->allow_close                = TRUE; // always TRUE in javascript
  1596.     inChrome->disable_commands            = mCommandsDisabled;
  1597.     //inChrome->copy_history               = FALSE;    /* XXX need data tainting */
  1598.  
  1599.     // default values if there is no scroller of HTMLView
  1600.     inChrome->w_hint                    = inChrome->outw_hint;
  1601.     inChrome->h_hint                    = inChrome->outh_hint;
  1602.     inChrome->show_scrollbar            = FALSE;
  1603.     
  1604.     CHyperScroller* theScroller = (CHyperScroller*)FindPaneByID(Hyper_Scroller_PaneID);
  1605.     
  1606.     if (theScroller == NULL) return;
  1607.     
  1608.     SDimension16    theInnerSize;
  1609.     /* if (theScroller != nil) theScroller->GetFrameSize(theInnerSize);
  1610.     else */ GetHTMLView()->GetFrameSize(theInnerSize);
  1611.     
  1612.     inChrome->w_hint                    = theInnerSize.width;
  1613.     inChrome->h_hint                    = theInnerSize.height;
  1614.     
  1615.     inChrome->show_scrollbar            = (theScroller != nil) && (GetHTMLView()->GetScrollMode() != LO_SCROLL_NEVER);
  1616. }
  1617.  
  1618. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1619. //    Ñ    
  1620. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1621.         
  1622. void CBrowserWindow::NoteDocTitleChanged(const char* inNewTitle)
  1623. {
  1624.     CStr255 netscapeTitle;
  1625.     // Get Window title prefix
  1626.     ::GetIndString( netscapeTitle, ID_STRINGS, APPNAME_STRING_INDEX );
  1627.     netscapeTitle += ": ";
  1628.     // append title
  1629.     netscapeTitle += inNewTitle;
  1630.     SetDescriptor( netscapeTitle );
  1631. }
  1632.  
  1633. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1634. //    Ñ    
  1635. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1636.  
  1637. void CBrowserWindow::NoteBeginLayout(void)
  1638. {
  1639. //    
  1640. //    if (!is_grid)    // If we are laying out main new document, adjust the URLs
  1641. //    {
  1642. //        CStr31 newTitle = CFileMgr::FileNameFromURL (request->address);
  1643. //        SetDocTitle( newTitle );
  1644. //        
  1645. //        if ( fTopWrapper )
  1646. //            fTopWrapper->SetLayingOutURLCaption( CStr255( NET_URLStruct_Address( request ) ) , request->is_netsite);    
  1647. //        fHasTitle = FALSE;
  1648. //    }    
  1649. //    this->UpdateStatusBar();
  1650.  
  1651.     // ÑÑÑ TELL NAVCENTER ABOUT THE CHANGE?
  1652.  
  1653.     // 1997-05-22 brade -- context can be NULL
  1654.     if (mContext)
  1655.     {
  1656.         // 1997-05-02 pkc -- hack to select doc info window if we're laying it out.
  1657.         if (mContext->IsRootDocInfoContext())
  1658.             Select();
  1659.         // 1997-05-09 pkc -- set mSupportsPageServices
  1660.         mSupportsPageServices = mContext->SupportsPageServices();
  1661.     }
  1662. }
  1663.  
  1664. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1665. //    Ñ    
  1666. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1667.         
  1668. void CBrowserWindow::NoteFinishedLayout(void)
  1669. {
  1670.     // Do we need to do anything??
  1671.     // Ñ TELL NAVCENTER ABOUT THE CHANGE?
  1672. }
  1673.  
  1674. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1675. //    Ñ    
  1676. // ╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤╤
  1677.  
  1678. void CBrowserWindow::NoteAllConnectionsComplete(void)
  1679. {
  1680. //    NetscapeContext::AllConnectionsComplete();
  1681. //
  1682. //    HideProgressBar();
  1683. //
  1684. //    if (fProgress)
  1685. //        fProgress->SetValue(0);
  1686. //
  1687. //      this->SetMessage( CStr255( *GetString(DOCUMENT_DONE_RESID)) );
  1688. //    this->UpdateStatusBar();
  1689. //    this->StopSpinIcon();
  1690.  
  1691. //    CleanupImagesInTempMemory();
  1692. //    fHyperView->RepaginateIfNeeded();        // This is needed for grids. The main view gets
  1693.             // done before its subviews are done, so repagination never happens
  1694.     
  1695.     // CPaneEnabler::UpdatePanes();        // moved this to CHTMLView.cp  deeje 97-02-10
  1696. }
  1697.  
  1698.  
  1699. CBrowserWindow* CBrowserWindow::MakeNewBrowserWindow(Boolean inShow, Boolean inSelect)
  1700. {    
  1701.     ThrowIf_(Memory_MemoryIsLow());
  1702.  
  1703.     CBrowserWindow* result = nil;
  1704.  
  1705.     try
  1706.     {
  1707.         CBrowserContext* theContext = new CBrowserContext(MWContextBrowser);
  1708.         StSharer theShareLock(theContext);
  1709.         
  1710.         result = dynamic_cast<CBrowserWindow*>(LWindow::CreateWindow(res_ID, LCommander::GetTopCommander()));
  1711.         ThrowIfNil_(result);
  1712.         result->SetWindowContext(theContext);    
  1713.         
  1714.         if (inShow)
  1715.             result->Show();
  1716.             
  1717.         if (inSelect)
  1718.             result->Select();
  1719.     }
  1720.     catch(...)
  1721.     {
  1722.     }
  1723.     
  1724.     return result;
  1725. }
  1726.  
  1727. CBrowserWindow* CBrowserWindow::FindAndShow(Boolean inMakeNew)
  1728. {    
  1729.     ThrowIf_(Memory_MemoryIsLow());
  1730.  
  1731.     CBrowserWindow*        result = NULL;
  1732.     CWindowIterator        iter(WindowType_Browser);
  1733.     CMediatedWindow*    window;
  1734.     
  1735.     iter.Next(window);
  1736.  
  1737.     if (window)
  1738.     {
  1739.         result = dynamic_cast<CBrowserWindow*>(window);
  1740.     }
  1741.     else if (inMakeNew)
  1742.     {
  1743.         try
  1744.         {
  1745. //            ThrowIfNil_(CURLDispatcher::GetURLDispatcher());
  1746. //            CURLDispatcher::GetURLDispatcher()->DispatchToView(nil, nil, FO_CACHE_AND_PRESENT, true);
  1747.             result = CURLDispatcher::CreateNewBrowserWindow();
  1748.         }
  1749.         catch(...)
  1750.         {
  1751.         }
  1752.         
  1753. //        iter.Next(window);
  1754. //
  1755. //        if (window)
  1756. //        {
  1757. //            result = dynamic_cast<CBrowserWindow*>(window);
  1758. //        }
  1759.     }
  1760.     else
  1761.     {
  1762.         CWindowMediator* mediator = CWindowMediator::GetWindowMediator();
  1763.         CMediatedWindow* topWindow = mediator->FetchTopWindow(WindowType_Browser, dontCareLayerType, false);
  1764.         result = dynamic_cast<CBrowserWindow*>(topWindow);
  1765.     }
  1766.  
  1767.     return result;
  1768. }
  1769.  
  1770. CBrowserWindow* CBrowserWindow::FindAndPrepareEmpty(Boolean inMakeNew)
  1771. {
  1772. /*
  1773.     CWindowIterator iter(WindowType_Browser);
  1774.     CMediatedWindow* window;
  1775.     CBrowserWindow* result = NULL;
  1776.     iter.Next(window);
  1777. */
  1778.     CMediatedWindow* window;
  1779.     CBrowserWindow* result = NULL;
  1780.     // Find the topmost regular browser window which is not a restricted target
  1781.     window = CWindowMediator::GetWindowMediator()->FetchTopWindow(WindowType_Browser, regularLayerType, false);
  1782.  
  1783.     if (window)
  1784.         result = dynamic_cast<CBrowserWindow*>(window);
  1785.     else if (inMakeNew)
  1786.     {
  1787.         result = MakeNewBrowserWindow(kShow, kSelect);
  1788.     }
  1789.     return result;
  1790. }
  1791.  
  1792. Boolean CBrowserWindow::HandleKeyPress(const EventRecord &inKeyEvent)
  1793. {
  1794.     Char16        theChar = inKeyEvent.message & charCodeMask;
  1795.     short         modifiers = inKeyEvent.modifiers & (cmdKey | shiftKey | optionKey | controlKey);
  1796.  
  1797.     // Command-Key Events
  1798.     if ( ( modifiers & cmdKey ) == cmdKey )
  1799.     {
  1800.         switch ( theChar & charCodeMask )
  1801.         {
  1802.             case char_LeftArrow:
  1803.                 ObeyCommand( cmd_GoBack );
  1804.             return true;
  1805.  
  1806.             case char_RightArrow:
  1807.                 ObeyCommand( cmd_GoForward );
  1808.             return true;
  1809.         }
  1810.     }
  1811.     
  1812.     // Passing on the scrolling keys
  1813.     
  1814.     // ÑÑÑ tj - only when modifiers are 0, because
  1815.     // we the hyperview may have already passed the key
  1816.     // up to us if there are  modifiers 
  1817.     //    
  1818.     
  1819.     if ( modifiers == 0 && GetHTMLView())
  1820.     {
  1821.         if ((theChar == char_UpArrow) ||
  1822.             (theChar == char_DownArrow) ||
  1823.             (theChar == char_PageUp) ||
  1824.             (theChar == char_PageDown) ||
  1825.             (theChar == ' ') ||
  1826.             (theChar == char_Home) ||
  1827.             (theChar == char_End))
  1828.                 return GetHTMLView()->HandleKeyPress( inKeyEvent );
  1829.     }
  1830.     
  1831.     return CNetscapeWindow::HandleKeyPress(inKeyEvent);
  1832. }
  1833.  
  1834. //
  1835. // WriteWindowStatus
  1836. //
  1837. // Write out status of the toolbars and nav center
  1838. //
  1839. void CBrowserWindow :: WriteWindowStatus ( LStream *outStatusData )
  1840. {
  1841.     CSaveWindowStatus::WriteWindowStatus(outStatusData);
  1842.     CDragBarContainer* dragContainer = dynamic_cast<CDragBarContainer*>(FindPaneByID('DbCt'));
  1843.     if (dragContainer && outStatusData)
  1844.         dragContainer->SavePlace(outStatusData);
  1845.         
  1846.     if ( mNavCenterParent )
  1847.         mNavCenterParent->SavePlace(outStatusData);
  1848.  
  1849. } // CBrowserWindow :: WriteWindowStatus
  1850.  
  1851.  
  1852. //
  1853. // ReadWindowStatus
  1854. //
  1855. // Read in status of toolbars and nav center
  1856. //
  1857. void CBrowserWindow :: ReadWindowStatus ( LStream *inStatusData )
  1858. {
  1859.     CSaveWindowStatus::ReadWindowStatus(inStatusData);
  1860.     CDragBarContainer* dragContainer = dynamic_cast<CDragBarContainer*>(FindPaneByID('DbCt'));
  1861.     if (dragContainer && inStatusData)
  1862.         dragContainer->RestorePlace(inStatusData);
  1863.     
  1864.     if ( mNavCenterParent )
  1865.         mNavCenterParent->RestorePlace(inStatusData);
  1866.     
  1867. } // ReadWindowStatus
  1868.  
  1869.  
  1870. #pragma mark -- I18N Support --
  1871. Int16     CBrowserWindow::DefaultCSIDForNewWindow()
  1872. {
  1873.     Int16        default_csid;
  1874.     CHTMLView    *mainView = GetHTMLView();
  1875.  
  1876.     /* mainView might be zero if the window is still being created (haven't executed
  1877.        FinishCreateSelf).  (note that in that case, we could still fetch mainView by
  1878.        calling FindPaneByID, but again in that case, the pane's context hasn't been set up
  1879.        and the view simply returns a 0, so we just skip that step and do the same) */
  1880.     default_csid = mainView ? mainView->DefaultCSIDForNewWindow() : 0;
  1881.             
  1882.     // Get it from mContext
  1883.     if((0 == default_csid) && mContext)
  1884.         default_csid = mContext->GetDefaultCSID();
  1885.         
  1886.     return default_csid;
  1887. }
  1888.  
  1889. Int16     CBrowserWindow::GetDefaultCSID() const
  1890. {
  1891.     if(mContext)
  1892.         return mContext->GetDefaultCSID();
  1893.     return 0;
  1894. }
  1895. void     CBrowserWindow::SetDefaultCSID(Int16 default_csid)
  1896. {
  1897.     if(mContext)
  1898.         mContext->SetDefaultCSID(default_csid);
  1899. }
  1900. #pragma mark -- AppleEvent Support --
  1901.  
  1902. // pkc 2/17/97
  1903. // This code copied from mcontext.cp
  1904. // If the event action is long, dispatches it to the proper handler
  1905. // short actions are handled in this loop
  1906. void CBrowserWindow::HandleAppleEvent(const AppleEvent        &inAppleEvent,
  1907.                                       AppleEvent            &outAEReply,
  1908.                                       AEDesc                &outResult,
  1909.                                       long                    inAENumber)
  1910. {
  1911.     switch (inAENumber) {    
  1912.         case AE_Go:
  1913.             {
  1914.             StAEDescriptor    directionSpec;
  1915.             OSErr err = ::AEGetParamDesc(&inAppleEvent,AE_www_go_direction,typeWildCard,&directionSpec.mDesc);
  1916.             ThrowIfOSErr_(err);
  1917.             OSType    direction;
  1918.             UExtractFromAEDesc::TheEnum(directionSpec.mDesc, direction);
  1919.             DoAEGo((Int32)direction);
  1920.             }
  1921.             break;
  1922.         case AE_GetURL:
  1923.             HandleGetURLEvent(inAppleEvent, outAEReply, outResult);
  1924.             break;
  1925.         case AE_OpenURL:
  1926.             HandleOpenURLEvent(inAppleEvent, outAEReply, outResult);
  1927.             break;
  1928.         case AE_RegisterWinClose:
  1929.             Try_
  1930.             {
  1931.                 OSType appSignature;
  1932.                 Size     realSize;
  1933.                 OSType    realType;
  1934.     
  1935.                 OSErr err = ::AEGetParamPtr(&inAppleEvent, keyDirectObject, typeApplSignature, &realType,
  1936.                             &appSignature, sizeof(appSignature), &realSize);
  1937.                 if (err == noErr)    // No parameters, extract the signature from the Apple Event
  1938.                     fCloseNotifier = GetPSNBySig(appSignature);
  1939.                 else
  1940.                     fCloseNotifier = MoreExtractFromAEDesc::ExtractAESender(inAppleEvent);
  1941.                 break;
  1942.             }
  1943.             Catch_(inErr)
  1944.             {
  1945.                 fCloseNotifier = MakeNoProcessPSN();
  1946.             }
  1947.             EndCatch_
  1948.             break;
  1949.         case AE_UnregisterWinClose:
  1950.             fCloseNotifier = MakeNoProcessPSN();
  1951.             break;
  1952.         default:
  1953.             LWindow::HandleAppleEvent( inAppleEvent, outAEReply, outResult, inAENumber );
  1954.             break;
  1955.     }
  1956. }
  1957.  
  1958.  
  1959. void CBrowserWindow::GetAEProperty(DescType inProperty,
  1960.                             const AEDesc    &inRequestedType,
  1961.                             AEDesc            &outPropertyDesc) const
  1962. {
  1963.     switch (inProperty)
  1964.     {
  1965.         case AE_www_typeWindowURL:            // Current URL
  1966.             {
  1967.                 if (!GetWindowContext())
  1968.                 {
  1969.                     ThrowOSErr_(errAEDescNotFound);
  1970.                 }
  1971.                 
  1972.                 History_entry* theCurrentHistoryEntry = GetWindowContext()->GetCurrentHistoryEntry();
  1973.                 if (!theCurrentHistoryEntry || !theCurrentHistoryEntry->address)
  1974.                 {
  1975.                     ThrowOSErr_(errAEDescNotFound);
  1976.                 }
  1977.                 
  1978.                 OSErr err = ::AECreateDesc(typeChar,
  1979.                                             (Ptr) theCurrentHistoryEntry->address,
  1980.                                             strlen(theCurrentHistoryEntry->address),
  1981.                                             &outPropertyDesc);
  1982.                 ThrowIfOSErr_(err);
  1983.             }
  1984.             break;
  1985.             
  1986.         case AE_www_typeWindowBusy:            // is the window busy?
  1987.             {
  1988.                 if ( !GetWindowContext() )
  1989.                 {
  1990.                     ThrowOSErr_(errAEDescNotFound);
  1991.                 }
  1992.             
  1993.                 Uint32 busy = XP_IsContextBusy ( *GetWindowContext() );
  1994.                 OSErr err = ::AECreateDesc(typeLongInteger,
  1995.                                             &busy,
  1996.                                             sizeof(Uint32),
  1997.                                             &outPropertyDesc);
  1998.                 ThrowIfOSErr_(err);
  1999.                 
  2000.             }
  2001.             break;
  2002.             
  2003.         case AE_www_typeWindowID:            // get the window ID
  2004.             {
  2005.                 if ( !GetWindowContext() )
  2006.                 {
  2007.                     ThrowOSErr_(errAEDescNotFound);
  2008.                 }
  2009.             
  2010.                 Uint32 id = GetWindowContext()->GetContextUniqueID();
  2011.                 OSErr err = ::AECreateDesc(typeLongInteger,
  2012.                                             & id,
  2013.                                             sizeof(Uint32),
  2014.                                             &outPropertyDesc);
  2015.                 ThrowIfOSErr_(err);
  2016.                 
  2017.             }
  2018.             break;
  2019.         
  2020.             
  2021.         default:
  2022.             super::GetAEProperty(inProperty, inRequestedType, outPropertyDesc);
  2023.             break;
  2024.     }
  2025. }
  2026.  
  2027.  
  2028.  
  2029.  
  2030. // Sends an GetURL event
  2031. void CBrowserWindow::SendAEGetURL(const char* url)
  2032. {
  2033.     OSErr anError = noErr;
  2034.     try
  2035.     {
  2036.         AppleEvent    getURLEvent;
  2037.         UAppleEventsMgr::MakeAppleEvent(AE_url_suite, AE_url_getURL,
  2038.                                             getURLEvent);
  2039.         
  2040.             // URL
  2041.         anError = ::AEPutParamPtr(&getURLEvent,
  2042.                                     keyDirectObject,
  2043.                                     typeChar,
  2044.                                     url,
  2045.                                     strlen(url));
  2046.         ThrowIfOSErr_(anError);
  2047.         
  2048.             // This window
  2049.         StAEDescriptor    modelSpec;
  2050.         LWindow::MakeSpecifier(modelSpec.mDesc);
  2051.         anError = ::AEPutParamDesc(&getURLEvent,
  2052.                                     AE_www_typeWindow,
  2053.                                     &modelSpec.mDesc);
  2054.         ThrowIfOSErr_(anError);
  2055.         
  2056.     /*
  2057.             // Refererer
  2058.         if (strlen(refererer) > 0)
  2059.         {
  2060.             anError = ::AEPutParamPtr(&getURLEvent,
  2061.                                         AE_url_getURLrefererer,
  2062.                                         typeChar,
  2063.                                         refererer,
  2064.                                         strlen(refererer));
  2065.             ThrowIfOSErr_(anError);
  2066.         }
  2067.         
  2068.             // Window name
  2069.         if (strlen(winName) > 0)
  2070.         {
  2071.             anError = ::AEPutParamPtr(&getURLEvent,
  2072.                                         AE_url_getURLname,
  2073.                                         typeChar,
  2074.                                         winName,
  2075.                                         strlen(winName));
  2076.             ThrowIfOSErr_(anError);
  2077.         }
  2078.         
  2079.             // Optional load-to-disk parameter
  2080.         if (loadToDisk)
  2081.         {
  2082.             anError = ::AEPutParamPtr(&getURLEvent,
  2083.                                         AE_url_getURLdestination,
  2084.                                         typeNull,
  2085.                                         NULL,
  2086.                                         0);
  2087.             ThrowIfOSErr_(anError);
  2088.         }
  2089.     */
  2090.                     
  2091.         UAppleEventsMgr::SendAppleEvent(getURLEvent);
  2092.     }    
  2093.     catch(...)
  2094.     {
  2095.         URL_Struct* theURL = NET_CreateURLStruct(url, NET_DONT_RELOAD);
  2096.         mContext->SwitchLoadURL(theURL, FO_CACHE_AND_PRESENT);
  2097.     }
  2098. }
  2099.  
  2100.  
  2101.  
  2102.  
  2103.  
  2104. // Simplify the navigation events to only a single event, Go <direction>
  2105. // Still incomplete, since I have not figured out how to deal with history
  2106. // in an easy way.
  2107. // right now, the possible constants are:
  2108. //    kAENext
  2109. //    kAEPrevious
  2110. //    AE_www_go_again
  2111. //    AE_www_super_reload
  2112. void CBrowserWindow::SendAEGo( OSType direction )
  2113. {
  2114.     OSErr        anError = noErr;
  2115.     
  2116.     try 
  2117.     {
  2118.         AppleEvent    goEvent;
  2119.         UAppleEventsMgr::MakeAppleEvent(AE_www_suite, AE_www_go, goEvent);
  2120.  
  2121.         // Ñ╩this window
  2122.         StAEDescriptor        modelSpec;
  2123.         LWindow::MakeSpecifier(modelSpec.mDesc);
  2124.         anError = ::AEPutParamDesc(&goEvent, keyDirectObject, &modelSpec.mDesc);
  2125.         ThrowIfOSErr_(anError);
  2126.  
  2127.         StAEDescriptor        directionSpec(typeEnumerated, &direction, sizeof(direction));
  2128.         anError = ::AEPutParamDesc(&goEvent, AE_www_go_direction, &directionSpec.mDesc);
  2129.         ThrowIfOSErr_(anError);
  2130.  
  2131.         UAppleEventsMgr::SendAppleEvent(goEvent);
  2132.     }    
  2133.     catch(...)
  2134.     {
  2135.         DoAEGo(direction);
  2136.     }    
  2137. }
  2138.  
  2139.  
  2140.  
  2141.  
  2142.  
  2143. // updated to send an event to javascript, also checks for null context - 1997-02-26 mjc
  2144. // Handles the navigation events
  2145. void CBrowserWindow::DoAEGo( OSType direction )
  2146. {
  2147.     switch ( direction )
  2148.     {
  2149.         case kAENext:    // going back in history
  2150.             if (mContext != NULL)
  2151.             {
  2152.                 mContext->GoForward();
  2153.                 CMochaHacks::SendForwardEvent(*mContext);
  2154.             }
  2155.             break;
  2156.         
  2157.         case kAEPrevious:
  2158.             if (mContext != NULL)
  2159.             {
  2160.                 mContext->GoBack();
  2161.                 CMochaHacks::SendBackEvent(*mContext);
  2162.             }
  2163.             break;
  2164.         
  2165.         case AE_www_go_again:
  2166.             if (mContext != NULL)
  2167.                 mContext->LoadHistoryEntry(CBrowserContext::index_Reload);
  2168.             break;
  2169.         
  2170.         case AE_www_super_reload:
  2171.             if (mContext != NULL)
  2172.                 mContext->LoadHistoryEntry(CBrowserContext::index_Reload, true);
  2173.             break;
  2174.         
  2175.         case AE_www_go_home:
  2176.         {
  2177.             URL_Struct* homeURL =
  2178.                 NET_CreateURLStruct(CPrefs::GetString(CPrefs::HomePage), NET_DONT_RELOAD);
  2179.             if (mContext != NULL)
  2180.                 mContext->SwitchLoadURL(homeURL, FO_CACHE_AND_PRESENT);
  2181.         }
  2182.         break;
  2183.         
  2184.         default:
  2185.             SysBeep( 1 );
  2186.         break;
  2187.     }
  2188. }
  2189.  
  2190.  
  2191.  
  2192.  
  2193.  
  2194. void CBrowserWindow::HandleGetURLEvent(const AppleEvent        &inAppleEvent,
  2195.                                        AppleEvent            &outAEReply,
  2196.                                        AEDesc                &/*outResult*/,
  2197.                                        CBrowserWindow        *inBrowserWindow)
  2198. {    
  2199.     FSSpec fileSpec;
  2200.     Boolean hasFileSpec = FALSE;
  2201.     Boolean doLoadToDisk = FALSE;
  2202.     DescType realType;
  2203.     Size actualSize;
  2204.     OSErr err;
  2205.     char * url = NULL;
  2206.     char * refererer = NULL;
  2207.     char * winName = NULL;
  2208.  
  2209. #ifdef DEBUG
  2210.     StValueChanger<EDebugAction> changeDebugThrow(gDebugThrow, debugAction_Nothing);
  2211. #endif
  2212.     MoreExtractFromAEDesc::GetCString(inAppleEvent, keyDirectObject, url);
  2213.  
  2214.     // Extract the referer, if possible
  2215.     Try_
  2216.     {
  2217.         MoreExtractFromAEDesc::GetCString(inAppleEvent, AE_url_getURLrefererer, refererer);
  2218.     }
  2219.     Catch_(inErr){}
  2220.     EndCatch_
  2221.     Try_
  2222.     {
  2223.         MoreExtractFromAEDesc::GetCString(inAppleEvent, AE_url_getURLname, winName);
  2224.     }
  2225.     Catch_(inErr){}
  2226.     EndCatch_
  2227.     // See if we are doing load-to-disk.
  2228.     // If the descriptor is of typeNull, we should load to disk
  2229.     // but we have to file spec
  2230.     {
  2231.         StAEDescriptor fileDesc;
  2232.         err = ::AEGetParamDesc(&inAppleEvent,AE_url_getURLdestination,typeWildCard,&fileDesc.mDesc);
  2233.         if (err == noErr)
  2234.         {
  2235.             if (fileDesc.mDesc.descriptorType == typeNull)
  2236.                 doLoadToDisk = TRUE;
  2237.             else
  2238.             {
  2239.                 err = ::AEGetParamPtr(&inAppleEvent, AE_url_getURLdestination,
  2240.                                     typeFSS, &realType,
  2241.                                     &fileSpec, 
  2242.                                     sizeof(FSSpec), &actualSize);
  2243.                 if (err == errAECoercionFail)
  2244.                 {
  2245.                     char * filePath = NULL;
  2246.                     Try_
  2247.                     {
  2248.                         MoreExtractFromAEDesc::GetCString(inAppleEvent, AE_url_getURLdestination, filePath);
  2249.                         err = CFileMgr::FSSpecFromPathname(filePath, &fileSpec);
  2250.                         if (err == fnfErr)
  2251.                             err = noErr;
  2252.                         ThrowIfOSErr_(err);
  2253.                     }
  2254.                     Catch_(inErr)
  2255.                     {
  2256.                         err = fnfErr;
  2257.                     }
  2258.                     EndCatch_
  2259.                     if (filePath)
  2260.                         XP_FREE(filePath);
  2261.                 }
  2262.                 hasFileSpec = (err == noErr);
  2263.                 doLoadToDisk = TRUE;
  2264.             }
  2265.         }
  2266.     }
  2267.     
  2268.     URL_Struct * request = NET_CreateURLStruct (url, NET_DONT_RELOAD);
  2269.     if (winName)
  2270.         request->window_target = XP_STRDUP(winName);
  2271.     ThrowIfNil_(request);
  2272.     request->referer = refererer;
  2273.  
  2274.     if (hasFileSpec && doLoadToDisk)
  2275.     {
  2276.         CURLDispatcher::DispatchToStorage(request, fileSpec, FO_SAVE_AS, true);
  2277.     }
  2278.     else if (!hasFileSpec && !doLoadToDisk)
  2279.     {
  2280.         if (inBrowserWindow)
  2281.         {
  2282.             ThrowIfNil_(inBrowserWindow->mContext);
  2283.             
  2284.             long windowIndex = inBrowserWindow->mContext->GetContextUniqueID();
  2285.             // StartLoadingURL(request, FO_CACHE_AND_PRESENT);
  2286.             // mContext->SwitchLoadURL(request, FO_CACHE_AND_PRESENT);
  2287.             CURLDispatcher::DispatchURL(request, inBrowserWindow->mContext, true);
  2288.             
  2289.             if (outAEReply.descriptorType != typeNull)
  2290.                 err = ::AEPutParamPtr (&outAEReply, keyAEResult, typeLongInteger, &windowIndex, sizeof(windowIndex));
  2291.         }
  2292.         else
  2293.         {
  2294.             if (CFrontApp::GetApplication()->HasProperlyStartedUp())
  2295.             {
  2296.                 // Get a window - but don't show it
  2297.  
  2298.                 CBrowserWindow*    win = CBrowserWindow::MakeNewBrowserWindow(kDontShow);
  2299.                 ThrowIfNil_(win);
  2300.  
  2301.                 ThrowIfNil_(win->mContext);
  2302.                 long windowIndex = win->mContext->GetContextUniqueID();
  2303.                 
  2304.                 CURLDispatcher::DispatchURL(request, win->mContext, true);
  2305.                 
  2306.                 if (outAEReply.descriptorType != typeNull)
  2307.                     err = ::AEPutParamPtr (&outAEReply, keyAEResult, typeLongInteger, &windowIndex, sizeof(windowIndex));
  2308.             }
  2309.             else
  2310.             {
  2311.                 // MGY 5/22: If there are multiple profiles and the event is handled before the user selects a profile,
  2312.                 // then prefs have not been loaded and we will crash trying to restore the position of the browser window.
  2313.                 // To fix it right, we will have to delay the positioning of the window until it is shown. The mechanism
  2314.                 // by which the position of windows is restored is not flexible enough to allow this and to make it so now
  2315.                 // would be too intrusive of a change at this late date. So we just return 0 for the window ID and the
  2316.                 // window will be created when the delayed URL is handled.
  2317.               
  2318.                 CURLDispatcher::DispatchURL(request, nil, true);
  2319.  
  2320.                 long windowIndex = 0;
  2321.                 if (outAEReply.descriptorType != typeNull)
  2322.                     err = ::AEPutParamPtr (&outAEReply, keyAEResult, typeLongInteger, &windowIndex, sizeof(windowIndex));
  2323.             }
  2324.         }
  2325.     }
  2326.     XP_FREE (url);
  2327.     if (winName)
  2328.         XP_FREE(winName);
  2329. }
  2330.  
  2331. //--------------------------------------------------------------------------------
  2332. // Spyglass AppleEvent suite
  2333. //--------------------------------------------------------------------------------
  2334.  
  2335. void CBrowserWindow::HandleOpenURLEvent(const AppleEvent    &inAppleEvent,
  2336.                                         AppleEvent            &outAEReply,
  2337.                                         AEDesc                &/*outResult*/,
  2338.                                         CBrowserWindow        *inBrowserWindow)
  2339. {
  2340.     // The use of "volatile" in  the following lines
  2341.     //        (a) generated compiler warnings, because they are passed to routines that
  2342.     //            are not declared with correspondingly volatile parameters.
  2343.     //        (b) do not appear to need to be volatile in the sense given (If they were
  2344.     //            declared as volatile char*, that would be another thing...
  2345.     char * /*volatile*/ url = NULL;
  2346.     char * /*volatile*/ formData = NULL;    // Do not free this
  2347.     char * /*volatile*/ formHeader = NULL;    // form headers (MIME type)
  2348.     ProcessSerialNumber psn;
  2349.     FSSpec fileSpec;
  2350.     Boolean hasFileSpec = FALSE;
  2351.     Boolean hasFormData = FALSE;
  2352.     Boolean hasPSN = FALSE;
  2353.     Boolean forceReload = FALSE;
  2354.     OSErr volatile err;
  2355.     Size actualSize;
  2356.     DescType realType;
  2357.     
  2358.     // Get the url
  2359.     MoreExtractFromAEDesc::GetCString(inAppleEvent, keyDirectObject, url);
  2360.  
  2361.     {    // See if we are doing load-to-disk
  2362.         err = ::AEGetParamPtr(&inAppleEvent, AE_spy_openURL_into,
  2363.                             typeFSS, &realType,
  2364.                             &fileSpec, 
  2365.                             sizeof(fileSpec), &actualSize);
  2366.         if (err == noErr)
  2367.             hasFileSpec = TRUE;
  2368.     }
  2369.     // Flags
  2370.     Try_
  2371.     {
  2372.         long flags;
  2373.         err = ::AEGetParamPtr(&inAppleEvent, AE_spy_openURL_flag, typeLongInteger,
  2374.                          &realType, &flags, sizeof(flags), &actualSize);
  2375.         ThrowIfOSErr_(err);
  2376.         if ((flags & 0x1) || (flags & 0x2))
  2377.             forceReload = TRUE;
  2378.     }
  2379.     Catch_(inErr){}
  2380.     EndCatch_
  2381.     // Form data?
  2382.     Try_
  2383.     {
  2384.         MoreExtractFromAEDesc::GetCString(inAppleEvent, AE_spy_openURL_post, formData);
  2385.         hasFormData = TRUE;
  2386.     }
  2387.     Catch_(inErr){}
  2388.     EndCatch_
  2389.     // If we have form data, get the form MIME type
  2390.     if (formData)    
  2391.     Try_
  2392.     {
  2393.         char * newFormHeader = NULL;
  2394.         MoreExtractFromAEDesc::GetCString(inAppleEvent, AE_spy_openURL_mime, formHeader);
  2395.         StrAllocCat(formHeader, CRLF);
  2396.     }
  2397.     Catch_(inErr)
  2398.     {
  2399.         StrAllocCopy(formHeader, "Content-type: application/x-www-form-urlencoded");
  2400.         StrAllocCat(formHeader, CRLF);
  2401.     }
  2402.     EndCatch_
  2403.     if (formData && formHeader)
  2404.     {
  2405.         char buffer[64];
  2406.         XP_SPRINTF(buffer, "Content-length: %ld%s", strlen(formData), CRLF);
  2407.         StrAllocCat(formHeader, buffer);
  2408.     }
  2409.     {    // Progress application
  2410.         err = ::AEGetParamPtr(&inAppleEvent, AE_spy_openURL_prog,
  2411.                             typeProcessSerialNumber, &realType,
  2412.                             &psn, 
  2413.                             sizeof(psn), &actualSize);
  2414.         if (err == noErr)
  2415.             hasPSN = TRUE;
  2416.     }
  2417.     
  2418.     // create a Netlib geturl thread
  2419.     URL_Struct * request = NET_CreateURLStruct (url, NET_DONT_RELOAD);
  2420.     ThrowIfNil_(request);
  2421.     
  2422.     if (forceReload)
  2423.         request->force_reload = NET_NORMAL_RELOAD;
  2424.     else
  2425.         request->force_reload = NET_DONT_RELOAD;
  2426.     if (hasFormData)
  2427.     {
  2428.         request->method = 1;
  2429.         request->post_data = formData;
  2430.         request->post_data_size = strlen(formData);
  2431.         request->post_headers = formHeader;
  2432.     }
  2433.     
  2434.         // service non-interactive request from a different application
  2435.     
  2436.     /*
  2437.         ÑÑÑ what do we do with this in dobgert, since SetProgressApp no longer exists?
  2438.     if (hasPSN)
  2439.         mContext->SetProgressApp(psn);
  2440.     */
  2441.     
  2442.     if (hasFileSpec)
  2443.     {
  2444.         CURLDispatcher::DispatchToStorage(request, fileSpec, FO_SAVE_AS, true);
  2445.     }
  2446.     else
  2447.     {
  2448.         if (inBrowserWindow)
  2449.         {
  2450.             ThrowIfNil_(inBrowserWindow->mContext);
  2451.             
  2452.             long windowID = inBrowserWindow->mContext->GetContextUniqueID();
  2453.             /*
  2454.                 ÑÑÑ what is this?  deeje 97-03-07
  2455.             if (!fHyperView->CanLoad())
  2456.                 windowID = 0;
  2457.             */
  2458.             if (outAEReply.descriptorType != typeNull)
  2459.             {
  2460.                 StAEDescriptor    windowIDDesc(windowID);
  2461.                 err = ::AEPutParamDesc(&outAEReply, keyAEResult, &windowIDDesc.mDesc);
  2462.             }
  2463.             
  2464.             CURLDispatcher::DispatchURL(request, inBrowserWindow->mContext, true);
  2465.         }
  2466.         else
  2467.         {
  2468.             if (CFrontApp::GetApplication()->HasProperlyStartedUp())
  2469.             {
  2470.                 // Get a window - but don't show it
  2471.  
  2472.                 CBrowserWindow*    win = CBrowserWindow::MakeNewBrowserWindow(kDontShow);
  2473.                 ThrowIfNil_(win);
  2474.  
  2475.                 ThrowIfNil_(win->mContext);
  2476.                 long windowIndex = win->mContext->GetContextUniqueID();
  2477.                 
  2478.                 CURLDispatcher::DispatchURL(request, win->mContext, true);
  2479.                 
  2480.                 if (outAEReply.descriptorType != typeNull)
  2481.                     err = ::AEPutParamPtr (&outAEReply, keyAEResult, typeLongInteger, &windowIndex, sizeof(windowIndex));
  2482.             }
  2483.             else
  2484.             {
  2485.                 // MGY 5/22: If there are multiple profiles and the event is handled before the user selects a profile,
  2486.                 // then prefs have not been loaded and we will crash trying to restore the position of the browser window.
  2487.                 // To fix it right, we will have to delay the positioning of the window until it is shown. The mechanism
  2488.                 // by which the position of windows is restored is not flexible enough to allow this and to make it so now
  2489.                 // would be too intrusive of a change at this late date. So we just return 0 for the window ID and the
  2490.                 // window will be created when the delayed URL is handled.
  2491.               
  2492.                 CURLDispatcher::DispatchURL(request, nil, true);
  2493.  
  2494.                 long windowIndex = 0;
  2495.                 if (outAEReply.descriptorType != typeNull)
  2496.                     err = ::AEPutParamPtr (&outAEReply, keyAEResult, typeLongInteger, &windowIndex, sizeof(windowIndex));
  2497.             }
  2498.         }
  2499.     }
  2500.  
  2501.     if (url)
  2502.         XP_FREE (url);
  2503. }
  2504.  
  2505. // override to send javascript move events when the user performs the action
  2506. // because ClickInDrag sends an AppleEvent which doesn't come back to the app.
  2507. void    
  2508. CBrowserWindow::SendAESetPosition(Point inPosition, Boolean inExecuteAE)
  2509. {
  2510.     CNetscapeWindow::SendAESetPosition(inPosition, inExecuteAE);
  2511.     if (mContext != NULL)
  2512.     {
  2513.         Rect bounds;
  2514.         bounds = UWindows::GetWindowStructureRect(GetMacPort());
  2515.         CMochaHacks::SendMoveEvent(*mContext, bounds.left, bounds.top - ::GetMBarHeight());
  2516.     }
  2517. }
  2518.  
  2519. void CBrowserWindow::DoDefaultPrefs()
  2520. {
  2521.     CPrefsDialog::EditPrefs(CPrefsDialog::eExpandBrowser);
  2522. }
  2523.  
  2524.  
  2525.  
  2526. #if 0
  2527. History_entry* CBrowserWindow::GetBookmarksEntry()
  2528. {
  2529.     return mContext->GetCurrentHistoryEntry();
  2530. }
  2531. #endif // 0
  2532.  
  2533.  
  2534. #pragma mark -- Helper functions for ObeyCommand --
  2535.  
  2536. // ---------------------------------------------------------------------------
  2537. //        Ñ HandleNetSearchCommand
  2538. // ---------------------------------------------------------------------------
  2539.  
  2540. void
  2541. CBrowserWindow::HandleNetSearchCommand()
  2542. {
  2543.     CAutoPtrXP<char>    url;
  2544.     char*                tempURL = 0;
  2545.     int                    rc;
  2546.  
  2547.     rc = PREF_CopyConfigString("internal_url.net_search.url", &tempURL);
  2548.     url.reset(tempURL);
  2549.     
  2550.     if (rc == PREF_NOERROR)
  2551.     {
  2552.         CFrontApp& theApp = dynamic_cast<CFrontApp&>(CApplicationEventAttachment::GetApplication());
  2553.         
  2554.         theApp.DoGetURL(url.get());
  2555.     }
  2556. }
  2557.