2001-09-28 20:14:13 +00:00
|
|
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
2005-08-22 20:35:47 +00:00
|
|
|
/* vim: set ts=2 sw=2 et tw=80: */
|
2001-09-28 20:14:13 +00:00
|
|
|
/* ***** BEGIN LICENSE BLOCK *****
|
2004-04-18 14:30:37 +00:00
|
|
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
1999-03-27 01:35:55 +00:00
|
|
|
*
|
2004-04-18 14:30:37 +00:00
|
|
|
* The contents of this file are subject to the Mozilla Public License Version
|
|
|
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
|
|
|
* the License. You may obtain a copy of the License at
|
|
|
|
* http://www.mozilla.org/MPL/
|
1999-03-27 01:35:55 +00:00
|
|
|
*
|
2001-09-28 20:14:13 +00:00
|
|
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
|
|
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
|
|
|
* for the specific language governing rights and limitations under the
|
|
|
|
* License.
|
1999-03-27 01:35:55 +00:00
|
|
|
*
|
|
|
|
* The Original Code is Mozilla Communicator client code.
|
|
|
|
*
|
2004-04-18 14:30:37 +00:00
|
|
|
* The Initial Developer of the Original Code is
|
2001-09-28 20:14:13 +00:00
|
|
|
* Netscape Communications Corporation.
|
|
|
|
* Portions created by the Initial Developer are Copyright (C) 1998
|
|
|
|
* the Initial Developer. All Rights Reserved.
|
1999-11-06 03:40:37 +00:00
|
|
|
*
|
2001-09-28 20:14:13 +00:00
|
|
|
* Contributor(s):
|
2000-02-02 22:24:56 +00:00
|
|
|
* Pierre Phaneuf <pp@ludusdesign.com>
|
2001-09-28 20:14:13 +00:00
|
|
|
*
|
|
|
|
* Alternatively, the contents of this file may be used under the terms of
|
2004-04-18 14:30:37 +00:00
|
|
|
* either of the GNU General Public License Version 2 or later (the "GPL"),
|
|
|
|
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
2001-09-28 20:14:13 +00:00
|
|
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
|
|
|
* of those above. If you wish to allow use of your version of this file only
|
|
|
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
2004-04-18 14:30:37 +00:00
|
|
|
* use your version of this file under the terms of the MPL, indicate your
|
2001-09-28 20:14:13 +00:00
|
|
|
* decision by deleting the provisions above and replace them with the notice
|
|
|
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
|
|
|
* the provisions above, a recipient may use your version of this file under
|
2004-04-18 14:30:37 +00:00
|
|
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
2001-09-28 20:14:13 +00:00
|
|
|
*
|
|
|
|
* ***** END LICENSE BLOCK ***** */
|
1999-03-27 01:35:55 +00:00
|
|
|
|
|
|
|
//
|
|
|
|
// Eric Vaughan
|
|
|
|
// Netscape Communications
|
|
|
|
//
|
|
|
|
// See documentation in associated header file
|
|
|
|
//
|
|
|
|
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
// How boxes layout
|
|
|
|
// ----------------
|
|
|
|
// Boxes layout a bit differently than html. html does a bottom up layout. Where boxes do a top down.
|
|
|
|
// 1) First thing a box does it goes out and askes each child for its min, max, and preferred sizes.
|
|
|
|
// 2) It then adds them up to determine its size.
|
|
|
|
// 3) If the box was asked to layout it self intrinically it will layout its children at their preferred size
|
|
|
|
// otherwise it will layout the child at the size it was told to. It will squeeze or stretch its children if
|
|
|
|
// Necessary.
|
|
|
|
//
|
|
|
|
// However there is a catch. Some html components like block frames can not determine their preferred size.
|
2005-11-20 22:05:24 +00:00
|
|
|
// this is their size if they were laid out intrinsically. So the box will flow the child to determine this can
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
// cache the value.
|
|
|
|
|
|
|
|
// Boxes and Incremental Reflow
|
|
|
|
// ----------------------------
|
2005-11-20 22:05:24 +00:00
|
|
|
// Boxes layout out top down by adding up their children's min, max, and preferred sizes. Only problem is if a incremental
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
// reflow occurs. The preferred size of a child deep in the hierarchy could change. And this could change
|
|
|
|
// any number of syblings around the box. Basically any children in the reflow chain must have their caches cleared
|
2000-03-31 07:02:06 +00:00
|
|
|
// so when asked for there current size they can relayout themselves.
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
#include "nsBoxLayoutState.h"
|
1999-03-27 01:35:55 +00:00
|
|
|
#include "nsBoxFrame.h"
|
2003-02-22 00:32:13 +00:00
|
|
|
#include "nsStyleContext.h"
|
2004-07-31 23:15:21 +00:00
|
|
|
#include "nsPresContext.h"
|
1999-03-27 01:35:55 +00:00
|
|
|
#include "nsCOMPtr.h"
|
|
|
|
#include "nsUnitConversion.h"
|
|
|
|
#include "nsINameSpaceManager.h"
|
|
|
|
#include "nsHTMLAtoms.h"
|
|
|
|
#include "nsXULAtoms.h"
|
1999-05-09 21:46:24 +00:00
|
|
|
#include "nsIContent.h"
|
1999-07-02 05:28:32 +00:00
|
|
|
#include "nsSpaceManager.h"
|
|
|
|
#include "nsHTMLParts.h"
|
1999-06-30 22:17:43 +00:00
|
|
|
#include "nsIViewManager.h"
|
2000-01-14 10:34:27 +00:00
|
|
|
#include "nsIView.h"
|
1999-08-19 03:51:25 +00:00
|
|
|
#include "nsIPresShell.h"
|
1999-09-05 20:46:59 +00:00
|
|
|
#include "nsFrameNavigator.h"
|
1999-09-10 00:57:01 +00:00
|
|
|
#include "nsCSSRendering.h"
|
2000-03-02 07:13:02 +00:00
|
|
|
#include "nsIServiceManager.h"
|
2000-03-31 07:02:06 +00:00
|
|
|
#include "nsIBoxLayout.h"
|
|
|
|
#include "nsSprocketLayout.h"
|
2000-05-22 09:15:54 +00:00
|
|
|
#include "nsIDocument.h"
|
|
|
|
#include "nsIBindingManager.h"
|
|
|
|
#include "nsIScrollableFrame.h"
|
2000-06-22 00:48:49 +00:00
|
|
|
#include "nsWidgetsCID.h"
|
2000-06-28 22:19:54 +00:00
|
|
|
#include "nsLayoutAtoms.h"
|
2002-11-17 15:37:56 +00:00
|
|
|
#include "nsCSSAnonBoxes.h"
|
2000-06-28 22:19:54 +00:00
|
|
|
#include "nsIScrollableView.h"
|
2000-09-01 00:59:09 +00:00
|
|
|
#include "nsHTMLContainerFrame.h"
|
2001-07-16 02:40:48 +00:00
|
|
|
#include "nsIWidget.h"
|
2002-02-21 13:39:39 +00:00
|
|
|
#include "nsIEventStateManager.h"
|
|
|
|
#include "nsIDOMDocument.h"
|
|
|
|
#include "nsIDOMElement.h"
|
2002-01-08 00:43:20 +00:00
|
|
|
#include "nsITheme.h"
|
2002-06-17 23:35:15 +00:00
|
|
|
#include "nsTransform2D.h"
|
2002-07-03 16:38:15 +00:00
|
|
|
#include "nsIEventListenerManager.h"
|
|
|
|
#include "nsIEventStateManager.h"
|
2006-03-07 17:08:51 +00:00
|
|
|
#include "nsEventDispatcher.h"
|
2002-07-03 16:38:15 +00:00
|
|
|
#include "nsIDOMEvent.h"
|
2005-04-28 23:48:28 +00:00
|
|
|
#include "nsIPrivateDOMEvent.h"
|
2004-04-29 23:34:19 +00:00
|
|
|
#include "nsContentUtils.h"
|
2006-01-26 02:29:17 +00:00
|
|
|
#include "nsDisplayList.h"
|
2000-06-22 00:48:49 +00:00
|
|
|
|
2002-01-23 02:53:02 +00:00
|
|
|
// Needed for Print Preview
|
|
|
|
#include "nsIDocument.h"
|
|
|
|
#include "nsIURI.h"
|
|
|
|
|
|
|
|
|
2000-06-22 00:48:49 +00:00
|
|
|
static NS_DEFINE_IID(kWidgetCID, NS_CHILD_CID);
|
1999-05-09 21:46:24 +00:00
|
|
|
|
2000-02-14 01:42:09 +00:00
|
|
|
//define DEBUG_REDRAW
|
2000-05-15 04:12:31 +00:00
|
|
|
|
1999-08-27 06:06:39 +00:00
|
|
|
#define DEBUG_SPRING_SIZE 8
|
|
|
|
#define DEBUG_BORDER_SIZE 2
|
|
|
|
#define COIL_SIZE 8
|
|
|
|
|
2000-02-16 23:00:52 +00:00
|
|
|
//#define TEST_SANITY
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-08-23 11:02:19 +00:00
|
|
|
#ifdef DEBUG_rods
|
2000-08-24 13:19:57 +00:00
|
|
|
//#define DO_NOISY_REFLOW
|
2000-08-23 11:02:19 +00:00
|
|
|
#endif
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool nsBoxFrame::gDebug = PR_FALSE;
|
|
|
|
nsIBox* nsBoxFrame::mDebugChild = nsnull;
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2005-10-26 21:46:39 +00:00
|
|
|
nsIFrame*
|
2006-03-26 21:30:36 +00:00
|
|
|
NS_NewBoxFrame(nsIPresShell* aPresShell, nsStyleContext* aContext, PRBool aIsRoot, nsIBoxLayout* aLayoutManager)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2006-03-26 21:30:36 +00:00
|
|
|
return new (aPresShell) nsBoxFrame(aPresShell, aContext, aIsRoot, aLayoutManager);
|
1999-03-27 01:35:55 +00:00
|
|
|
} // NS_NewBoxFrame
|
|
|
|
|
2006-03-26 21:30:36 +00:00
|
|
|
nsBoxFrame::nsBoxFrame(nsIPresShell* aPresShell,
|
|
|
|
nsStyleContext* aContext,
|
|
|
|
PRBool aIsRoot,
|
|
|
|
nsIBoxLayout* aLayoutManager) :
|
|
|
|
nsContainerFrame(aContext),
|
|
|
|
mMouseThrough(unset)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2004-09-28 18:37:50 +00:00
|
|
|
mState |= NS_FRAME_IS_BOX;
|
2001-03-06 02:27:50 +00:00
|
|
|
mState |= NS_STATE_IS_HORIZONTAL;
|
2000-02-14 01:42:09 +00:00
|
|
|
mState |= NS_STATE_AUTO_STRETCH;
|
2000-02-16 23:00:52 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
if (aIsRoot)
|
2000-03-02 03:01:30 +00:00
|
|
|
mState |= NS_STATE_IS_ROOT;
|
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
mValign = vAlign_Top;
|
|
|
|
mHalign = hAlign_Left;
|
2001-09-25 22:17:00 +00:00
|
|
|
|
2000-04-05 00:19:00 +00:00
|
|
|
// if no layout manager specified us the static sprocket layout
|
|
|
|
nsCOMPtr<nsIBoxLayout> layout = aLayoutManager;
|
|
|
|
|
|
|
|
if (layout == nsnull) {
|
|
|
|
NS_NewSprocketLayout(aPresShell, layout);
|
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
SetLayoutManager(layout);
|
|
|
|
|
2000-04-05 00:19:00 +00:00
|
|
|
NeedsRecalc();
|
1999-08-27 06:06:39 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
nsBoxFrame::~nsBoxFrame()
|
|
|
|
{
|
1999-03-27 01:35:55 +00:00
|
|
|
}
|
|
|
|
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
NS_IMETHODIMP
|
2000-03-31 07:02:06 +00:00
|
|
|
nsBoxFrame::GetVAlign(Valignment& aAlign)
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
{
|
2002-10-10 06:39:30 +00:00
|
|
|
aAlign = mValign;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetHAlign(Halignment& aAlign)
|
|
|
|
{
|
2002-10-10 06:39:30 +00:00
|
|
|
aAlign = mHalign;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
1999-12-02 01:07:27 +00:00
|
|
|
NS_IMETHODIMP
|
2006-04-10 00:16:29 +00:00
|
|
|
nsBoxFrame::SetInitialChildList(nsIAtom* aListName,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aChildList)
|
1999-12-02 01:07:27 +00:00
|
|
|
{
|
2006-04-10 00:16:29 +00:00
|
|
|
nsresult r = nsContainerFrame::SetInitialChildList(aListName, aChildList);
|
2000-03-31 07:02:06 +00:00
|
|
|
if (r == NS_OK) {
|
|
|
|
// initialize our list of infos.
|
2006-04-10 00:16:29 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext()->PresShell());
|
2004-09-28 18:37:50 +00:00
|
|
|
CheckBoxOrder(state);
|
|
|
|
if (mLayoutManager)
|
|
|
|
mLayoutManager->ChildrenSet(this, state, mFrames.FirstChild());
|
2000-03-31 07:02:06 +00:00
|
|
|
} else {
|
2002-09-09 21:32:33 +00:00
|
|
|
NS_WARNING("Warning add child failed!!\n");
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
1999-12-02 01:07:27 +00:00
|
|
|
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
2006-04-17 23:58:17 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::DidSetStyleContext()
|
|
|
|
{
|
|
|
|
// The values that CacheAttributes() computes depend on our style,
|
|
|
|
// so we need to recompute them here...
|
|
|
|
CacheAttributes();
|
2006-04-18 02:28:00 +00:00
|
|
|
|
|
|
|
return NS_OK;
|
2006-04-17 23:58:17 +00:00
|
|
|
}
|
|
|
|
|
1999-05-09 21:46:24 +00:00
|
|
|
/**
|
|
|
|
* Initialize us. This is a good time to get the alignment of the box
|
|
|
|
*/
|
1999-03-27 01:35:55 +00:00
|
|
|
NS_IMETHODIMP
|
2006-03-09 18:55:21 +00:00
|
|
|
nsBoxFrame::Init(nsIContent* aContent,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aParent,
|
|
|
|
nsIFrame* aPrevInFlow)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2006-03-26 21:30:36 +00:00
|
|
|
nsresult rv = nsContainerFrame::Init(aContent, aParent, aPrevInFlow);
|
2000-01-08 02:18:14 +00:00
|
|
|
|
2005-12-14 23:46:34 +00:00
|
|
|
// see if we need a widget
|
2004-09-28 18:37:50 +00:00
|
|
|
if (aParent && aParent->IsBoxFrame()) {
|
2000-06-22 00:48:49 +00:00
|
|
|
PRBool needsWidget = PR_FALSE;
|
2004-09-28 18:37:50 +00:00
|
|
|
aParent->ChildrenMustHaveWidgets(needsWidget);
|
2000-06-22 00:48:49 +00:00
|
|
|
if (needsWidget) {
|
2003-10-17 02:38:37 +00:00
|
|
|
nsHTMLContainerFrame::CreateViewForFrame(this, nsnull, PR_TRUE);
|
2000-06-22 00:48:49 +00:00
|
|
|
|
2003-07-09 03:30:40 +00:00
|
|
|
nsIView* view = GetView();
|
|
|
|
if (!view->HasWidget())
|
2000-06-22 00:48:49 +00:00
|
|
|
view->CreateWidget(kWidgetCID);
|
|
|
|
}
|
|
|
|
}
|
2000-04-05 00:19:00 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
CacheAttributes();
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-02 03:01:30 +00:00
|
|
|
// if we are root and this
|
|
|
|
if (mState & NS_STATE_IS_ROOT)
|
2006-04-10 00:16:29 +00:00
|
|
|
GetDebugPref(GetPresContext());
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-02-14 01:42:09 +00:00
|
|
|
|
2000-04-18 00:17:00 +00:00
|
|
|
mMouseThrough = unset;
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
UpdateMouseThrough();
|
2001-12-03 23:41:13 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
// register access key
|
2006-04-10 00:16:29 +00:00
|
|
|
rv = RegUnregAccessKey(PR_TRUE);
|
2002-02-21 13:39:39 +00:00
|
|
|
|
2001-12-03 23:41:13 +00:00
|
|
|
return rv;
|
|
|
|
}
|
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
void nsBoxFrame::UpdateMouseThrough()
|
2001-12-03 23:41:13 +00:00
|
|
|
{
|
2002-10-10 06:39:30 +00:00
|
|
|
if (mContent) {
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::never, &nsXULAtoms::always, nsnull};
|
|
|
|
static const eMouseThrough values[] = {never, always};
|
|
|
|
PRInt32 index = mContent->FindAttrValueIn(kNameSpaceID_None,
|
|
|
|
nsXULAtoms::mousethrough, strings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
mMouseThrough = values[index];
|
|
|
|
}
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
}
|
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetMouseThrough(PRBool& aMouseThrough)
|
|
|
|
{
|
|
|
|
switch(mMouseThrough)
|
|
|
|
{
|
|
|
|
case always:
|
|
|
|
aMouseThrough = PR_TRUE;
|
|
|
|
return NS_OK;
|
|
|
|
case never:
|
|
|
|
aMouseThrough = PR_FALSE;
|
|
|
|
return NS_OK;
|
|
|
|
case unset:
|
|
|
|
{
|
|
|
|
if (mParent && mParent->IsBoxFrame())
|
|
|
|
return mParent->GetMouseThrough(aMouseThrough);
|
|
|
|
else {
|
|
|
|
aMouseThrough = PR_FALSE;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
}
|
|
|
|
|
2000-06-23 05:15:04 +00:00
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::CacheAttributes()
|
2000-06-23 05:15:04 +00:00
|
|
|
{
|
|
|
|
/*
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Caching: ");
|
2002-10-10 06:39:30 +00:00
|
|
|
DumpBox(stdout);
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("\n");
|
2000-06-23 05:15:04 +00:00
|
|
|
*/
|
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
mValign = vAlign_Top;
|
|
|
|
mHalign = hAlign_Left;
|
2000-06-23 05:15:04 +00:00
|
|
|
|
|
|
|
PRBool orient = PR_FALSE;
|
2002-10-10 06:39:30 +00:00
|
|
|
GetInitialOrientation(orient);
|
2000-06-23 05:15:04 +00:00
|
|
|
if (orient)
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_IS_HORIZONTAL;
|
2001-08-02 00:09:27 +00:00
|
|
|
else
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_IS_HORIZONTAL;
|
2000-06-23 05:15:04 +00:00
|
|
|
|
2001-08-15 04:09:41 +00:00
|
|
|
PRBool normal = PR_TRUE;
|
2002-10-10 06:39:30 +00:00
|
|
|
GetInitialDirection(normal);
|
2001-08-15 04:09:41 +00:00
|
|
|
if (normal)
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_IS_DIRECTION_NORMAL;
|
2001-08-15 04:09:41 +00:00
|
|
|
else
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_IS_DIRECTION_NORMAL;
|
2001-08-15 04:09:41 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
GetInitialVAlignment(mValign);
|
|
|
|
GetInitialHAlignment(mHalign);
|
2001-08-02 00:09:27 +00:00
|
|
|
|
2000-06-23 05:15:04 +00:00
|
|
|
PRBool equalSize = PR_FALSE;
|
2002-10-10 06:39:30 +00:00
|
|
|
GetInitialEqualSize(equalSize);
|
2000-06-23 05:15:04 +00:00
|
|
|
if (equalSize)
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_EQUAL_SIZE;
|
2000-06-23 05:15:04 +00:00
|
|
|
else
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_EQUAL_SIZE;
|
2000-06-23 05:15:04 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool autostretch = mState & NS_STATE_AUTO_STRETCH;
|
|
|
|
GetInitialAutoStretch(autostretch);
|
2000-06-23 05:15:04 +00:00
|
|
|
if (autostretch)
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_AUTO_STRETCH;
|
2000-06-23 05:15:04 +00:00
|
|
|
else
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_AUTO_STRETCH;
|
2000-06-23 05:15:04 +00:00
|
|
|
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool debug = mState & NS_STATE_SET_TO_DEBUG;
|
2000-06-23 05:15:04 +00:00
|
|
|
PRBool debugSet = GetInitialDebug(debug);
|
|
|
|
if (debugSet) {
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_DEBUG_WAS_SET;
|
2000-06-23 05:15:04 +00:00
|
|
|
if (debug)
|
2002-10-10 06:39:30 +00:00
|
|
|
mState |= NS_STATE_SET_TO_DEBUG;
|
2000-06-23 05:15:04 +00:00
|
|
|
else
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_SET_TO_DEBUG;
|
2000-06-23 05:15:04 +00:00
|
|
|
} else {
|
2002-10-10 06:39:30 +00:00
|
|
|
mState &= ~NS_STATE_DEBUG_WAS_SET;
|
2000-06-23 05:15:04 +00:00
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-06-23 05:15:04 +00:00
|
|
|
}
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-02 03:01:30 +00:00
|
|
|
PRBool
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetInitialDebug(PRBool& aDebug)
|
2000-03-02 03:01:30 +00:00
|
|
|
{
|
|
|
|
nsCOMPtr<nsIContent> content;
|
2002-10-10 06:39:30 +00:00
|
|
|
GetContentOf(getter_AddRefs(content));
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
if (!content)
|
|
|
|
return PR_FALSE;
|
|
|
|
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::_false, &nsXULAtoms::_true, nsnull};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None,
|
|
|
|
nsXULAtoms::debug, strings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
aDebug = index == 1;
|
|
|
|
return PR_TRUE;
|
2000-03-02 03:01:30 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-02-14 01:42:09 +00:00
|
|
|
PRBool
|
|
|
|
nsBoxFrame::GetInitialHAlignment(nsBoxFrame::Halignment& aHalign)
|
|
|
|
{
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
nsCOMPtr<nsIContent> content;
|
2000-03-31 07:02:06 +00:00
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
if (!content)
|
|
|
|
return PR_FALSE;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2005-10-28 11:25:24 +00:00
|
|
|
// XXXdwh Everything inside this if statement is deprecated code.
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray alignStrings[] =
|
|
|
|
{&nsXULAtoms::left, &nsXULAtoms::right, nsnull};
|
|
|
|
static const Halignment alignValues[] = {hAlign_Left, hAlign_Right};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None, nsHTMLAtoms::align,
|
|
|
|
alignStrings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
aHalign = alignValues[index];
|
|
|
|
return PR_TRUE;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
}
|
2001-08-02 00:09:27 +00:00
|
|
|
|
|
|
|
// Now that the deprecated stuff is out of the way, we move on to check the appropriate
|
|
|
|
// attribute. For horizontal boxes, we are checking the PACK attribute. For vertical boxes
|
|
|
|
// we are checking the ALIGN attribute.
|
2006-01-18 04:09:33 +00:00
|
|
|
nsIAtom* attrName = IsHorizontal() ? nsXULAtoms::pack : nsHTMLAtoms::align;
|
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::_empty, &nsXULAtoms::start, &nsXULAtoms::center, &nsXULAtoms::end, nsnull};
|
|
|
|
static const Halignment values[] =
|
|
|
|
{hAlign_Left/*not used*/, hAlign_Left, hAlign_Center, hAlign_Right};
|
|
|
|
index = content->FindAttrValueIn(kNameSpaceID_None, attrName,
|
|
|
|
strings, eCaseMatters);
|
|
|
|
|
|
|
|
if (index == nsIContent::ATTR_VALUE_NO_MATCH) {
|
2001-08-02 00:09:27 +00:00
|
|
|
// The attr was present but had a nonsensical value. Revert to the default.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
2006-01-18 04:09:33 +00:00
|
|
|
if (index > 0) {
|
|
|
|
aHalign = values[index];
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
|
2001-08-02 00:09:27 +00:00
|
|
|
// Now that we've checked for the attribute it's time to check CSS. For
|
|
|
|
// horizontal boxes we're checking PACK. For vertical boxes we are checking
|
|
|
|
// ALIGN.
|
2003-05-15 03:42:21 +00:00
|
|
|
const nsStyleXUL* boxInfo = GetStyleXUL();
|
2001-08-02 00:09:27 +00:00
|
|
|
if (IsHorizontal()) {
|
|
|
|
switch (boxInfo->mBoxPack) {
|
|
|
|
case NS_STYLE_BOX_PACK_START:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Left;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_PACK_CENTER:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Center;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_PACK_END:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Right;
|
|
|
|
return PR_TRUE;
|
|
|
|
default: // Nonsensical value. Just bail.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
switch (boxInfo->mBoxAlign) {
|
|
|
|
case NS_STYLE_BOX_ALIGN_START:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Left;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_ALIGN_CENTER:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Center;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_ALIGN_END:
|
|
|
|
aHalign = nsBoxFrame::hAlign_Right;
|
|
|
|
return PR_TRUE;
|
|
|
|
default: // Nonsensical value. Just bail.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::GetInitialVAlignment(nsBoxFrame::Valignment& aValign)
|
|
|
|
{
|
|
|
|
nsCOMPtr<nsIContent> content;
|
2000-03-31 07:02:06 +00:00
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
if (!content)
|
|
|
|
return PR_FALSE;
|
2000-02-14 01:42:09 +00:00
|
|
|
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray valignStrings[] =
|
|
|
|
{&nsXULAtoms::top, &nsXULAtoms::baseline, &nsXULAtoms::middle, &nsXULAtoms::bottom, nsnull};
|
|
|
|
static const Valignment valignValues[] =
|
|
|
|
{vAlign_Top, vAlign_BaseLine, vAlign_Middle, vAlign_Bottom};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None, nsHTMLAtoms::valign,
|
|
|
|
valignStrings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
aValign = valignValues[index];
|
|
|
|
return PR_TRUE;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
}
|
|
|
|
|
2001-08-02 00:09:27 +00:00
|
|
|
// Now that the deprecated stuff is out of the way, we move on to check the appropriate
|
|
|
|
// attribute. For horizontal boxes, we are checking the ALIGN attribute. For vertical boxes
|
|
|
|
// we are checking the PACK attribute.
|
2006-01-18 04:09:33 +00:00
|
|
|
nsIAtom* attrName = IsHorizontal() ? nsHTMLAtoms::align : nsXULAtoms::pack;
|
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::_empty, &nsXULAtoms::start, &nsXULAtoms::center,
|
|
|
|
&nsXULAtoms::baseline, &nsXULAtoms::end, nsnull};
|
|
|
|
static const Valignment values[] =
|
|
|
|
{vAlign_Top/*not used*/, vAlign_Top, vAlign_Middle, vAlign_BaseLine, vAlign_Bottom};
|
|
|
|
index = content->FindAttrValueIn(kNameSpaceID_None, attrName,
|
|
|
|
strings, eCaseMatters);
|
|
|
|
if (index == nsIContent::ATTR_VALUE_NO_MATCH) {
|
2001-08-02 00:09:27 +00:00
|
|
|
// The attr was present but had a nonsensical value. Revert to the default.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
2006-01-18 04:09:33 +00:00
|
|
|
if (index > 0) {
|
|
|
|
aValign = values[index];
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
2001-08-02 00:09:27 +00:00
|
|
|
|
|
|
|
// Now that we've checked for the attribute it's time to check CSS. For
|
|
|
|
// horizontal boxes we're checking ALIGN. For vertical boxes we are checking
|
|
|
|
// PACK.
|
2003-05-15 03:42:21 +00:00
|
|
|
const nsStyleXUL* boxInfo = GetStyleXUL();
|
2001-08-02 00:09:27 +00:00
|
|
|
if (IsHorizontal()) {
|
|
|
|
switch (boxInfo->mBoxAlign) {
|
|
|
|
case NS_STYLE_BOX_ALIGN_START:
|
|
|
|
aValign = nsBoxFrame::vAlign_Top;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_ALIGN_CENTER:
|
|
|
|
aValign = nsBoxFrame::vAlign_Middle;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_ALIGN_BASELINE:
|
|
|
|
aValign = nsBoxFrame::vAlign_BaseLine;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_ALIGN_END:
|
|
|
|
aValign = nsBoxFrame::vAlign_Bottom;
|
|
|
|
return PR_TRUE;
|
|
|
|
default: // Nonsensical value. Just bail.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
switch (boxInfo->mBoxPack) {
|
|
|
|
case NS_STYLE_BOX_PACK_START:
|
|
|
|
aValign = nsBoxFrame::vAlign_Top;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_PACK_CENTER:
|
|
|
|
aValign = nsBoxFrame::vAlign_Middle;
|
|
|
|
return PR_TRUE;
|
|
|
|
case NS_STYLE_BOX_PACK_END:
|
|
|
|
aValign = nsBoxFrame::vAlign_Bottom;
|
|
|
|
return PR_TRUE;
|
|
|
|
default: // Nonsensical value. Just bail.
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
|
|
|
|
return PR_FALSE;
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
2001-03-06 02:27:50 +00:00
|
|
|
void
|
2000-02-14 01:42:09 +00:00
|
|
|
nsBoxFrame::GetInitialOrientation(PRBool& aIsHorizontal)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
|
|
|
// see if we are a vertical or horizontal box.
|
1999-10-12 00:16:06 +00:00
|
|
|
nsCOMPtr<nsIContent> content;
|
2000-03-31 07:02:06 +00:00
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
|
|
|
|
if (!content)
|
2001-03-06 02:27:50 +00:00
|
|
|
return;
|
|
|
|
|
|
|
|
// Check the style system first.
|
2003-05-15 03:42:21 +00:00
|
|
|
const nsStyleXUL* boxInfo = GetStyleXUL();
|
2001-03-06 02:27:50 +00:00
|
|
|
if (boxInfo->mBoxOrient == NS_STYLE_BOX_ORIENT_HORIZONTAL)
|
|
|
|
aIsHorizontal = PR_TRUE;
|
|
|
|
else
|
|
|
|
aIsHorizontal = PR_FALSE;
|
|
|
|
|
|
|
|
// Now see if we have an attribute. The attribute overrides
|
|
|
|
// the style system value.
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::vertical, &nsXULAtoms::horizontal, nsnull};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None, nsXULAtoms::orient,
|
|
|
|
strings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
aIsHorizontal = index == 1;
|
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
}
|
|
|
|
|
2001-08-15 04:09:41 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::GetInitialDirection(PRBool& aIsNormal)
|
|
|
|
{
|
|
|
|
nsCOMPtr<nsIContent> content;
|
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
|
|
|
|
if (!content)
|
|
|
|
return;
|
|
|
|
|
|
|
|
if (IsHorizontal()) {
|
|
|
|
// For horizontal boxes only, we initialize our value based off the CSS 'direction' property.
|
|
|
|
// This means that BiDI users will end up with horizontally inverted chrome.
|
2003-05-15 03:42:21 +00:00
|
|
|
aIsNormal = (GetStyleVisibility()->mDirection == NS_STYLE_DIRECTION_LTR); // If text runs RTL then so do we.
|
2001-08-15 04:09:41 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
aIsNormal = PR_TRUE; // Assume a normal direction in the vertical case.
|
|
|
|
|
|
|
|
// Now check the style system to see if we should invert aIsNormal.
|
2003-05-15 03:42:21 +00:00
|
|
|
const nsStyleXUL* boxInfo = GetStyleXUL();
|
2001-08-15 04:09:41 +00:00
|
|
|
if (boxInfo->mBoxDirection == NS_STYLE_BOX_DIRECTION_REVERSE)
|
|
|
|
aIsNormal = !aIsNormal; // Invert our direction.
|
|
|
|
|
|
|
|
// Now see if we have an attribute. The attribute overrides
|
|
|
|
// the style system value.
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::reverse, &nsXULAtoms::ltr, &nsXULAtoms::rtl, nsnull};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None, nsXULAtoms::dir,
|
|
|
|
strings, eCaseMatters);
|
|
|
|
if (index >= 0) {
|
|
|
|
PRPackedBool values[] = {!aIsNormal, PR_TRUE, PR_FALSE};
|
|
|
|
aIsNormal = values[index];
|
2001-08-15 04:09:41 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2000-06-23 05:15:04 +00:00
|
|
|
/* Returns true if it was set.
|
|
|
|
*/
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::GetInitialEqualSize(PRBool& aEqualSize)
|
|
|
|
{
|
|
|
|
// see if we are a vertical or horizontal box.
|
|
|
|
nsCOMPtr<nsIContent> content;
|
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
|
|
|
|
if (!content)
|
|
|
|
return PR_FALSE;
|
2005-10-28 11:25:24 +00:00
|
|
|
|
|
|
|
if (content->AttrValueIs(kNameSpaceID_None, nsXULAtoms::equalsize,
|
|
|
|
nsLayoutAtoms::always, eCaseMatters)) {
|
|
|
|
aEqualSize = PR_TRUE;
|
|
|
|
return PR_TRUE;
|
2000-06-23 05:15:04 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
2000-02-14 01:42:09 +00:00
|
|
|
/* Returns true if it was set.
|
|
|
|
*/
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::GetInitialAutoStretch(PRBool& aStretch)
|
|
|
|
{
|
|
|
|
nsCOMPtr<nsIContent> content;
|
2000-03-31 07:02:06 +00:00
|
|
|
GetContentOf(getter_AddRefs(content));
|
|
|
|
|
|
|
|
if (!content)
|
|
|
|
return PR_FALSE;
|
107642 - XUL syntax/cleanup landing. Fixes 94470, 96008, 96019, 76800, 102637, 80399, 108303, and removes over a thousand unnecessary or nonsensical attributes. Also fixes 108302, 102366, 102367, 105815. r=sspitzer,cmanske on appropriate parts sr=ben
2001-11-03 04:17:02 +00:00
|
|
|
|
|
|
|
// Check the align attribute.
|
2006-01-18 04:09:33 +00:00
|
|
|
static nsIContent::AttrValuesArray strings[] =
|
|
|
|
{&nsXULAtoms::_empty, &nsXULAtoms::stretch, nsnull};
|
|
|
|
PRInt32 index = content->FindAttrValueIn(kNameSpaceID_None, nsHTMLAtoms::align,
|
|
|
|
strings, eCaseMatters);
|
|
|
|
if (index != nsIContent::ATTR_MISSING && index != 0) {
|
|
|
|
aStretch = index == 1;
|
107642 - XUL syntax/cleanup landing. Fixes 94470, 96008, 96019, 76800, 102637, 80399, 108303, and removes over a thousand unnecessary or nonsensical attributes. Also fixes 108302, 102366, 102367, 105815. r=sspitzer,cmanske on appropriate parts sr=ben
2001-11-03 04:17:02 +00:00
|
|
|
return PR_TRUE;
|
2001-08-02 00:09:27 +00:00
|
|
|
}
|
2000-02-14 01:42:09 +00:00
|
|
|
|
107642 - XUL syntax/cleanup landing. Fixes 94470, 96008, 96019, 76800, 102637, 80399, 108303, and removes over a thousand unnecessary or nonsensical attributes. Also fixes 108302, 102366, 102367, 105815. r=sspitzer,cmanske on appropriate parts sr=ben
2001-11-03 04:17:02 +00:00
|
|
|
// Check the CSS box-align property.
|
2003-05-15 03:42:21 +00:00
|
|
|
const nsStyleXUL* boxInfo = GetStyleXUL();
|
107642 - XUL syntax/cleanup landing. Fixes 94470, 96008, 96019, 76800, 102637, 80399, 108303, and removes over a thousand unnecessary or nonsensical attributes. Also fixes 108302, 102366, 102367, 105815. r=sspitzer,cmanske on appropriate parts sr=ben
2001-11-03 04:17:02 +00:00
|
|
|
aStretch = (boxInfo->mBoxAlign == NS_STYLE_BOX_ALIGN_STRETCH);
|
2001-08-02 00:09:27 +00:00
|
|
|
|
|
|
|
return PR_TRUE;
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
1999-07-02 05:28:32 +00:00
|
|
|
|
1999-11-18 21:05:43 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::ReflowDirtyChild(nsIPresShell* aPresShell, nsIFrame* aChild)
|
|
|
|
{
|
2001-12-03 23:41:13 +00:00
|
|
|
// if we receive a ReflowDirtyChild it is because there is an HTML frame
|
|
|
|
// just inside us. So must find the adaptor that contains the child and
|
|
|
|
// tell it that things are dirty.
|
2004-08-20 20:34:37 +00:00
|
|
|
nsBoxLayoutState state(aPresShell->GetPresContext());
|
2001-12-03 23:41:13 +00:00
|
|
|
|
|
|
|
nsIBox* box = nsnull;
|
|
|
|
GetChildBox(&box);
|
|
|
|
while (box)
|
|
|
|
{
|
2004-09-28 18:37:50 +00:00
|
|
|
if (box == aChild) {
|
2001-12-03 23:41:13 +00:00
|
|
|
box->MarkDirty(state);
|
|
|
|
return RelayoutDirtyChild(state, box);
|
|
|
|
}
|
|
|
|
|
|
|
|
box->GetNextBox(&box);
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_ERROR("Could not find an adaptor!");
|
|
|
|
return NS_OK;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
1999-11-18 21:05:43 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::DidReflow(nsPresContext* aPresContext,
|
2001-12-07 14:51:12 +00:00
|
|
|
const nsHTMLReflowState* aReflowState,
|
|
|
|
nsDidReflowStatus aStatus)
|
1999-09-10 00:57:01 +00:00
|
|
|
{
|
2003-06-01 20:03:13 +00:00
|
|
|
nsFrameState preserveBits =
|
|
|
|
mState & (NS_FRAME_IS_DIRTY | NS_FRAME_HAS_DIRTY_CHILDREN);
|
2001-12-07 14:51:12 +00:00
|
|
|
nsresult rv = nsFrame::DidReflow(aPresContext, aReflowState, aStatus);
|
2003-06-01 20:03:13 +00:00
|
|
|
mState |= preserveBits;
|
2000-03-31 07:02:06 +00:00
|
|
|
return rv;
|
1999-09-10 00:57:01 +00:00
|
|
|
}
|
|
|
|
|
2000-08-23 11:02:19 +00:00
|
|
|
#ifdef DO_NOISY_REFLOW
|
|
|
|
static int myCounter = 0;
|
|
|
|
static void printSize(char * aDesc, nscoord aSize)
|
|
|
|
{
|
2000-10-28 22:17:53 +00:00
|
|
|
printf(" %s: ", aDesc);
|
2000-08-23 11:02:19 +00:00
|
|
|
if (aSize == NS_UNCONSTRAINEDSIZE) {
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("UC");
|
2000-08-23 11:02:19 +00:00
|
|
|
} else {
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("%d", aSize);
|
2000-08-23 11:02:19 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-01-23 02:53:02 +00:00
|
|
|
/**
|
|
|
|
* Returns PR_TRUE when the reflow reason is "Initial" and doing Print Preview
|
|
|
|
* when returning PR_FALSE aIsChrome's value is indeterminate
|
|
|
|
* aIsChrome - Returns PR_TRUE when document is chrome, otherwise PR_FALSE
|
|
|
|
*/
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::IsInitialReflowForPrintPreview(nsBoxLayoutState& aState,
|
|
|
|
PRBool& aIsChrome)
|
|
|
|
{
|
|
|
|
aIsChrome = PR_FALSE;
|
|
|
|
const nsHTMLReflowState* reflowState = aState.GetReflowState();
|
|
|
|
if (reflowState->reason == eReflowReason_Initial) {
|
|
|
|
// See if we are doing Print Preview
|
2006-04-01 01:19:28 +00:00
|
|
|
if (aState.PresContext()->Type() == nsPresContext::eContext_PrintPreview ||
|
|
|
|
aState.PresContext()->Type() == nsPresContext::eContext_PageLayout) {
|
2003-12-21 05:36:36 +00:00
|
|
|
// Now, get the current URI to see if we doing chrome
|
2004-06-22 02:55:04 +00:00
|
|
|
nsIPresShell *presShell = aState.PresShell();
|
2002-01-23 02:53:02 +00:00
|
|
|
if (!presShell) return PR_FALSE;
|
2004-08-02 04:52:55 +00:00
|
|
|
nsIDocument *doc = presShell->GetDocument();
|
2002-01-23 02:53:02 +00:00
|
|
|
if (!doc) return PR_FALSE;
|
2004-01-09 23:54:21 +00:00
|
|
|
nsIURI *uri = doc->GetDocumentURI();
|
2002-01-23 02:53:02 +00:00
|
|
|
if (!uri) return PR_FALSE;
|
|
|
|
uri->SchemeIs("chrome", &aIsChrome);
|
|
|
|
return PR_TRUE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return PR_FALSE;
|
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::Reflow(nsPresContext* aPresContext,
|
2002-05-28 22:50:43 +00:00
|
|
|
nsHTMLReflowMetrics& aDesiredSize,
|
|
|
|
const nsHTMLReflowState& aReflowState,
|
|
|
|
nsReflowStatus& aStatus)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2002-02-14 00:08:08 +00:00
|
|
|
// If you make changes to this method, please keep nsLeafBoxFrame::Reflow
|
|
|
|
// in sync, if the changes are applicable there.
|
|
|
|
|
2000-04-21 14:59:47 +00:00
|
|
|
DO_GLOBAL_REFLOW_COUNT("nsBoxFrame", aReflowState.reason);
|
2002-03-03 19:53:56 +00:00
|
|
|
DISPLAY_REFLOW(aPresContext, this, aReflowState, aDesiredSize, aStatus);
|
1999-03-27 01:35:55 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_ASSERTION(aReflowState.mComputedWidth >=0 && aReflowState.mComputedHeight >= 0, "Computed Size < 0");
|
1999-04-12 21:48:21 +00:00
|
|
|
|
2000-08-23 11:02:19 +00:00
|
|
|
#ifdef DO_NOISY_REFLOW
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("\n-------------Starting BoxFrame Reflow ----------------------------\n");
|
|
|
|
printf("%p ** nsBF::Reflow %d R: ", this, myCounter++);
|
2000-08-23 11:02:19 +00:00
|
|
|
switch (aReflowState.reason) {
|
|
|
|
case eReflowReason_Initial:
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Ini");break;
|
2000-08-23 11:02:19 +00:00
|
|
|
case eReflowReason_Incremental:
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Inc");break;
|
2000-08-23 11:02:19 +00:00
|
|
|
case eReflowReason_Resize:
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Rsz");break;
|
2000-08-23 11:02:19 +00:00
|
|
|
case eReflowReason_StyleChange:
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Sty");break;
|
2000-08-23 11:02:19 +00:00
|
|
|
case eReflowReason_Dirty:
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("Drt ");
|
2000-08-23 11:02:19 +00:00
|
|
|
break;
|
2000-10-28 22:17:53 +00:00
|
|
|
default:printf("<unknown>%d", aReflowState.reason);break;
|
2000-08-23 11:02:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
printSize("AW", aReflowState.availableWidth);
|
|
|
|
printSize("AH", aReflowState.availableHeight);
|
|
|
|
printSize("CW", aReflowState.mComputedWidth);
|
|
|
|
printSize("CH", aReflowState.mComputedHeight);
|
|
|
|
|
2000-10-28 22:17:53 +00:00
|
|
|
printf(" *\n");
|
2000-08-23 11:02:19 +00:00
|
|
|
|
|
|
|
#endif
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
aStatus = NS_FRAME_COMPLETE;
|
1999-04-12 21:48:21 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// create the layout state
|
2000-04-03 03:55:38 +00:00
|
|
|
nsBoxLayoutState state(aPresContext, aReflowState, aDesiredSize);
|
1999-04-12 21:48:21 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// coelesce reflows if we are root.
|
2000-04-25 07:10:48 +00:00
|
|
|
state.HandleReflow(this);
|
2000-04-05 23:02:29 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsSize computedSize(aReflowState.mComputedWidth,aReflowState.mComputedHeight);
|
1999-09-13 20:24:20 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsMargin m;
|
2002-09-25 20:23:34 +00:00
|
|
|
m = aReflowState.mComputedBorderPadding;
|
|
|
|
// GetBorderAndPadding(m);
|
1999-08-30 22:32:25 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsSize prefSize(0,0);
|
1999-09-13 20:24:20 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// if we are told to layout intrinic then get our preferred size.
|
|
|
|
if (computedSize.width == NS_INTRINSICSIZE || computedSize.height == NS_INTRINSICSIZE) {
|
2000-04-05 00:19:00 +00:00
|
|
|
nsSize minSize(0,0);
|
|
|
|
nsSize maxSize(0,0);
|
2000-03-31 07:02:06 +00:00
|
|
|
GetPrefSize(state, prefSize);
|
|
|
|
GetMinSize(state, minSize);
|
|
|
|
GetMaxSize(state, maxSize);
|
|
|
|
BoundsCheck(minSize, prefSize, maxSize);
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// get our desiredSize
|
2000-08-17 20:08:44 +00:00
|
|
|
if (aReflowState.mComputedWidth == NS_INTRINSICSIZE) {
|
2000-08-24 13:19:57 +00:00
|
|
|
computedSize.width = prefSize.width;
|
2000-08-17 20:08:44 +00:00
|
|
|
} else {
|
|
|
|
computedSize.width += m.left + m.right;
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-08-17 20:08:44 +00:00
|
|
|
if (aReflowState.mComputedHeight == NS_INTRINSICSIZE) {
|
2000-08-24 13:19:57 +00:00
|
|
|
computedSize.height = prefSize.height;
|
2000-08-17 20:08:44 +00:00
|
|
|
} else {
|
|
|
|
computedSize.height += m.top + m.bottom;
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-10-07 00:49:08 +00:00
|
|
|
// handle reflow state min and max sizes
|
|
|
|
|
|
|
|
if (computedSize.width > aReflowState.mComputedMaxWidth)
|
|
|
|
computedSize.width = aReflowState.mComputedMaxWidth;
|
|
|
|
|
|
|
|
if (computedSize.height > aReflowState.mComputedMaxHeight)
|
|
|
|
computedSize.height = aReflowState.mComputedMaxHeight;
|
|
|
|
|
|
|
|
if (computedSize.width < aReflowState.mComputedMinWidth)
|
|
|
|
computedSize.width = aReflowState.mComputedMinWidth;
|
|
|
|
|
|
|
|
if (computedSize.height < aReflowState.mComputedMinHeight)
|
|
|
|
computedSize.height = aReflowState.mComputedMinHeight;
|
|
|
|
|
2000-06-23 05:15:04 +00:00
|
|
|
nsRect r(mRect.x, mRect.y, computedSize.width, computedSize.height);
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
SetBounds(state, r);
|
|
|
|
|
|
|
|
// layout our children
|
|
|
|
Layout(state);
|
|
|
|
|
|
|
|
// ok our child could have gotten bigger. So lets get its bounds
|
|
|
|
|
|
|
|
// get the ascent
|
2004-09-28 18:37:50 +00:00
|
|
|
nscoord ascent = mRect.height;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// getting the ascent could be a lot of work. Don't get it if
|
|
|
|
// we are the root. The viewport doesn't care about it.
|
2002-01-23 02:53:02 +00:00
|
|
|
if (!(mState & NS_STATE_IS_ROOT)) {
|
|
|
|
// Only call GetAscent when not doing Initial reflow while in PP
|
|
|
|
// or when it is Initial reflow while in PP and a chrome doc
|
|
|
|
// If called again with initial reflow it crashes because the
|
|
|
|
// frames are fully constructed (I think).
|
|
|
|
PRBool isChrome;
|
|
|
|
PRBool isInitialPP = IsInitialReflowForPrintPreview(state, isChrome);
|
|
|
|
if (!isInitialPP || (isInitialPP && isChrome)) {
|
|
|
|
GetAscent(state, ascent);
|
|
|
|
}
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
aDesiredSize.width = mRect.width;
|
|
|
|
aDesiredSize.height = mRect.height;
|
2000-03-31 07:02:06 +00:00
|
|
|
aDesiredSize.ascent = ascent;
|
2004-09-28 18:37:50 +00:00
|
|
|
aDesiredSize.descent = mRect.height - ascent;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2004-07-16 16:56:21 +00:00
|
|
|
// NS_FRAME_OUTSIDE_CHILDREN is set in SetBounds() above
|
|
|
|
if (mState & NS_FRAME_OUTSIDE_CHILDREN) {
|
|
|
|
nsRect* overflowArea = GetOverflowAreaProperty();
|
|
|
|
NS_ASSERTION(overflowArea, "Failed to set overflow area property");
|
|
|
|
aDesiredSize.mOverflowArea = *overflowArea;
|
|
|
|
}
|
|
|
|
|
2005-01-09 21:23:43 +00:00
|
|
|
if(aDesiredSize.mFlags & NS_REFLOW_CALC_MAX_WIDTH) {
|
|
|
|
aDesiredSize.mMaximumWidth = prefSize.width;
|
|
|
|
}
|
|
|
|
|
2000-04-05 00:19:00 +00:00
|
|
|
// max sure the max element size reflects
|
|
|
|
// our min width
|
2003-01-09 14:26:32 +00:00
|
|
|
nscoord* maxElementWidth = state.GetMaxElementWidth();
|
|
|
|
if (maxElementWidth)
|
2000-04-05 00:19:00 +00:00
|
|
|
{
|
|
|
|
nsSize minSize(0,0);
|
2000-06-23 02:28:01 +00:00
|
|
|
GetMinSize(state, minSize);
|
2004-08-31 18:50:40 +00:00
|
|
|
if (aReflowState.mStylePosition->mWidth.GetUnit() == eStyleUnit_Percent ||
|
|
|
|
(mRect.width > minSize.width &&
|
|
|
|
aReflowState.mComputedWidth == NS_INTRINSICSIZE))
|
|
|
|
*maxElementWidth = minSize.width;
|
2003-06-01 20:03:13 +00:00
|
|
|
else
|
|
|
|
*maxElementWidth = mRect.width;
|
2000-04-05 00:19:00 +00:00
|
|
|
}
|
2000-08-23 11:02:19 +00:00
|
|
|
#ifdef DO_NOISY_REFLOW
|
|
|
|
{
|
2000-10-28 22:17:53 +00:00
|
|
|
printf("%p ** nsBF(done) W:%d H:%d ", this, aDesiredSize.width, aDesiredSize.height);
|
2000-08-23 11:02:19 +00:00
|
|
|
|
|
|
|
if (maxElementSize) {
|
2003-01-09 14:26:32 +00:00
|
|
|
printf("MW:%d\n", *maxElementWidth);
|
2000-08-23 11:02:19 +00:00
|
|
|
} else {
|
2003-01-09 14:26:32 +00:00
|
|
|
printf("MW:?\n");
|
2000-08-23 11:02:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
#endif
|
2000-04-05 00:19:00 +00:00
|
|
|
|
2002-05-28 22:50:43 +00:00
|
|
|
NS_FRAME_SET_TRUNCATION(aStatus, aReflowState, aDesiredSize);
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
1999-04-12 21:48:21 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetPrefSize(nsBoxLayoutState& aBoxLayoutState, nsSize& aSize)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2000-06-06 01:25:03 +00:00
|
|
|
if (!DoesNeedRecalc(mPrefSize)) {
|
|
|
|
aSize = mPrefSize;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
2000-02-25 04:18:34 +00:00
|
|
|
}
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
PropagateDebug(aBoxLayoutState);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
1999-03-27 01:35:55 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult rv = NS_OK;
|
2004-09-28 18:37:50 +00:00
|
|
|
aSize.width = 0;
|
|
|
|
aSize.height = 0;
|
|
|
|
|
|
|
|
PRBool collapsed = PR_FALSE;
|
|
|
|
IsCollapsed(aBoxLayoutState, collapsed);
|
2005-04-03 21:19:37 +00:00
|
|
|
if (collapsed) {
|
2004-09-28 18:37:50 +00:00
|
|
|
return NS_OK;
|
2005-04-03 21:19:37 +00:00
|
|
|
}
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
// if the size was not completely redefined in CSS then ask our children
|
|
|
|
if (!nsIBox::AddCSSPrefSize(aBoxLayoutState, this, aSize))
|
|
|
|
{
|
|
|
|
aSize.width = 0;
|
|
|
|
aSize.height = 0;
|
|
|
|
|
|
|
|
if (mLayoutManager) {
|
|
|
|
rv = mLayoutManager->GetPrefSize(this, aBoxLayoutState, aSize);
|
|
|
|
nsIBox::AddCSSPrefSize(aBoxLayoutState, this, aSize);
|
|
|
|
} else
|
|
|
|
rv = nsBox::GetPrefSize(aBoxLayoutState, aSize);
|
|
|
|
}
|
|
|
|
|
|
|
|
nsSize minSize(0,0);
|
|
|
|
nsSize maxSize(0,0);
|
|
|
|
GetMinSize(aBoxLayoutState, minSize);
|
|
|
|
GetMaxSize(aBoxLayoutState, maxSize);
|
|
|
|
|
|
|
|
BoundsCheck(minSize, aSize, maxSize);
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
mPrefSize = aSize;
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
return rv;
|
|
|
|
}
|
1999-10-21 20:17:51 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetAscent(nsBoxLayoutState& aBoxLayoutState, nscoord& aAscent)
|
|
|
|
{
|
2000-06-06 01:25:03 +00:00
|
|
|
if (!DoesNeedRecalc(mAscent)) {
|
|
|
|
aAscent = mAscent;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
PropagateDebug(aBoxLayoutState);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult rv = NS_OK;
|
2004-09-28 18:37:50 +00:00
|
|
|
aAscent = 0;
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
PRBool collapsed = PR_FALSE;
|
|
|
|
IsCollapsed(aBoxLayoutState, collapsed);
|
|
|
|
if (collapsed)
|
|
|
|
return NS_OK;
|
|
|
|
|
|
|
|
if (mLayoutManager)
|
|
|
|
rv = mLayoutManager->GetAscent(this, aBoxLayoutState, aAscent);
|
|
|
|
else
|
|
|
|
rv = nsBox::GetAscent(aBoxLayoutState, aAscent);
|
|
|
|
|
|
|
|
mAscent = aAscent;
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
return rv;
|
|
|
|
}
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetMinSize(nsBoxLayoutState& aBoxLayoutState, nsSize& aSize)
|
|
|
|
{
|
2000-06-06 01:25:03 +00:00
|
|
|
if (!DoesNeedRecalc(mMinSize)) {
|
|
|
|
aSize = mMinSize;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
PropagateDebug(aBoxLayoutState);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult rv = NS_OK;
|
2000-02-10 21:36:28 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
aSize.SizeTo(0, 0);
|
|
|
|
|
|
|
|
PRBool collapsed = PR_FALSE;
|
|
|
|
IsCollapsed(aBoxLayoutState, collapsed);
|
|
|
|
if (collapsed)
|
|
|
|
return NS_OK;
|
|
|
|
|
|
|
|
// if the size was not completely redefined in CSS then ask our children
|
|
|
|
if (!nsIBox::AddCSSMinSize(aBoxLayoutState, this, aSize))
|
|
|
|
{
|
|
|
|
aSize.width = 0;
|
|
|
|
aSize.height = 0;
|
|
|
|
|
|
|
|
if (mLayoutManager) {
|
|
|
|
rv = mLayoutManager->GetMinSize(this, aBoxLayoutState, aSize);
|
|
|
|
nsIBox::AddCSSMinSize(aBoxLayoutState, this, aSize);
|
|
|
|
} else {
|
|
|
|
rv = nsBox::GetMinSize(aBoxLayoutState, aSize);
|
|
|
|
}
|
|
|
|
}
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
mMinSize = aSize;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
return rv;
|
|
|
|
}
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetMaxSize(nsBoxLayoutState& aBoxLayoutState, nsSize& aSize)
|
|
|
|
{
|
2000-06-06 01:25:03 +00:00
|
|
|
if (!DoesNeedRecalc(mMaxSize)) {
|
|
|
|
aSize = mMaxSize;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1999-07-23 23:30:17 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
PropagateDebug(aBoxLayoutState);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult rv = NS_OK;
|
1999-07-23 00:11:21 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
aSize.SizeTo(NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
|
|
|
|
PRBool collapsed = PR_FALSE;
|
|
|
|
IsCollapsed(aBoxLayoutState, collapsed);
|
|
|
|
if (collapsed)
|
|
|
|
return NS_OK;
|
|
|
|
|
|
|
|
// if the size was not completely redefined in CSS then ask our children
|
|
|
|
if (!nsIBox::AddCSSMaxSize(aBoxLayoutState, this, aSize))
|
|
|
|
{
|
|
|
|
aSize.width = NS_INTRINSICSIZE;
|
|
|
|
aSize.height = NS_INTRINSICSIZE;
|
|
|
|
|
|
|
|
if (mLayoutManager) {
|
|
|
|
rv = mLayoutManager->GetMaxSize(this, aBoxLayoutState, aSize);
|
|
|
|
nsIBox::AddCSSMaxSize(aBoxLayoutState, this, aSize);
|
|
|
|
} else {
|
|
|
|
rv = nsBox::GetMaxSize(aBoxLayoutState, aSize);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
mMaxSize = aSize;
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
return rv;
|
1999-03-27 01:35:55 +00:00
|
|
|
}
|
|
|
|
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
NS_IMETHODIMP
|
2000-03-31 07:02:06 +00:00
|
|
|
nsBoxFrame::GetFlex(nsBoxLayoutState& aBoxLayoutState, nscoord& aFlex)
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
{
|
2000-06-06 01:25:03 +00:00
|
|
|
if (!DoesNeedRecalc(mFlex)) {
|
|
|
|
aFlex = mFlex;
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult rv = NS_OK;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-06-06 01:25:03 +00:00
|
|
|
mFlex = 0;
|
2004-09-28 18:37:50 +00:00
|
|
|
rv = nsBox::GetFlex(aBoxLayoutState, mFlex);
|
2000-06-06 01:25:03 +00:00
|
|
|
aFlex = mFlex;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
return rv;
|
|
|
|
}
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2000-07-07 22:24:06 +00:00
|
|
|
/**
|
|
|
|
* If subclassing please subclass this method not layout.
|
|
|
|
* layout will call this method.
|
|
|
|
*/
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::DoLayout(nsBoxLayoutState& aState)
|
|
|
|
{
|
2004-09-28 18:37:50 +00:00
|
|
|
PRUint32 oldFlags = aState.LayoutFlags();
|
|
|
|
aState.SetLayoutFlags(0);
|
|
|
|
|
|
|
|
nsresult rv = NS_OK;
|
|
|
|
if (mLayoutManager)
|
|
|
|
rv = mLayoutManager->Layout(this, aState);
|
|
|
|
|
|
|
|
aState.SetLayoutFlags(oldFlags);
|
|
|
|
|
|
|
|
return rv;
|
2000-07-07 22:24:06 +00:00
|
|
|
}
|
|
|
|
|
2006-04-10 00:16:29 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::Destroy()
|
2000-02-17 04:10:02 +00:00
|
|
|
{
|
2002-02-21 13:39:39 +00:00
|
|
|
// unregister access key
|
2006-04-10 00:16:29 +00:00
|
|
|
RegUnregAccessKey(PR_FALSE);
|
2002-02-21 13:39:39 +00:00
|
|
|
|
2003-03-26 06:52:20 +00:00
|
|
|
// clean up the container box's layout manager and child boxes
|
2004-09-28 18:37:50 +00:00
|
|
|
SetLayoutManager(nsnull);
|
2000-04-18 00:17:00 +00:00
|
|
|
|
2006-04-10 00:16:29 +00:00
|
|
|
nsContainerFrame::Destroy();
|
2000-02-17 04:10:02 +00:00
|
|
|
}
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-02 03:01:30 +00:00
|
|
|
NS_IMETHODIMP
|
2000-03-31 07:02:06 +00:00
|
|
|
nsBoxFrame::SetDebug(nsBoxLayoutState& aState, PRBool aDebug)
|
2000-03-02 03:01:30 +00:00
|
|
|
{
|
|
|
|
// see if our state matches the given debug state
|
|
|
|
PRBool debugSet = mState & NS_STATE_CURRENTLY_IN_DEBUG;
|
|
|
|
PRBool debugChanged = (!aDebug && debugSet) || (aDebug && !debugSet);
|
|
|
|
|
|
|
|
// if it doesn't then tell each child below us the new debug state
|
|
|
|
if (debugChanged)
|
|
|
|
{
|
|
|
|
if (aDebug) {
|
|
|
|
mState |= NS_STATE_CURRENTLY_IN_DEBUG;
|
|
|
|
} else {
|
|
|
|
mState &= ~NS_STATE_CURRENTLY_IN_DEBUG;
|
|
|
|
}
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
SetDebugOnChildList(aState, mFirstChild, aDebug);
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NeedsRecalc();
|
2000-03-02 03:01:30 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::NeedsRecalc()
|
2000-03-02 03:01:30 +00:00
|
|
|
{
|
2002-10-10 06:39:30 +00:00
|
|
|
SizeNeedsRecalc(mPrefSize);
|
|
|
|
SizeNeedsRecalc(mMinSize);
|
|
|
|
SizeNeedsRecalc(mMaxSize);
|
|
|
|
CoordNeedsRecalc(mFlex);
|
|
|
|
CoordNeedsRecalc(mAscent);
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
2005-02-07 01:58:25 +00:00
|
|
|
nsBoxFrame::RemoveFrame(nsIAtom* aListName,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aOldFrame)
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2005-02-20 22:29:28 +00:00
|
|
|
NS_PRECONDITION(!aListName, "We don't support out-of-flow kids");
|
2005-02-07 01:58:25 +00:00
|
|
|
nsPresContext* presContext = GetPresContext();
|
|
|
|
nsBoxLayoutState state(presContext);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
// remove the child frame
|
2004-09-28 18:37:50 +00:00
|
|
|
mFrames.RemoveFrame(aOldFrame);
|
|
|
|
|
|
|
|
// notify the layout manager
|
|
|
|
if (mLayoutManager)
|
|
|
|
mLayoutManager->ChildrenRemoved(this, state, aOldFrame);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
// destroy the child frame
|
2006-04-10 00:16:29 +00:00
|
|
|
aOldFrame->Destroy();
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
// mark us dirty and generate a reflow command
|
|
|
|
MarkDirtyChildren(state);
|
|
|
|
MarkDirty(state);
|
|
|
|
return NS_OK;
|
2000-03-02 03:01:30 +00:00
|
|
|
}
|
|
|
|
|
1999-05-09 21:46:24 +00:00
|
|
|
NS_IMETHODIMP
|
2005-02-07 01:58:25 +00:00
|
|
|
nsBoxFrame::InsertFrames(nsIAtom* aListName,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aPrevFrame,
|
|
|
|
nsIFrame* aFrameList)
|
1999-05-09 21:46:24 +00:00
|
|
|
{
|
2006-06-29 02:32:36 +00:00
|
|
|
NS_ASSERTION(!aPrevFrame || aPrevFrame->GetParent() == this,
|
|
|
|
"inserting after sibling frame with different parent");
|
2005-02-20 22:29:28 +00:00
|
|
|
NS_PRECONDITION(!aListName, "We don't support out-of-flow kids");
|
2005-02-07 01:58:25 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext());
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
// insert the child frames
|
2000-02-16 23:00:52 +00:00
|
|
|
mFrames.InsertFrames(this, aPrevFrame, aFrameList);
|
1999-11-18 21:05:43 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
// notify the layout manager
|
|
|
|
if (mLayoutManager)
|
|
|
|
mLayoutManager->ChildrenInserted(this, state, aPrevFrame, aFrameList);
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-02 03:01:30 +00:00
|
|
|
// if we are in debug make sure our children are in debug as well.
|
|
|
|
if (mState & NS_STATE_CURRENTLY_IN_DEBUG)
|
2004-09-28 18:37:50 +00:00
|
|
|
SetDebugOnChildList(state, mFrames.FirstChild(), PR_TRUE);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
1999-11-18 21:05:43 +00:00
|
|
|
// mark us dirty and generate a reflow command
|
2000-03-31 07:02:06 +00:00
|
|
|
MarkDirtyChildren(state);
|
|
|
|
MarkDirty(state);
|
|
|
|
return NS_OK;
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
1999-05-09 21:46:24 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
2005-02-07 01:58:25 +00:00
|
|
|
nsBoxFrame::AppendFrames(nsIAtom* aListName,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aFrameList)
|
1999-05-09 21:46:24 +00:00
|
|
|
{
|
2005-02-20 22:29:28 +00:00
|
|
|
NS_PRECONDITION(!aListName, "We don't support out-of-flow kids");
|
2005-02-07 01:58:25 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext());
|
1999-05-18 04:06:52 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
// append the new frames
|
|
|
|
mFrames.AppendFrames(this, aFrameList);
|
|
|
|
|
|
|
|
// notify the layout manager
|
|
|
|
if (mLayoutManager)
|
|
|
|
mLayoutManager->ChildrenAppended(this, state, aFrameList);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-02 03:01:30 +00:00
|
|
|
// if we are in debug make sure our children are in debug as well.
|
|
|
|
if (mState & NS_STATE_CURRENTLY_IN_DEBUG)
|
2004-09-28 18:37:50 +00:00
|
|
|
SetDebugOnChildList(state, mFrames.FirstChild(), PR_TRUE);
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2006-01-09 04:01:09 +00:00
|
|
|
if (!(GetStateBits() & NS_FRAME_FIRST_REFLOW)) {
|
|
|
|
MarkDirtyChildren(state);
|
|
|
|
MarkDirty(state);
|
|
|
|
}
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
1999-05-09 21:46:24 +00:00
|
|
|
}
|
|
|
|
|
1999-03-27 01:35:55 +00:00
|
|
|
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
2005-09-07 16:49:21 +00:00
|
|
|
nsBoxFrame::AttributeChanged(PRInt32 aNameSpaceID,
|
2002-02-21 13:39:39 +00:00
|
|
|
nsIAtom* aAttribute,
|
2003-07-11 21:16:12 +00:00
|
|
|
PRInt32 aModType)
|
2002-02-21 13:39:39 +00:00
|
|
|
{
|
2005-09-07 16:49:21 +00:00
|
|
|
nsresult rv = nsContainerFrame::AttributeChanged(aNameSpaceID, aAttribute,
|
|
|
|
aModType);
|
2003-07-11 21:16:12 +00:00
|
|
|
|
|
|
|
// Ignore 'width', 'height', 'screenX', 'screenY' and 'sizemode' on a
|
|
|
|
// <window>.
|
2003-11-19 01:20:56 +00:00
|
|
|
nsIAtom *tag = mContent->Tag();
|
2003-07-11 21:16:12 +00:00
|
|
|
if ((tag == nsXULAtoms::window ||
|
|
|
|
tag == nsXULAtoms::page ||
|
|
|
|
tag == nsXULAtoms::dialog ||
|
|
|
|
tag == nsXULAtoms::wizard) &&
|
|
|
|
(nsXULAtoms::width == aAttribute ||
|
|
|
|
nsXULAtoms::height == aAttribute ||
|
|
|
|
nsXULAtoms::screenX == aAttribute ||
|
|
|
|
nsXULAtoms::screenY == aAttribute ||
|
|
|
|
nsXULAtoms::sizemode == aAttribute)) {
|
|
|
|
return rv;
|
|
|
|
}
|
2002-02-21 13:39:39 +00:00
|
|
|
|
|
|
|
if (aAttribute == nsHTMLAtoms::width ||
|
|
|
|
aAttribute == nsHTMLAtoms::height ||
|
|
|
|
aAttribute == nsHTMLAtoms::align ||
|
|
|
|
aAttribute == nsHTMLAtoms::valign ||
|
|
|
|
aAttribute == nsHTMLAtoms::left ||
|
|
|
|
aAttribute == nsHTMLAtoms::top ||
|
2005-08-22 20:35:47 +00:00
|
|
|
aAttribute == nsXULAtoms::minwidth ||
|
|
|
|
aAttribute == nsXULAtoms::maxwidth ||
|
|
|
|
aAttribute == nsXULAtoms::minheight ||
|
|
|
|
aAttribute == nsXULAtoms::maxheight ||
|
2002-02-21 13:39:39 +00:00
|
|
|
aAttribute == nsXULAtoms::flex ||
|
|
|
|
aAttribute == nsXULAtoms::orient ||
|
|
|
|
aAttribute == nsXULAtoms::pack ||
|
|
|
|
aAttribute == nsXULAtoms::dir ||
|
|
|
|
aAttribute == nsXULAtoms::mousethrough ||
|
|
|
|
aAttribute == nsXULAtoms::equalsize) {
|
|
|
|
|
|
|
|
if (aAttribute == nsHTMLAtoms::align ||
|
|
|
|
aAttribute == nsHTMLAtoms::valign ||
|
|
|
|
aAttribute == nsXULAtoms::orient ||
|
|
|
|
aAttribute == nsXULAtoms::pack ||
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
|
|
|
aAttribute == nsXULAtoms::debug ||
|
|
|
|
#endif
|
|
|
|
aAttribute == nsXULAtoms::dir) {
|
2002-02-21 13:39:39 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
mValign = nsBoxFrame::vAlign_Top;
|
|
|
|
mHalign = nsBoxFrame::hAlign_Left;
|
2002-02-21 13:39:39 +00:00
|
|
|
|
|
|
|
PRBool orient = PR_TRUE;
|
|
|
|
GetInitialOrientation(orient);
|
|
|
|
if (orient)
|
|
|
|
mState |= NS_STATE_IS_HORIZONTAL;
|
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_IS_HORIZONTAL;
|
1999-05-09 21:46:24 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
PRBool normal = PR_TRUE;
|
|
|
|
GetInitialDirection(normal);
|
|
|
|
if (normal)
|
|
|
|
mState |= NS_STATE_IS_DIRECTION_NORMAL;
|
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_IS_DIRECTION_NORMAL;
|
2001-12-03 23:41:13 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
GetInitialVAlignment(mValign);
|
|
|
|
GetInitialHAlignment(mHalign);
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
PRBool equalSize = PR_FALSE;
|
|
|
|
GetInitialEqualSize(equalSize);
|
|
|
|
if (equalSize)
|
|
|
|
mState |= NS_STATE_EQUAL_SIZE;
|
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_EQUAL_SIZE;
|
1) implememted box reflow coelescing.
2) implemented gfx scrollbars for list boxes
3) fixed progess meter to be an animated gif
4) fixed bugs 23521, 24721, 19114, 20546, 24385, 24457, 23156, 20226, 22543
-r hyatt, troy, rod
2000-02-09 22:02:40 +00:00
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2002-02-21 13:39:39 +00:00
|
|
|
PRBool debug = mState & NS_STATE_SET_TO_DEBUG;
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool debugSet = GetInitialDebug(debug);
|
2002-02-21 13:39:39 +00:00
|
|
|
if (debugSet) {
|
|
|
|
mState |= NS_STATE_DEBUG_WAS_SET;
|
2001-12-03 23:41:13 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
if (debug)
|
|
|
|
mState |= NS_STATE_SET_TO_DEBUG;
|
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_SET_TO_DEBUG;
|
|
|
|
} else {
|
|
|
|
mState &= ~NS_STATE_DEBUG_WAS_SET;
|
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-02-14 01:42:09 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
PRBool autostretch = mState & NS_STATE_AUTO_STRETCH;
|
|
|
|
GetInitialAutoStretch(autostretch);
|
|
|
|
if (autostretch)
|
|
|
|
mState |= NS_STATE_AUTO_STRETCH;
|
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_AUTO_STRETCH;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2002-02-21 13:39:39 +00:00
|
|
|
else if (aAttribute == nsHTMLAtoms::left ||
|
|
|
|
aAttribute == nsHTMLAtoms::top) {
|
|
|
|
mState &= ~NS_STATE_STACK_NOT_POSITIONED;
|
|
|
|
}
|
|
|
|
else if (aAttribute == nsXULAtoms::mousethrough) {
|
2002-10-10 06:39:30 +00:00
|
|
|
UpdateMouseThrough();
|
2002-02-21 13:39:39 +00:00
|
|
|
}
|
2004-09-17 18:36:30 +00:00
|
|
|
|
2004-12-31 01:13:27 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext());
|
2004-09-17 18:36:30 +00:00
|
|
|
MarkDirty(state);
|
2002-02-21 13:39:39 +00:00
|
|
|
}
|
|
|
|
else if (aAttribute == nsXULAtoms::ordinal) {
|
2004-12-31 01:13:27 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext()->PresShell());
|
2006-04-03 03:55:11 +00:00
|
|
|
|
|
|
|
nsIFrame* frameToMove = this;
|
|
|
|
if (GetStateBits() & NS_FRAME_OUT_OF_FLOW) {
|
|
|
|
GetPresContext()->PresShell()->GetPlaceholderFrameFor(this,
|
|
|
|
&frameToMove);
|
|
|
|
NS_ASSERTION(frameToMove, "Out of flow without placeholder?");
|
|
|
|
}
|
2002-02-21 13:39:39 +00:00
|
|
|
|
|
|
|
nsIBox* parent;
|
2006-04-03 03:55:11 +00:00
|
|
|
frameToMove->GetParentBox(&parent);
|
2006-02-21 00:40:54 +00:00
|
|
|
// If our parent is not a box, there's not much we can do... but in that
|
|
|
|
// case our ordinal doesn't matter anyway, so that's ok.
|
|
|
|
if (parent) {
|
2006-04-03 03:55:11 +00:00
|
|
|
parent->RelayoutChildAtOrdinal(state, frameToMove);
|
2006-02-21 00:40:54 +00:00
|
|
|
parent->MarkDirty(state);
|
|
|
|
}
|
2002-02-21 13:39:39 +00:00
|
|
|
}
|
|
|
|
// If the accesskey changed, register for the new value
|
|
|
|
// The old value has been unregistered in nsXULElement::SetAttr
|
|
|
|
else if (aAttribute == nsXULAtoms::accesskey) {
|
2006-04-10 00:16:29 +00:00
|
|
|
RegUnregAccessKey(PR_TRUE);
|
2002-02-21 13:39:39 +00:00
|
|
|
}
|
2001-12-03 23:41:13 +00:00
|
|
|
|
1999-03-27 01:35:55 +00:00
|
|
|
return rv;
|
|
|
|
}
|
|
|
|
|
1999-05-09 21:46:24 +00:00
|
|
|
|
2000-05-15 04:12:31 +00:00
|
|
|
#ifdef DEBUG_COELESCED
|
2000-04-25 07:10:48 +00:00
|
|
|
static PRInt32 StyleCoelesced = 0;
|
|
|
|
#endif
|
|
|
|
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::HasStyleChange()
|
|
|
|
{
|
|
|
|
return mState & NS_STATE_STYLE_CHANGE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsBoxFrame::SetStyleChangeFlag(PRBool aDirty)
|
|
|
|
{
|
2000-05-15 04:12:31 +00:00
|
|
|
nsBox::SetStyleChangeFlag(aDirty);
|
|
|
|
|
2000-04-25 07:10:48 +00:00
|
|
|
if (aDirty)
|
2000-05-15 04:12:31 +00:00
|
|
|
mState |= (NS_STATE_STYLE_CHANGE);
|
2000-04-25 07:10:48 +00:00
|
|
|
else
|
|
|
|
mState &= ~NS_STATE_STYLE_CHANGE;
|
|
|
|
}
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
void
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::GetDebugPref(nsPresContext* aPresContext)
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2004-04-29 23:34:19 +00:00
|
|
|
gDebug = nsContentUtils::GetBoolPref("xul.debug.box");
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2000-09-01 00:59:09 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
class nsDisplayXULDebug : public nsDisplayItem {
|
|
|
|
public:
|
2006-03-14 20:43:18 +00:00
|
|
|
nsDisplayXULDebug(nsIFrame* aFrame) : nsDisplayItem(aFrame) {
|
2006-01-29 18:48:58 +00:00
|
|
|
MOZ_COUNT_CTOR(nsDisplayXULDebug);
|
|
|
|
}
|
|
|
|
#ifdef NS_BUILD_REFCNT_LOGGING
|
|
|
|
virtual ~nsDisplayXULDebug() {
|
|
|
|
MOZ_COUNT_DTOR(nsDisplayXULDebug);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
virtual nsIFrame* HitTest(nsDisplayListBuilder* aBuilder, nsPoint aPt) {
|
2006-03-14 20:43:18 +00:00
|
|
|
NS_STATIC_CAST(nsBoxFrame*, mFrame)->
|
|
|
|
DisplayDebugInfoFor(this, aPt - aBuilder->ToReferenceFrame(mFrame));
|
2006-01-26 02:29:17 +00:00
|
|
|
return PR_TRUE;
|
2000-09-01 00:59:09 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
virtual void Paint(nsDisplayListBuilder* aBuilder, nsIRenderingContext* aCtx,
|
|
|
|
const nsRect& aDirtyRect);
|
|
|
|
NS_DISPLAY_DECL_NAME("ComboboxFocus")
|
|
|
|
};
|
2001-04-25 19:52:49 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
void
|
|
|
|
nsDisplayXULDebug::Paint(nsDisplayListBuilder* aBuilder,
|
|
|
|
nsIRenderingContext* aCtx, const nsRect& aDirtyRect)
|
|
|
|
{
|
2006-03-14 20:43:18 +00:00
|
|
|
NS_STATIC_CAST(nsBoxFrame*, mFrame)->
|
|
|
|
PaintXULDebugOverlay(*aCtx, aBuilder->ToReferenceFrame(mFrame));
|
2006-01-26 02:29:17 +00:00
|
|
|
}
|
2000-09-01 00:59:09 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
static void
|
|
|
|
PaintXULDebugBackground(nsIFrame* aFrame, nsIRenderingContext* aCtx,
|
|
|
|
const nsRect& aDirtyRect, nsPoint aPt)
|
|
|
|
{
|
|
|
|
NS_STATIC_CAST(nsBoxFrame*, aFrame)->PaintXULDebugBackground(*aCtx, aPt);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsBoxFrame::BuildDisplayList(nsDisplayListBuilder* aBuilder,
|
|
|
|
const nsRect& aDirtyRect,
|
|
|
|
const nsDisplayListSet& aLists)
|
|
|
|
{
|
|
|
|
nsresult rv = DisplayBorderBackgroundOutline(aBuilder, aLists);
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
|
|
|
|
|
|
|
#ifdef DEBUG_LAYOUT
|
|
|
|
// REVIEW: From GetFrameForPoint
|
|
|
|
if (mState & NS_STATE_CURRENTLY_IN_DEBUG) {
|
|
|
|
rv = aLists.BorderBackground()->AppendNewToTop(new (aBuilder)
|
|
|
|
nsDisplayGeneric(this, PaintXULDebugBackground, "XULDebugBackground"));
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
|
|
|
rv = aLists.Outlines()->AppendNewToTop(new (aBuilder)
|
|
|
|
nsDisplayXULDebug(this));
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
2001-04-25 19:52:49 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
#endif
|
2001-04-25 19:52:49 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
rv = BuildDisplayListForChildren(aBuilder, aDirtyRect, aLists);
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
2000-09-01 00:59:09 +00:00
|
|
|
|
|
|
|
// see if we have to draw a selection frame around this container
|
2006-01-26 02:29:17 +00:00
|
|
|
return DisplaySelectionOverlay(aBuilder, aLists);
|
2000-09-01 00:59:09 +00:00
|
|
|
}
|
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::BuildDisplayListForChildren(nsDisplayListBuilder* aBuilder,
|
|
|
|
const nsRect& aDirtyRect,
|
|
|
|
const nsDisplayListSet& aLists)
|
|
|
|
{
|
|
|
|
nsIFrame* kid = mFrames.FirstChild();
|
|
|
|
// Put each child's background onto the BlockBorderBackgrounds list
|
|
|
|
// to emulate the existing two-layer XUL painting scheme.
|
|
|
|
nsDisplayListSet set(aLists, aLists.BlockBorderBackgrounds());
|
|
|
|
// The children should be in the right order
|
|
|
|
while (kid) {
|
|
|
|
nsresult rv = BuildDisplayListForChild(aBuilder, kid, aDirtyRect, set);
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
|
|
|
kid = kid->GetNextSibling();
|
2000-09-01 00:59:09 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
return NS_OK;
|
1999-09-10 00:57:01 +00:00
|
|
|
}
|
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
// REVIEW: PaintChildren did a few things none of which are a big deal
|
|
|
|
// anymore:
|
|
|
|
// * Paint some debugging rects for this frame.
|
|
|
|
// This is done by nsDisplayXULDebugBackground, which goes in the
|
|
|
|
// BorderBackground() layer so it isn't clipped by OVERFLOW_CLIP.
|
|
|
|
// * Apply OVERFLOW_CLIP to the children.
|
|
|
|
// This is now in nsFrame::BuildDisplayListForStackingContext/Child.
|
|
|
|
// * Actually paint the children.
|
|
|
|
// Moved to BuildDisplayList.
|
|
|
|
// * Paint per-kid debug information.
|
|
|
|
// This is done by nsDisplayXULDebug, which is in the Outlines()
|
|
|
|
// layer so it goes on top. This means it is not clipped by OVERFLOW_CLIP,
|
|
|
|
// whereas it did used to respect OVERFLOW_CLIP, but too bad.
|
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-02-25 04:18:34 +00:00
|
|
|
void
|
2006-01-26 02:29:17 +00:00
|
|
|
nsBoxFrame::PaintXULDebugBackground(nsIRenderingContext& aRenderingContext,
|
|
|
|
nsPoint aPt)
|
2000-02-25 04:18:34 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
nsMargin border;
|
|
|
|
nsRect inner;
|
|
|
|
|
2000-04-25 07:10:48 +00:00
|
|
|
GetBorder(border);
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
nsMargin debugBorder;
|
|
|
|
nsMargin debugMargin;
|
|
|
|
nsMargin debugPadding;
|
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
PRBool isHorizontal = IsHorizontal();
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetDebugBorder(debugBorder);
|
|
|
|
PixelMarginToTwips(GetPresContext(), debugBorder);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetDebugMargin(debugMargin);
|
|
|
|
PixelMarginToTwips(GetPresContext(), debugMargin);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetDebugPadding(debugPadding);
|
|
|
|
PixelMarginToTwips(GetPresContext(), debugPadding);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetContentRect(inner);
|
|
|
|
inner += aPt;
|
|
|
|
inner.Deflate(debugMargin);
|
|
|
|
inner.Deflate(border);
|
|
|
|
//nsRect borderRect(inner);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nscolor color;
|
|
|
|
if (isHorizontal) {
|
|
|
|
color = NS_RGB(0,0,255);
|
|
|
|
} else {
|
|
|
|
color = NS_RGB(255,0,0);
|
|
|
|
}
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
aRenderingContext.SetColor(color);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
//left
|
|
|
|
nsRect r(inner);
|
|
|
|
r.width = debugBorder.left;
|
|
|
|
aRenderingContext.FillRect(r);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
// top
|
|
|
|
r = inner;
|
|
|
|
r.height = debugBorder.top;
|
|
|
|
aRenderingContext.FillRect(r);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
//right
|
|
|
|
r = inner;
|
|
|
|
r.x = r.x + r.width - debugBorder.right;
|
|
|
|
r.width = debugBorder.right;
|
|
|
|
aRenderingContext.FillRect(r);
|
2000-05-15 04:12:31 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
//bottom
|
|
|
|
r = inner;
|
|
|
|
r.y = r.y + r.height - debugBorder.bottom;
|
|
|
|
r.height = debugBorder.bottom;
|
|
|
|
aRenderingContext.FillRect(r);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
|
|
|
|
// if we have dirty children or we are dirty
|
|
|
|
// place a green border around us.
|
|
|
|
PRBool dirty = PR_FALSE;
|
|
|
|
IsDirty(dirty);
|
|
|
|
PRBool dirtyc = PR_FALSE;
|
|
|
|
HasDirtyChildren(dirtyc);
|
2000-02-25 04:18:34 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
if (dirty || dirtyc) {
|
|
|
|
IsDirty(dirty);
|
|
|
|
HasDirtyChildren(dirty);
|
2000-02-25 04:18:34 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nsRect dirtyr(inner);
|
|
|
|
aRenderingContext.SetColor(NS_RGB(0,255,0));
|
|
|
|
aRenderingContext.DrawRect(dirtyr);
|
|
|
|
aRenderingContext.SetColor(color);
|
2000-02-25 04:18:34 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
}
|
2000-02-25 04:18:34 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::PaintXULDebugOverlay(nsIRenderingContext& aRenderingContext,
|
|
|
|
nsPoint aPt)
|
|
|
|
nsMargin border;
|
|
|
|
GetBorder(border);
|
2000-02-25 04:18:34 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nsMargin debugMargin;
|
|
|
|
GetDebugMargin(debugMargin);
|
|
|
|
PixelMarginToTwips(GetPresContext(), debugMargin);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nsRect inner;
|
|
|
|
GetContentRect(inner);
|
|
|
|
inner += aPt;
|
|
|
|
inner.Deflate(debugMargin);
|
|
|
|
inner.Deflate(border);
|
2000-02-25 04:18:34 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nscoord onePixel = GetPresContext()->IntScaledPixelsToTwips(1);
|
|
|
|
GetContentRect(r);
|
1999-09-14 22:17:19 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetChildBox(&kid);
|
|
|
|
while (nsnull != kid) {
|
|
|
|
PRBool isHorizontal = IsHorizontal();
|
1999-08-27 06:06:39 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nscoord x, y, borderSize, spacerSize;
|
|
|
|
|
|
|
|
nsRect cr(kid->mRect);
|
|
|
|
nsMargin margin;
|
|
|
|
kid->GetMargin(margin);
|
|
|
|
cr.Inflate(margin);
|
|
|
|
|
|
|
|
if (isHorizontal)
|
|
|
|
{
|
|
|
|
cr.y = inner.y;
|
|
|
|
x = cr.x;
|
|
|
|
y = cr.y + onePixel;
|
|
|
|
spacerSize = debugBorder.top - onePixel*4;
|
|
|
|
} else {
|
|
|
|
cr.x = inner.x;
|
|
|
|
x = cr.y;
|
|
|
|
y = cr.x + onePixel;
|
|
|
|
spacerSize = debugBorder.left - onePixel*4;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
1999-09-10 00:57:01 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext());
|
|
|
|
nscoord flex = 0;
|
|
|
|
kid->GetFlex(state, flex);
|
1999-09-10 00:57:01 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
PRBool isCollapsed = PR_FALSE;
|
|
|
|
kid->IsCollapsed(state, isCollapsed);
|
1999-08-27 06:06:39 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
if (!isCollapsed) {
|
|
|
|
aRenderingContext.SetColor(NS_RGB(255,255,255));
|
1999-08-27 06:06:39 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
if (isHorizontal)
|
|
|
|
borderSize = cr.width;
|
|
|
|
else
|
|
|
|
borderSize = cr.height;
|
|
|
|
|
|
|
|
DrawSpacer(GetPresContext(), aRenderingContext, isHorizontal, flex, x, y, borderSize, spacerSize);
|
2000-03-02 03:01:30 +00:00
|
|
|
}
|
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
kid->GetNextBox(&kid);
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
1999-07-23 00:11:21 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
#endif
|
1999-07-23 00:11:21 +00:00
|
|
|
|
1999-05-09 21:46:24 +00:00
|
|
|
NS_IMETHODIMP_(nsrefcnt)
|
|
|
|
nsBoxFrame::AddRef(void)
|
1999-03-27 01:35:55 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
2000-03-02 03:01:30 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP_(nsrefcnt)
|
|
|
|
nsBoxFrame::Release(void)
|
1999-05-09 21:46:24 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
return NS_OK;
|
1999-05-09 21:46:24 +00:00
|
|
|
}
|
|
|
|
|
2002-09-09 21:32:33 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-05-15 04:12:31 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::GetBoxName(nsAutoString& aName)
|
|
|
|
{
|
|
|
|
GetFrameName(aName);
|
|
|
|
}
|
2002-09-09 21:32:33 +00:00
|
|
|
#endif
|
2000-05-15 04:12:31 +00:00
|
|
|
|
2001-09-15 00:45:54 +00:00
|
|
|
#ifdef DEBUG
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
2001-11-14 01:33:42 +00:00
|
|
|
nsBoxFrame::GetFrameName(nsAString& aResult) const
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2001-11-14 01:33:42 +00:00
|
|
|
return MakeFrameName(NS_LITERAL_STRING("Box"), aResult);
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2001-09-15 00:45:54 +00:00
|
|
|
#endif
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2003-10-31 20:19:18 +00:00
|
|
|
nsIAtom*
|
|
|
|
nsBoxFrame::GetType() const
|
2001-12-07 14:51:12 +00:00
|
|
|
{
|
2003-10-31 20:19:18 +00:00
|
|
|
return nsLayoutAtoms::boxFrame;
|
2001-12-07 14:51:12 +00:00
|
|
|
}
|
|
|
|
|
2004-06-19 09:07:47 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
2000-03-31 07:02:06 +00:00
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetDebug(PRBool& aDebug)
|
|
|
|
{
|
|
|
|
aDebug = (mState & NS_STATE_CURRENTLY_IN_DEBUG);
|
|
|
|
return NS_OK;
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
1999-09-10 00:57:01 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
// REVIEW: nsBoxFrame::GetFrameForPoint is a problem because of 'mousethrough'
|
|
|
|
// attribute support. Here's how it works:
|
|
|
|
// * For each child frame F, we determine the target frame T(F) by recursively
|
|
|
|
// invoking GetFrameForPoint on the child
|
|
|
|
// * Let F' be the last child frame such that T(F') doesn't have mousethrough.
|
|
|
|
// If F' exists, return T(F')
|
|
|
|
// * Otherwise let F'' be the first child frame such that T(F'') is non-null.
|
|
|
|
// If F'' exists, return T(F'')
|
|
|
|
// * Otherwise return this frame, if this frame contains the point
|
|
|
|
// * Otherwise return null
|
|
|
|
// It's not clear how this should work for more complex z-ordering situations.
|
|
|
|
// The basic principle seems to be that if a frame F has a descendant
|
|
|
|
// 'mousethrough' frame that includes the target position, then F
|
|
|
|
// will not receive events (unless it overrides GetFrameForPoint).
|
|
|
|
// A 'mousethrough' frame will only receive an event if, after applying that rule,
|
|
|
|
// all eligible frames are 'mousethrough'; the bottom-most inner-most 'mousethrough'
|
|
|
|
// frame is then chosen (the first eligible frame reached in a
|
|
|
|
// traversal of the frame tree --- pre/post is irrelevant since ancestors
|
|
|
|
// of the mousethrough frames can't be eligible).
|
|
|
|
// IMHO this is very bogus and adds a great deal of complexity for something
|
|
|
|
// that is very rarely used. So I'm redefining 'mousethrough' to the following:
|
|
|
|
// a frame with mousethrough is transparent to mouse events. This is compatible
|
|
|
|
// with the way 'mousethrough' is used in Seamonkey's navigator.xul and
|
|
|
|
// Firefox's browser.xul. The only other place it's used is in the 'expander'
|
|
|
|
// XBL binding, which in our tree is only used by Thunderbird SMIME Advanced
|
|
|
|
// Preferences, and I can't figure out what that does, so I'll have to test it.
|
|
|
|
// If it's broken I'll probably just change the binding to use it more sensibly.
|
|
|
|
// This new behaviour is implemented in nsDisplayList::HitTest.
|
|
|
|
// REVIEW: This debug-box stuff is annoying. I'm just going to put debug boxes
|
|
|
|
// in the outline layer and avoid GetDebugBoxAt.
|
2000-04-18 00:17:00 +00:00
|
|
|
nsIBox*
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetBoxForFrame(nsIFrame* aFrame, PRBool& aIsAdaptor)
|
2000-04-18 00:17:00 +00:00
|
|
|
{
|
2004-09-28 18:37:50 +00:00
|
|
|
if (aFrame && !aFrame->IsBoxFrame())
|
2000-04-18 00:17:00 +00:00
|
|
|
aIsAdaptor = PR_TRUE;
|
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
return aFrame;
|
2000-04-18 00:17:00 +00:00
|
|
|
}
|
2000-04-12 02:59:26 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
// REVIEW: GetCursor had debug-only event dumping code. I have replaced it
|
|
|
|
// with instrumentation in nsDisplayXULDebug.
|
1999-10-12 00:16:06 +00:00
|
|
|
nsresult
|
2000-03-31 07:02:06 +00:00
|
|
|
nsBoxFrame::GetContentOf(nsIContent** aContent)
|
1999-10-12 00:16:06 +00:00
|
|
|
{
|
|
|
|
// If we don't have a content node find a parent that does.
|
2004-09-28 18:37:50 +00:00
|
|
|
nsIFrame *frame = this;
|
2003-07-09 03:30:40 +00:00
|
|
|
while (frame) {
|
|
|
|
*aContent = frame->GetContent();
|
|
|
|
if (*aContent) {
|
|
|
|
NS_ADDREF(*aContent);
|
|
|
|
return NS_OK;
|
|
|
|
}
|
1999-10-12 00:16:06 +00:00
|
|
|
|
2003-07-09 03:30:40 +00:00
|
|
|
frame = frame->GetParent();
|
1999-10-12 00:16:06 +00:00
|
|
|
}
|
|
|
|
|
2003-07-09 03:30:40 +00:00
|
|
|
*aContent = nsnull;
|
1999-10-12 00:16:06 +00:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
2006-02-13 15:49:56 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
1999-11-18 21:05:43 +00:00
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::DrawLine(nsIRenderingContext& aRenderingContext, PRBool aHorizontal, nscoord x1, nscoord y1, nscoord x2, nscoord y2)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
if (aHorizontal)
|
|
|
|
aRenderingContext.DrawLine(x1,y1,x2,y2);
|
|
|
|
else
|
|
|
|
aRenderingContext.DrawLine(y1,x1,y2,x2);
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::FillRect(nsIRenderingContext& aRenderingContext, PRBool aHorizontal, nscoord x, nscoord y, nscoord width, nscoord height)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
if (aHorizontal)
|
|
|
|
aRenderingContext.FillRect(x,y,width,height);
|
|
|
|
else
|
|
|
|
aRenderingContext.FillRect(y,x,height,width);
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
void
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::DrawSpacer(nsPresContext* aPresContext, nsIRenderingContext& aRenderingContext, PRBool aHorizontal, PRInt32 flex, nscoord x, nscoord y, nscoord size, nscoord spacerSize)
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2004-07-29 19:41:39 +00:00
|
|
|
nscoord onePixel = aPresContext->IntScaledPixelsToTwips(1);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// if we do draw the coils
|
|
|
|
int distance = 0;
|
|
|
|
int center = 0;
|
|
|
|
int offset = 0;
|
|
|
|
int coilSize = COIL_SIZE*onePixel;
|
2001-09-18 21:47:32 +00:00
|
|
|
int halfSpacer = spacerSize/2;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
distance = size;
|
2001-09-18 21:47:32 +00:00
|
|
|
center = y + halfSpacer;
|
2000-03-31 07:02:06 +00:00
|
|
|
offset = x;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
int coils = distance/coilSize;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
int halfCoilSize = coilSize/2;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
if (flex == 0) {
|
2001-09-18 21:47:32 +00:00
|
|
|
DrawLine(aRenderingContext, aHorizontal, x,y + spacerSize/2, x + size, y + spacerSize/2);
|
2000-03-31 07:02:06 +00:00
|
|
|
} else {
|
|
|
|
for (int i=0; i < coils; i++)
|
|
|
|
{
|
2001-09-18 21:47:32 +00:00
|
|
|
DrawLine(aRenderingContext, aHorizontal, offset, center+halfSpacer, offset+halfCoilSize, center-halfSpacer);
|
|
|
|
DrawLine(aRenderingContext, aHorizontal, offset+halfCoilSize, center-halfSpacer, offset+coilSize, center+halfSpacer);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
offset += coilSize;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2001-09-18 21:47:32 +00:00
|
|
|
FillRect(aRenderingContext, aHorizontal, x + size - spacerSize/2, y, spacerSize/2, spacerSize);
|
|
|
|
FillRect(aRenderingContext, aHorizontal, x, y, spacerSize/2, spacerSize);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2001-09-18 21:47:32 +00:00
|
|
|
//DrawKnob(aPresContext, aRenderingContext, x + size - spacerSize, y, spacerSize);
|
1999-12-02 01:07:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetDebugBorder(nsMargin& aInset)
|
1999-12-02 01:07:27 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
aInset.SizeTo(2,2,2,2);
|
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
if (IsHorizontal())
|
2000-03-31 07:02:06 +00:00
|
|
|
aInset.top = 10;
|
|
|
|
else
|
|
|
|
aInset.left = 10;
|
1999-12-02 01:07:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetDebugMargin(nsMargin& aInset)
|
1999-12-02 01:07:27 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
aInset.SizeTo(2,2,2,2);
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetDebugPadding(nsMargin& aPadding)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
aPadding.SizeTo(2,2,2,2);
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetInset(nsMargin& margin)
|
|
|
|
{
|
|
|
|
margin.SizeTo(0,0,0,0);
|
|
|
|
|
|
|
|
if (mState & NS_STATE_CURRENTLY_IN_DEBUG) {
|
2005-12-15 03:30:17 +00:00
|
|
|
nsPresContext* presContext = GetPresContext();
|
|
|
|
nsMargin debugMargin(0,0,0,0);
|
|
|
|
nsMargin debugBorder(0,0,0,0);
|
|
|
|
nsMargin debugPadding(0,0,0,0);
|
|
|
|
GetDebugBorder(debugBorder);
|
|
|
|
PixelMarginToTwips(presContext, debugBorder);
|
|
|
|
GetDebugMargin(debugMargin);
|
|
|
|
PixelMarginToTwips(presContext, debugMargin);
|
|
|
|
GetDebugMargin(debugPadding);
|
|
|
|
PixelMarginToTwips(presContext, debugPadding);
|
|
|
|
margin += debugBorder;
|
|
|
|
margin += debugMargin;
|
|
|
|
margin += debugPadding;
|
2004-09-28 18:37:50 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
2004-06-19 09:07:47 +00:00
|
|
|
#endif
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
void
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::PixelMarginToTwips(nsPresContext* aPresContext, nsMargin& aMarginPixels)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
2004-07-29 19:41:39 +00:00
|
|
|
nscoord onePixel = aPresContext->IntScaledPixelsToTwips(1);
|
2000-03-31 07:02:06 +00:00
|
|
|
aMarginPixels.left *= onePixel;
|
|
|
|
aMarginPixels.right *= onePixel;
|
|
|
|
aMarginPixels.top *= onePixel;
|
|
|
|
aMarginPixels.bottom *= onePixel;
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2002-09-09 21:32:33 +00:00
|
|
|
#ifdef DEBUG_LAYOUT
|
1999-11-18 21:05:43 +00:00
|
|
|
void
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::GetValue(nsPresContext* aPresContext, const nsSize& a, const nsSize& b, char* ch)
|
1999-11-18 21:05:43 +00:00
|
|
|
{
|
2004-07-29 19:41:39 +00:00
|
|
|
float p2t = aPresContext->ScaledPixelsToTwips();
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
char width[100];
|
|
|
|
char height[100];
|
|
|
|
|
|
|
|
if (a.width == NS_INTRINSICSIZE)
|
|
|
|
sprintf(width,"%s","INF");
|
2006-01-26 02:29:17 +00:00
|
|
|
else
|
2000-03-31 07:02:06 +00:00
|
|
|
sprintf(width,"%d", nscoord(a.width/*/p2t*/));
|
|
|
|
|
|
|
|
if (a.height == NS_INTRINSICSIZE)
|
|
|
|
sprintf(height,"%s","INF");
|
1999-12-02 01:07:27 +00:00
|
|
|
else
|
2000-03-31 07:02:06 +00:00
|
|
|
sprintf(height,"%d", nscoord(a.height/*/p2t*/));
|
1999-12-02 01:07:27 +00:00
|
|
|
|
1999-11-18 21:05:43 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
sprintf(ch, "(%s%s, %s%s)", width, (b.width != NS_INTRINSICSIZE ? "[SET]" : ""),
|
|
|
|
height, (b.height != NS_INTRINSICSIZE ? "[SET]" : ""));
|
1999-12-02 01:07:27 +00:00
|
|
|
|
1999-11-18 21:05:43 +00:00
|
|
|
}
|
|
|
|
|
1999-12-02 01:07:27 +00:00
|
|
|
void
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::GetValue(nsPresContext* aPresContext, PRInt32 a, PRInt32 b, char* ch)
|
1999-12-02 01:07:27 +00:00
|
|
|
{
|
2000-03-31 07:02:06 +00:00
|
|
|
if (a == NS_INTRINSICSIZE)
|
|
|
|
sprintf(ch, "%d[SET]", b);
|
|
|
|
else
|
|
|
|
sprintf(ch, "%d", a);
|
1999-12-02 01:07:27 +00:00
|
|
|
}
|
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult
|
2006-01-26 02:29:17 +00:00
|
|
|
nsBoxFrame::DisplayDebugInfoFor(nsIBox* aBox,
|
|
|
|
nsPoint& aPoint)
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2006-01-26 02:29:17 +00:00
|
|
|
nsBoxLayoutState state(GetPresContext());
|
2000-03-31 07:02:06 +00:00
|
|
|
|
|
|
|
nscoord x = aPoint.x;
|
|
|
|
nscoord y = aPoint.y;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
// get the area inside our border but not our debug margins.
|
|
|
|
nsRect insideBorder;
|
|
|
|
aBox->GetContentRect(insideBorder);
|
|
|
|
nsMargin border(0,0,0,0);
|
|
|
|
aBox->GetBorderAndPadding(border);
|
|
|
|
insideBorder.Deflate(border);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool isHorizontal = IsHorizontal();
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
if (!insideBorder.Contains(nsPoint(x,y)))
|
|
|
|
return NS_ERROR_FAILURE;
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
//printf("%%%%%% inside box %%%%%%%\n");
|
2000-02-14 01:42:09 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
int count = 0;
|
|
|
|
nsIBox* child = nsnull;
|
|
|
|
aBox->GetChildBox(&child);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
nsMargin m;
|
|
|
|
nsMargin m2;
|
|
|
|
GetDebugBorder(m);
|
|
|
|
PixelMarginToTwips(aPresContext, m);
|
1999-12-02 01:07:27 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
GetDebugMargin(m2);
|
|
|
|
PixelMarginToTwips(aPresContext, m2);
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
m += m2;
|
2000-03-31 07:02:06 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
if ((isHorizontal && y < insideBorder.y + m.top) ||
|
|
|
|
(!isHorizontal && x < insideBorder.x + m.left)) {
|
|
|
|
//printf("**** inside debug border *******\n");
|
|
|
|
while (child)
|
|
|
|
{
|
|
|
|
const nsRect& r = child->mRect;
|
|
|
|
|
|
|
|
// if we are not in the child. But in the spacer above the child.
|
|
|
|
if ((isHorizontal && x >= r.x && x < r.x + r.width) ||
|
|
|
|
(!isHorizontal && y >= r.y && y < r.y + r.height)) {
|
|
|
|
aCursor = NS_STYLE_CURSOR_POINTER;
|
|
|
|
// found it but we already showed it.
|
|
|
|
if (mDebugChild == child)
|
|
|
|
return NS_OK;
|
|
|
|
|
|
|
|
if (aBox->GetContent()) {
|
|
|
|
printf("---------------\n");
|
|
|
|
DumpBox(stdout);
|
|
|
|
printf("\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
if (child->GetContent()) {
|
|
|
|
printf("child #%d: ", count);
|
|
|
|
child->DumpBox(stdout);
|
|
|
|
printf("\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
mDebugChild = child;
|
|
|
|
|
|
|
|
nsSize prefSizeCSS(NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
nsSize minSizeCSS (NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
nsSize maxSizeCSS (NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
nscoord flexCSS = NS_INTRINSICSIZE;
|
|
|
|
|
|
|
|
nsSize prefSize(0, 0);
|
|
|
|
nsSize minSize (0, 0);
|
|
|
|
nsSize maxSize (NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
nscoord flexSize = 0;
|
|
|
|
nscoord ascentSize = 0;
|
|
|
|
|
|
|
|
|
|
|
|
nsIBox::AddCSSPrefSize(state, child, prefSizeCSS);
|
|
|
|
nsIBox::AddCSSMinSize (state, child, minSizeCSS);
|
|
|
|
nsIBox::AddCSSMaxSize (state, child, maxSizeCSS);
|
|
|
|
nsIBox::AddCSSFlex (state, child, flexCSS);
|
|
|
|
|
|
|
|
child->GetPrefSize(state, prefSize);
|
|
|
|
child->GetMinSize(state, minSize);
|
|
|
|
child->GetMaxSize(state, maxSize);
|
|
|
|
child->GetFlex(state, flexSize);
|
|
|
|
child->GetAscent(state, ascentSize);
|
|
|
|
|
|
|
|
char min[100];
|
|
|
|
char pref[100];
|
|
|
|
char max[100];
|
|
|
|
char calc[100];
|
|
|
|
char flex[100];
|
|
|
|
char ascent[100];
|
|
|
|
|
|
|
|
nsSize actualSize;
|
|
|
|
GetFrameSizeWithMargin(child, actualSize);
|
|
|
|
nsSize actualSizeCSS (NS_INTRINSICSIZE, NS_INTRINSICSIZE);
|
|
|
|
|
|
|
|
GetValue(aPresContext, minSize, minSizeCSS, min);
|
|
|
|
GetValue(aPresContext, prefSize, prefSizeCSS, pref);
|
|
|
|
GetValue(aPresContext, maxSize, maxSizeCSS, max);
|
|
|
|
GetValue(aPresContext, actualSize, actualSizeCSS, calc);
|
|
|
|
GetValue(aPresContext, flexSize, flexCSS, flex);
|
|
|
|
GetValue(aPresContext, ascentSize, NS_INTRINSICSIZE, ascent);
|
|
|
|
|
|
|
|
|
|
|
|
printf("min%s, pref%s, max%s, actual%s, flex=%s, ascent=%s\n\n",
|
|
|
|
min,
|
|
|
|
pref,
|
|
|
|
max,
|
|
|
|
calc,
|
|
|
|
flex,
|
|
|
|
ascent
|
|
|
|
);
|
|
|
|
|
|
|
|
return NS_OK;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
|
|
|
|
child->GetNextBox(&child);
|
|
|
|
count++;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
} else {
|
|
|
|
}
|
1999-09-10 00:57:01 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
mDebugChild = nsnull;
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2006-01-26 02:29:17 +00:00
|
|
|
return NS_OK;
|
2000-03-31 07:02:06 +00:00
|
|
|
}
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
nsBoxFrame::SetDebugOnChildList(nsBoxLayoutState& aState, nsIBox* aChild, PRBool aDebug)
|
|
|
|
{
|
|
|
|
nsIBox* child = nsnull;
|
|
|
|
GetChildBox(&child);
|
|
|
|
while (child)
|
|
|
|
{
|
|
|
|
child->SetDebug(aState, aDebug);
|
|
|
|
child->GetNextBox(&child);
|
|
|
|
}
|
|
|
|
}
|
2002-09-09 21:32:33 +00:00
|
|
|
#endif
|
2000-03-02 03:01:30 +00:00
|
|
|
|
2000-03-31 07:02:06 +00:00
|
|
|
nsresult
|
2002-10-10 06:39:30 +00:00
|
|
|
nsBoxFrame::GetFrameSizeWithMargin(nsIBox* aBox, nsSize& aSize)
|
2000-03-31 07:02:06 +00:00
|
|
|
{
|
2004-09-28 18:37:50 +00:00
|
|
|
nsRect rect(aBox->GetRect());
|
2000-03-31 07:02:06 +00:00
|
|
|
nsMargin margin(0,0,0,0);
|
|
|
|
aBox->GetMargin(margin);
|
|
|
|
rect.Inflate(margin);
|
|
|
|
aSize.width = rect.width;
|
|
|
|
aSize.height = rect.height;
|
|
|
|
return NS_OK;
|
2000-04-02 07:17:25 +00:00
|
|
|
}
|
2000-06-28 22:19:54 +00:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Boxed don't support fixed positionioning of their children.
|
|
|
|
*/
|
|
|
|
nsresult
|
2004-07-31 23:15:21 +00:00
|
|
|
nsBoxFrame::CreateViewForFrame(nsPresContext* aPresContext,
|
2002-10-10 06:39:30 +00:00
|
|
|
nsIFrame* aFrame,
|
2003-02-22 00:32:13 +00:00
|
|
|
nsStyleContext* aStyleContext,
|
2002-10-10 06:39:30 +00:00
|
|
|
PRBool aForce)
|
2000-06-28 22:19:54 +00:00
|
|
|
{
|
|
|
|
// If we don't yet have a view, see if we need a view
|
2003-06-19 23:44:01 +00:00
|
|
|
if (!aFrame->HasView()) {
|
2000-06-28 22:19:54 +00:00
|
|
|
PRInt32 zIndex = 0;
|
|
|
|
PRBool autoZIndex = PR_FALSE;
|
|
|
|
PRBool fixedBackgroundAttachment = PR_FALSE;
|
|
|
|
|
2002-01-14 15:00:30 +00:00
|
|
|
const nsStyleBackground* bg;
|
|
|
|
PRBool isCanvas;
|
|
|
|
PRBool hasBG =
|
|
|
|
nsCSSRendering::FindBackground(aPresContext, aFrame, &bg, &isCanvas);
|
2003-11-01 22:34:59 +00:00
|
|
|
const nsStyleDisplay* disp = aStyleContext->GetStyleDisplay();
|
2000-06-28 22:19:54 +00:00
|
|
|
|
2003-11-01 22:34:59 +00:00
|
|
|
if (disp->mOpacity != 1.0f) {
|
2000-06-28 22:19:54 +00:00
|
|
|
NS_FRAME_LOG(NS_FRAME_TRACE_CALLS,
|
2001-05-31 22:19:43 +00:00
|
|
|
("nsBoxFrame::CreateViewForFrame: frame=%p opacity=%g",
|
2003-11-01 22:34:59 +00:00
|
|
|
aFrame, disp->mOpacity));
|
2000-06-28 22:19:54 +00:00
|
|
|
aForce = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
// See if the frame has a fixed background attachment
|
2004-09-13 05:39:27 +00:00
|
|
|
if (hasBG && bg->HasFixedBackground()) {
|
2000-06-28 22:19:54 +00:00
|
|
|
aForce = PR_TRUE;
|
|
|
|
fixedBackgroundAttachment = PR_TRUE;
|
|
|
|
}
|
|
|
|
|
|
|
|
// See if the frame is a scrolled frame
|
|
|
|
if (!aForce) {
|
2003-10-17 02:38:37 +00:00
|
|
|
if (aStyleContext->GetPseudoType() == nsCSSAnonBoxes::scrolledContent) {
|
2000-06-28 22:19:54 +00:00
|
|
|
NS_FRAME_LOG(NS_FRAME_TRACE_CALLS,
|
2001-05-31 22:19:43 +00:00
|
|
|
("nsBoxFrame::CreateViewForFrame: scrolled frame=%p", aFrame));
|
2000-06-28 22:19:54 +00:00
|
|
|
aForce = PR_TRUE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (aForce) {
|
|
|
|
// Create a view
|
2003-07-09 03:30:40 +00:00
|
|
|
nsIFrame* parent = aFrame->GetAncestorWithView();
|
|
|
|
NS_ASSERTION(parent, "GetAncestorWithView failed");
|
|
|
|
nsIView* parentView = parent->GetView();
|
2000-06-28 22:19:54 +00:00
|
|
|
NS_ASSERTION(parentView, "no parent with view");
|
2004-11-04 15:06:50 +00:00
|
|
|
nsIViewManager* viewManager = parentView->GetViewManager();
|
|
|
|
NS_ASSERTION(nsnull != viewManager, "null view manager");
|
2000-06-28 22:19:54 +00:00
|
|
|
|
|
|
|
// Create a view
|
2004-11-04 15:06:50 +00:00
|
|
|
nsIView *view = viewManager->CreateView(aFrame->GetRect(), parentView);
|
|
|
|
if (view) {
|
2000-06-28 22:19:54 +00:00
|
|
|
// If the frame has a fixed background attachment, then indicate that the
|
|
|
|
// view's contents should be repainted and not bitblt'd
|
|
|
|
if (fixedBackgroundAttachment) {
|
2001-12-01 14:31:45 +00:00
|
|
|
viewManager->SetViewBitBltEnabled(view, PR_FALSE);
|
2000-06-28 22:19:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Insert the view into the view hierarchy. If the parent view is a
|
|
|
|
// scrolling view we need to do this differently
|
2004-11-24 00:19:21 +00:00
|
|
|
nsIScrollableView* scrollingView = parentView->ToScrollableView();
|
|
|
|
if (scrollingView) {
|
2000-06-28 22:19:54 +00:00
|
|
|
scrollingView->SetScrolledView(view);
|
|
|
|
} else {
|
2001-12-01 14:31:45 +00:00
|
|
|
viewManager->SetViewZIndex(view, autoZIndex, zIndex);
|
|
|
|
// XXX put view last in document order until we can do better
|
|
|
|
viewManager->InsertChild(parentView, view, nsnull, PR_TRUE);
|
2000-06-28 22:19:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// See if the view should be hidden
|
|
|
|
PRBool viewIsVisible = PR_TRUE;
|
2002-01-14 15:00:30 +00:00
|
|
|
PRBool viewHasTransparentContent =
|
|
|
|
!isCanvas &&
|
|
|
|
(!hasBG ||
|
|
|
|
(bg->mBackgroundFlags & NS_STYLE_BG_COLOR_TRANSPARENT));
|
2000-06-28 22:19:54 +00:00
|
|
|
|
2003-11-01 22:34:59 +00:00
|
|
|
const nsStyleVisibility* vis = aStyleContext->GetStyleVisibility();
|
2001-05-31 22:19:43 +00:00
|
|
|
if (NS_STYLE_VISIBILITY_COLLAPSE == vis->mVisible) {
|
2000-06-28 22:19:54 +00:00
|
|
|
viewIsVisible = PR_FALSE;
|
|
|
|
}
|
2001-05-31 22:19:43 +00:00
|
|
|
else if (NS_STYLE_VISIBILITY_HIDDEN == vis->mVisible) {
|
2000-06-28 22:19:54 +00:00
|
|
|
// If it has a widget, hide the view because the widget can't deal with it
|
2003-07-09 03:30:40 +00:00
|
|
|
if (view->HasWidget()) {
|
2000-06-28 22:19:54 +00:00
|
|
|
viewIsVisible = PR_FALSE;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
// If it's a container element, then leave the view visible, but
|
|
|
|
// mark it as having transparent content. The reason we need to
|
|
|
|
// do this is that child elements can override their parent's
|
|
|
|
// hidden visibility and be visible anyway.
|
|
|
|
//
|
|
|
|
// Because this function is called before processing the content
|
|
|
|
// object's child elements, we can't tell if it's a leaf by looking
|
|
|
|
// at whether the frame has any child frames
|
2003-07-09 03:30:40 +00:00
|
|
|
nsIContent* content = aFrame->GetContent();
|
2000-06-28 22:19:54 +00:00
|
|
|
|
2006-05-05 06:52:21 +00:00
|
|
|
if (content && content->IsNodeOfType(nsINode::eELEMENT)) {
|
2000-06-28 22:19:54 +00:00
|
|
|
// The view needs to be visible, but marked as having transparent
|
|
|
|
// content
|
|
|
|
viewHasTransparentContent = PR_TRUE;
|
|
|
|
} else {
|
|
|
|
// Go ahead and hide the view
|
|
|
|
viewIsVisible = PR_FALSE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (viewIsVisible) {
|
|
|
|
if (viewHasTransparentContent) {
|
|
|
|
viewManager->SetViewContentTransparency(view, PR_TRUE);
|
|
|
|
}
|
|
|
|
|
|
|
|
} else {
|
2001-12-01 14:31:45 +00:00
|
|
|
viewManager->SetViewVisibility(view, nsViewVisibility_kHide);
|
2000-06-28 22:19:54 +00:00
|
|
|
}
|
|
|
|
|
2003-11-01 22:34:59 +00:00
|
|
|
viewManager->SetViewOpacity(view, disp->mOpacity);
|
2000-06-28 22:19:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Remember our view
|
2003-07-09 03:30:40 +00:00
|
|
|
aFrame->SetView(view);
|
2000-06-28 22:19:54 +00:00
|
|
|
|
|
|
|
NS_FRAME_LOG(NS_FRAME_TRACE_CALLS,
|
|
|
|
("nsBoxFrame::CreateViewForFrame: frame=%p view=%p",
|
|
|
|
aFrame));
|
2004-11-04 15:06:50 +00:00
|
|
|
if (!view)
|
|
|
|
return NS_ERROR_OUT_OF_MEMORY;
|
2000-06-28 22:19:54 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
2001-10-09 21:02:29 +00:00
|
|
|
|
2002-02-21 13:39:39 +00:00
|
|
|
// If you make changes to this function, check its counterparts
|
|
|
|
// in nsTextBoxFrame and nsAreaFrame
|
|
|
|
nsresult
|
2006-04-10 00:16:29 +00:00
|
|
|
nsBoxFrame::RegUnregAccessKey(PRBool aDoReg)
|
2002-02-21 13:39:39 +00:00
|
|
|
{
|
|
|
|
// if we have no content, we can't do anything
|
|
|
|
if (!mContent)
|
|
|
|
return NS_ERROR_FAILURE;
|
|
|
|
|
|
|
|
// find out what type of element this is
|
2003-11-19 01:20:56 +00:00
|
|
|
nsIAtom *atom = mContent->Tag();
|
2002-02-21 13:39:39 +00:00
|
|
|
|
|
|
|
// only support accesskeys for the following elements
|
|
|
|
if (atom != nsXULAtoms::button &&
|
2002-12-04 05:38:07 +00:00
|
|
|
atom != nsXULAtoms::toolbarbutton &&
|
2002-02-21 13:39:39 +00:00
|
|
|
atom != nsXULAtoms::checkbox &&
|
2002-09-24 22:46:50 +00:00
|
|
|
atom != nsXULAtoms::textbox &&
|
2002-10-03 01:10:51 +00:00
|
|
|
atom != nsXULAtoms::tab &&
|
2002-02-21 13:39:39 +00:00
|
|
|
atom != nsXULAtoms::radio) {
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsAutoString accessKey;
|
|
|
|
mContent->GetAttr(kNameSpaceID_None, nsXULAtoms::accesskey, accessKey);
|
|
|
|
|
|
|
|
if (accessKey.IsEmpty())
|
|
|
|
return NS_OK;
|
|
|
|
|
|
|
|
// With a valid PresContext we can get the ESM
|
|
|
|
// and register the access key
|
2006-04-10 00:16:29 +00:00
|
|
|
nsIEventStateManager *esm = GetPresContext()->EventStateManager();
|
2002-02-21 13:39:39 +00:00
|
|
|
|
2004-02-27 17:17:37 +00:00
|
|
|
nsresult rv;
|
2002-02-21 13:39:39 +00:00
|
|
|
|
2004-02-27 17:17:37 +00:00
|
|
|
PRUint32 key = accessKey.First();
|
|
|
|
if (aDoReg)
|
|
|
|
rv = esm->RegisterAccessKey(mContent, key);
|
|
|
|
else
|
|
|
|
rv = esm->UnregisterAccessKey(mContent, key);
|
2002-02-21 13:39:39 +00:00
|
|
|
|
|
|
|
return rv;
|
|
|
|
}
|
|
|
|
|
2006-07-05 20:42:22 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::FireDOMEventSynch(const nsAString& aDOMEventName, nsIContent *aContent)
|
|
|
|
{
|
|
|
|
// XXX This will be deprecated, because it is not good to fire synchronous DOM events
|
|
|
|
// from layout. It's better to use nsFrame::FireDOMEvent() which is asynchronous.
|
|
|
|
nsPresContext *presContext = GetPresContext();
|
|
|
|
nsIContent *content = aContent ? aContent : mContent;
|
|
|
|
if (content && presContext) {
|
|
|
|
// Fire a DOM event
|
|
|
|
nsCOMPtr<nsIDOMEvent> event;
|
|
|
|
nsCOMPtr<nsIEventListenerManager> manager;
|
|
|
|
content->GetListenerManager(PR_TRUE, getter_AddRefs(manager));
|
|
|
|
if (manager && NS_SUCCEEDED(manager->CreateEvent(presContext, nsnull,
|
|
|
|
NS_LITERAL_STRING("Events"),
|
|
|
|
getter_AddRefs(event)))) {
|
|
|
|
event->InitEvent(aDOMEventName, PR_TRUE, PR_TRUE);
|
|
|
|
|
|
|
|
nsCOMPtr<nsIPrivateDOMEvent> privateEvent(do_QueryInterface(event));
|
|
|
|
privateEvent->SetTrusted(PR_TRUE);
|
|
|
|
|
|
|
|
nsEventDispatcher::DispatchDOMEvent(content, nsnull, event,
|
2006-08-01 17:29:48 +00:00
|
|
|
presContext, nsnull);
|
2006-07-05 20:42:22 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2001-10-09 21:02:29 +00:00
|
|
|
|
2004-09-28 18:37:50 +00:00
|
|
|
void
|
|
|
|
nsBoxFrame::CheckBoxOrder(nsBoxLayoutState& aState)
|
|
|
|
{
|
|
|
|
// Run through our list of children and check whether we
|
|
|
|
// need to sort them. Count up the children at the same
|
|
|
|
// time, since we're already traversing the list.
|
|
|
|
PRBool orderBoxes = PR_FALSE;
|
|
|
|
PRInt32 childCount = 0;
|
|
|
|
nsIFrame *child = mFrames.FirstChild();
|
|
|
|
|
|
|
|
while (child) {
|
|
|
|
++childCount;
|
|
|
|
|
|
|
|
PRUint32 ordinal;
|
|
|
|
child->GetOrdinal(aState, ordinal);
|
|
|
|
if (ordinal != DEFAULT_ORDINAL_GROUP)
|
|
|
|
orderBoxes = PR_TRUE;
|
|
|
|
|
|
|
|
child = child->GetNextSibling();
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!orderBoxes || childCount < 2)
|
|
|
|
return;
|
|
|
|
|
|
|
|
// Turn the child list into an array for sorting.
|
|
|
|
nsIFrame** boxes = new nsIFrame*[childCount];
|
|
|
|
nsIFrame* box = mFrames.FirstChild();
|
|
|
|
nsIFrame** boxPtr = boxes;
|
|
|
|
while (box) {
|
|
|
|
*boxPtr++ = box;
|
|
|
|
box = box->GetNextSibling();
|
|
|
|
}
|
|
|
|
|
|
|
|
// sort the array by ordinal group, selection sort
|
|
|
|
// XXX this could use a more efficient sort
|
|
|
|
PRInt32 i, j, min;
|
|
|
|
PRUint32 minOrd, jOrd;
|
|
|
|
for(i = 0; i < childCount; i++) {
|
|
|
|
min = i;
|
|
|
|
boxes[min]->GetOrdinal(aState, minOrd);
|
|
|
|
for(j = i + 1; j < childCount; j++) {
|
|
|
|
boxes[j]->GetOrdinal(aState, jOrd);
|
|
|
|
if (jOrd < minOrd) {
|
|
|
|
min = j;
|
|
|
|
minOrd = jOrd;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
box = boxes[min];
|
|
|
|
boxes[min] = boxes[i];
|
|
|
|
boxes[i] = box;
|
|
|
|
}
|
|
|
|
|
|
|
|
// turn the array back into linked list, with first and last cached
|
|
|
|
mFrames.SetFrames(boxes[0]);
|
|
|
|
for (i = 0; i < childCount - 1; ++i)
|
|
|
|
boxes[i]->SetNextSibling(boxes[i+1]);
|
|
|
|
|
|
|
|
boxes[childCount-1]->SetNextSibling(nsnull);
|
|
|
|
delete [] boxes;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::SetLayoutManager(nsIBoxLayout* aLayout)
|
|
|
|
{
|
|
|
|
mLayoutManager = aLayout;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetLayoutManager(nsIBoxLayout** aLayout)
|
|
|
|
{
|
|
|
|
*aLayout = mLayoutManager;
|
|
|
|
NS_IF_ADDREF(*aLayout);
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsBoxFrame::LayoutChildAt(nsBoxLayoutState& aState, nsIBox* aBox, const nsRect& aRect)
|
|
|
|
{
|
|
|
|
// get the current rect
|
|
|
|
nsRect oldRect(aBox->GetRect());
|
|
|
|
aBox->SetBounds(aState, aRect);
|
|
|
|
|
|
|
|
PRBool dirty = PR_FALSE;
|
|
|
|
PRBool dirtyChildren = PR_FALSE;
|
|
|
|
aBox->IsDirty(dirty);
|
|
|
|
aBox->HasDirtyChildren(dirtyChildren);
|
|
|
|
|
|
|
|
PRBool layout = PR_TRUE;
|
|
|
|
if (!(dirty || dirtyChildren) && aState.LayoutReason() != nsBoxLayoutState::Initial)
|
|
|
|
layout = PR_FALSE;
|
|
|
|
|
|
|
|
if (layout || (oldRect.width != aRect.width || oldRect.height != aRect.height)) {
|
|
|
|
return aBox->Layout(aState);
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::RelayoutChildAtOrdinal(nsBoxLayoutState& aState, nsIBox* aChild)
|
|
|
|
{
|
|
|
|
PRUint32 ord;
|
|
|
|
aChild->GetOrdinal(aState, ord);
|
|
|
|
|
2004-09-30 00:18:49 +00:00
|
|
|
nsIFrame *child = mFrames.FirstChild();
|
|
|
|
nsIFrame *curPrevSib = nsnull, *newPrevSib = nsnull;
|
|
|
|
PRBool foundPrevSib = PR_FALSE, foundNewPrevSib = PR_FALSE;
|
|
|
|
|
|
|
|
while (child) {
|
|
|
|
if (child == aChild)
|
|
|
|
foundPrevSib = PR_TRUE;
|
|
|
|
else if (!foundPrevSib)
|
|
|
|
curPrevSib = child;
|
|
|
|
|
|
|
|
PRUint32 ordCmp;
|
|
|
|
child->GetOrdinal(aState, ordCmp);
|
|
|
|
if (ord < ordCmp)
|
|
|
|
foundNewPrevSib = PR_TRUE;
|
2004-10-01 00:22:07 +00:00
|
|
|
else if (!foundNewPrevSib && child != aChild)
|
2004-09-30 00:18:49 +00:00
|
|
|
newPrevSib = child;
|
|
|
|
|
|
|
|
child->GetNextBox(&child);
|
2004-09-28 18:37:50 +00:00
|
|
|
}
|
2004-09-30 00:18:49 +00:00
|
|
|
|
|
|
|
NS_ASSERTION(foundPrevSib, "aChild not in frame list?");
|
|
|
|
|
|
|
|
if (curPrevSib == newPrevSib) {
|
|
|
|
// This box is not moving.
|
|
|
|
return NS_OK;
|
2004-09-28 18:37:50 +00:00
|
|
|
}
|
2004-09-30 00:18:49 +00:00
|
|
|
|
|
|
|
// Take aChild out of its old position in the child list.
|
|
|
|
if (curPrevSib)
|
|
|
|
curPrevSib->SetNextSibling(aChild->GetNextSibling());
|
2004-10-01 00:22:07 +00:00
|
|
|
else
|
|
|
|
mFrames.SetFrames(aChild->GetNextSibling());
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
nsIBox* newNextSib;
|
|
|
|
if (newPrevSib) {
|
|
|
|
// insert |aChild| between |newPrevSib| and its next sibling
|
2004-09-30 00:18:49 +00:00
|
|
|
newNextSib = newPrevSib->GetNextSibling();
|
|
|
|
newPrevSib->SetNextSibling(aChild);
|
2004-09-28 18:37:50 +00:00
|
|
|
} else {
|
|
|
|
// no |newPrevSib| found, so this box will become |mFirstChild|
|
2004-09-30 00:18:49 +00:00
|
|
|
newNextSib = mFrames.FirstChild();
|
|
|
|
mFrames.SetFrames(aChild);
|
2004-09-28 18:37:50 +00:00
|
|
|
}
|
|
|
|
|
2004-09-30 00:18:49 +00:00
|
|
|
aChild->SetNextSibling(newNextSib);
|
2004-09-28 18:37:50 +00:00
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
NS_IMETHODIMP
|
|
|
|
nsBoxFrame::GetIndexOf(nsIBox* aBox, PRInt32* aIndex)
|
|
|
|
{
|
|
|
|
nsIBox* child = mFrames.FirstChild();
|
|
|
|
PRInt32 count = 0;
|
|
|
|
while (child)
|
|
|
|
{
|
|
|
|
if (aBox == child) {
|
|
|
|
*aIndex = count;
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
child->GetNextBox(&child);
|
|
|
|
count++;
|
|
|
|
}
|
|
|
|
|
|
|
|
*aIndex = -1;
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
PRBool
|
|
|
|
nsBoxFrame::GetWasCollapsed(nsBoxLayoutState& aState)
|
|
|
|
{
|
|
|
|
return nsBox::GetWasCollapsed(aState);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsBoxFrame::SetWasCollapsed(nsBoxLayoutState& aState, PRBool aWas)
|
|
|
|
{
|
|
|
|
nsBox::SetWasCollapsed(aState, aWas);
|
|
|
|
}
|
2006-01-26 02:29:17 +00:00
|
|
|
|
|
|
|
/**
|
|
|
|
* This wrapper class lets us redirect mouse hits from descendant frames
|
|
|
|
* of a menu to the menu itself, if they didn't specify 'allowevents'.
|
|
|
|
*
|
|
|
|
* The wrapper simply turns a hit on a descendant element
|
|
|
|
* into a hit on the menu itself, unless there is an element between the target
|
|
|
|
* and the menu with the "allowevents" attribute.
|
|
|
|
*
|
|
|
|
* This is used by nsMenuFrame and nsTreeColFrame.
|
|
|
|
*
|
|
|
|
* Note that turning a hit on a descendant element into nsnull, so events
|
|
|
|
* could fall through to the menu background, might be an appealing simplification
|
|
|
|
* but it would mean slightly strange behaviour in some cases, because grabber
|
|
|
|
* wrappers can be created for many individual lists and items, so the exact
|
|
|
|
* fallthrough behaviour would be complex. E.g. an element with "allowevents"
|
|
|
|
* on top of the Content() list could receive the event even if it was covered
|
|
|
|
* by a PositionedDescenants() element without "allowevents". It is best to
|
|
|
|
* never convert a non-null hit into null.
|
|
|
|
*/
|
|
|
|
// REVIEW: This is roughly of what nsMenuFrame::GetFrameForPoint used to do.
|
|
|
|
// I've made 'allowevents' affect child elements because that seems the only
|
|
|
|
// reasonable thing to do.
|
|
|
|
class nsDisplayXULEventRedirector : public nsDisplayWrapList {
|
|
|
|
public:
|
|
|
|
nsDisplayXULEventRedirector(nsIFrame* aFrame, nsDisplayItem* aItem,
|
|
|
|
nsIFrame* aTargetFrame)
|
|
|
|
: nsDisplayWrapList(aFrame, aItem), mTargetFrame(aTargetFrame) {}
|
|
|
|
nsDisplayXULEventRedirector(nsIFrame* aFrame, nsDisplayList* aList,
|
|
|
|
nsIFrame* aTargetFrame)
|
|
|
|
: nsDisplayWrapList(aFrame, aList), mTargetFrame(aTargetFrame) {}
|
|
|
|
virtual nsIFrame* HitTest(nsDisplayListBuilder* aBuilder, nsPoint aPt);
|
2006-01-26 22:58:22 +00:00
|
|
|
NS_DISPLAY_DECL_NAME("XULEventRedirector")
|
2006-01-26 02:29:17 +00:00
|
|
|
private:
|
|
|
|
nsIFrame* mTargetFrame;
|
|
|
|
};
|
|
|
|
|
|
|
|
nsIFrame* nsDisplayXULEventRedirector::HitTest(nsDisplayListBuilder* aBuilder,
|
|
|
|
nsPoint aPt)
|
|
|
|
{
|
|
|
|
nsIFrame* frame = mList.HitTest(aBuilder, aPt);
|
|
|
|
if (!frame)
|
|
|
|
return nsnull;
|
|
|
|
|
|
|
|
for (nsIContent* content = frame->GetContent();
|
|
|
|
content && content != mTargetFrame->GetContent();
|
|
|
|
content = content->GetParent()) {
|
|
|
|
if (content->AttrValueIs(kNameSpaceID_None, nsXULAtoms::allowevents,
|
|
|
|
nsXULAtoms::_true, eCaseMatters)) {
|
|
|
|
// Events are allowed on 'frame', so let it go.
|
|
|
|
return frame;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
// Treat it as a hit on the target frame itself.
|
|
|
|
return mTargetFrame;
|
|
|
|
}
|
|
|
|
|
|
|
|
class nsXULEventRedirectorWrapper : public nsDisplayWrapper
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
nsXULEventRedirectorWrapper(nsIFrame* aTargetFrame)
|
|
|
|
: mTargetFrame(aTargetFrame) {}
|
|
|
|
virtual nsDisplayItem* WrapList(nsDisplayListBuilder* aBuilder,
|
|
|
|
nsIFrame* aFrame, nsDisplayList* aList) {
|
|
|
|
return new (aBuilder)
|
|
|
|
nsDisplayXULEventRedirector(aFrame, aList, mTargetFrame);
|
|
|
|
}
|
|
|
|
virtual nsDisplayItem* WrapItem(nsDisplayListBuilder* aBuilder,
|
|
|
|
nsDisplayItem* aItem) {
|
|
|
|
return new (aBuilder)
|
|
|
|
nsDisplayXULEventRedirector(aItem->GetUnderlyingFrame(), aItem,
|
|
|
|
mTargetFrame);
|
|
|
|
}
|
|
|
|
private:
|
|
|
|
nsIFrame* mTargetFrame;
|
|
|
|
};
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsBoxFrame::WrapListsInRedirector(nsDisplayListBuilder* aBuilder,
|
|
|
|
const nsDisplayListSet& aIn,
|
|
|
|
const nsDisplayListSet& aOut)
|
|
|
|
{
|
|
|
|
nsXULEventRedirectorWrapper wrapper(this);
|
|
|
|
return wrapper.WrapLists(aBuilder, this, aIn, aOut);
|
|
|
|
}
|