changeset 4658:9862ad8cc8f8

Merged commit #4653 (float clearance). Test case: <body> <div id="a"> <div id="b" style="float:left">main</div> </div> <div id="c" style="clear:left"></div> <div id="d">footer</div> </body> Note: passes all the tests at http://www.dillo.org/test/4648/test-suite.v1.txt
author Jorge Arellano Cid <jcid@dillo.org>
date Di, 09 Aug 2016 09:23:55 -0400
parents 6bf4db806b57
children 51dcebebbaa6
files dw/ooffloatsmgr.cc dw/ooffloatsmgr.hh dw/textblock.cc
diffstat 3 files changed, 43 insertions(+), 3 deletions(-) [+]
line wrap: on
line diff
--- a/dw/ooffloatsmgr.cc	Do Aug 04 10:12:09 2016 -0400
+++ b/dw/ooffloatsmgr.cc	Di Aug 09 09:23:55 2016 -0400
@@ -657,6 +657,19 @@
    vloat->dirty = true;
    DBG_OBJ_SET_BOOL_O (vloat->getWidget (), "<Float>.dirty", vloat->dirty);
 
+   updateGenerators (vloat);
+
+   DBG_OBJ_LEAVE ();
+}
+
+/**
+ * \brief Update all generators which are affected by a given float.
+ */
+void OOFFloatsMgr::updateGenerators (Float *vloat)
+{
+   DBG_OBJ_ENTER ("resize.oofm", 0, "updateGenerators", "#%d [%p]",
+                  vloat->index, vloat->getWidget ());
+
    assert (vloat->getWidget()->getWidgetReference() != NULL);
 
    int first = getOOFAwareWidget(vloat->generator)->index;
@@ -674,8 +687,7 @@
       tbInfos->get(i)->getOOFAwareWidget()->updateReference(0);
 
    SizeChanged = false; // Done.
-   DBG_OBJ_SET_BOOL ("SizeChanged", SizeChanged);
-   
+
    DBG_OBJ_LEAVE ();
 }
 
@@ -749,6 +761,8 @@
    getFloatsListsAndSide (vloat, &listSame, &listOpp, &side);
    ensureFloatSize (vloat);
 
+   int oldYReal = vloat->yReal;
+
    // "yReal" may change due to collisions (see below).
    vloat->yReq = vloat->yReal = y;
 
@@ -813,6 +827,25 @@
    DBG_OBJ_MSGF ("resize.oofm", 1, "vloat->yReq = %d, vloat->yReal = %d",
                  vloat->yReq, vloat->yReal);
 
+   // In some cases, an explicit update is neccessary, as in this example:
+   //
+   // <body>
+   //     <div id="a">
+   //         <div id="b" style="float:left">main</div>
+   //     </div>
+   //     <div id="c" style="clear:both">x</div>
+   //     <div id="d">footer</div>
+   // </body>
+   //
+   // Without an explicit update, #c would keep an old value for extraSpace.top,
+   // based on the old value of vloat->yReal.
+   //
+   // Notice that #c would be updated otherwise, if it had at least one word
+   // content.
+
+   if (vloat->yReal != oldYReal)
+      updateGenerators (vloat);
+
    DBG_OBJ_LEAVE ();
 }
 
--- a/dw/ooffloatsmgr.hh	Do Aug 04 10:12:09 2016 -0400
+++ b/dw/ooffloatsmgr.hh	Di Aug 09 09:23:55 2016 -0400
@@ -170,6 +170,7 @@
    void moveExternalIndices (lout::container::typed::Vector<Float> *list,
                              int oldStartIndex, int diff);
    Float *findFloatByWidget (core::Widget *widget);
+   void updateGenerators (Float *vloat);
    int findTBInfo (int y);
 
    void sizeAllocateFloats (Side side);
--- a/dw/textblock.cc	Do Aug 04 10:12:09 2016 -0400
+++ b/dw/textblock.cc	Di Aug 09 09:23:55 2016 -0400
@@ -3044,8 +3044,14 @@
 
 void Textblock::updateReference (int ref)
 {
-   if (words->size () > 0)
+   DBG_OBJ_ENTER ("resize", 0, "updateReference", "%d", ref);
+
+   // Only `queueResize` when there're words or float clearance
+   // (float clearance may change `extraSpace.top`).
+   if (words->size () > 0 || getStyle()->clear != core::style::CLEAR_NONE)
       queueResize (ref, false);
+
+   DBG_OBJ_LEAVE ();
 }
 
 void Textblock::widgetRefSizeChanged (int externalIndex)