El mar, 28-07-2009 a las 20:30 +0200, Albert Astals Cid escribió:

> > what about adding a new method to OutputDev like:
> >
> > GBool axialShadedSupportExtend(GfxAxialShading *shading);
> >
> > and of course
> >
> > GBool radialShadedSupportExetend(GfxRadialShading *shading);
> 
> That would work too (minus the typo on the second function ;-) ) 
> 
> Albert

Attached patch fixes it, and attached to bug #10942 there's a new patch
for radial patterns too. 


-- 
Carlos Garcia Campos
PGP key: http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x523E6462
diff --git a/poppler/CairoOutputDev.cc b/poppler/CairoOutputDev.cc
index 670ae40..565ac1c 100644
--- a/poppler/CairoOutputDev.cc
+++ b/poppler/CairoOutputDev.cc
@@ -609,12 +609,21 @@ GBool CairoOutputDev::axialShadedFill(GfxState *state, GfxAxialShading *shading,
   cairo_pattern_destroy(fill_pattern);
   fill_pattern = cairo_pattern_create_linear (x0 + tMin * dx, y0 + tMin * dy,
 					      x0 + tMax * dx, y0 + tMax * dy);
+  if (!shading->getExtend0() && !shading->getExtend1())
+    cairo_pattern_set_extend (fill_pattern, CAIRO_EXTEND_NONE);
+  else
+    cairo_pattern_set_extend (fill_pattern, CAIRO_EXTEND_PAD);
 
   // TODO: use the actual stops in the shading in the case
   // of linear interpolation (Type 2 Exponential functions with N=1)
   return gFalse;
 }
 
+GBool CairoOutputDev::axialShadedSupportExtend(GfxState *state, GfxAxialShading *shading)
+{
+  return (shading->getExtend0() == shading->getExtend1());
+}
+
 void CairoOutputDev::clip(GfxState *state) {
   doPath (cairo, state, state->getPath());
   cairo_set_fill_rule (cairo, CAIRO_FILL_RULE_WINDING);
diff --git a/poppler/CairoOutputDev.h b/poppler/CairoOutputDev.h
index cd66cb7..afff7ea 100644
--- a/poppler/CairoOutputDev.h
+++ b/poppler/CairoOutputDev.h
@@ -151,6 +151,7 @@ public:
   virtual void fill(GfxState *state);
   virtual void eoFill(GfxState *state);
   virtual GBool axialShadedFill(GfxState *state, GfxAxialShading *shading, double tMin, double tMax);
+  virtual GBool axialShadedSupportExtend(GfxState *state, GfxAxialShading *shading);
 
   //----- path clipping
   virtual void clip(GfxState *state);
diff --git a/poppler/Gfx.cc b/poppler/Gfx.cc
index c3f257f..284a124 100644
--- a/poppler/Gfx.cc
+++ b/poppler/Gfx.cc
@@ -2360,6 +2360,7 @@ void Gfx::doAxialShFill(GfxAxialShading *shading) {
   GfxColor color0, color1;
   int nComps;
   int i, j, k;
+  GBool needExtend = gTrue;
 
   // get the clip region bbox
   state->getUserClipBBox(&xMin, &yMin, &xMax, &yMax);
@@ -2447,6 +2448,12 @@ void Gfx::doAxialShFill(GfxAxialShading *shading) {
   }
   shading->getColor(tt, &color0);
 
+  if (out->useFillColorStop()) {
+    // make sure we add stop color when t = tMin
+    state->setFillColor(&color0);
+    out->updateFillColorStop(state, (tt - tMin)/(tMax - tMin));
+  }
+
   // compute the coordinates of the point on the t axis at t = tMin;
   // then compute the intersection of the perpendicular line with the
   // bounding box
@@ -2484,6 +2491,11 @@ void Gfx::doAxialShFill(GfxAxialShading *shading) {
     doneBBox1 = bboxIntersections[1] < tMin;
     doneBBox2 = bboxIntersections[2] > tMax;
   }
+
+  // If output device doesn't support the extended mode required
+  // we have to do it here
+  needExtend = !out->axialShadedSupportExtend(state, shading);
+
   while (i < axialMaxSplits) {
 
     // bisect until color difference is small enough or we hit the
@@ -2589,12 +2601,15 @@ void Gfx::doAxialShFill(GfxAxialShading *shading) {
     else
       out->updateFillColor(state);
 
-    // fill the region
-    state->moveTo(ux0, uy0);
-    state->lineTo(vx0, vy0);
-    state->lineTo(vx1, vy1);
-    state->lineTo(ux1, uy1);
-    state->closePath();
+    if (needExtend) {
+      // fill the region
+      state->moveTo(ux0, uy0);
+      state->lineTo(vx0, vy0);
+      state->lineTo(vx1, vy1);
+      state->lineTo(ux1, uy1);
+      state->closePath();
+    }
+
     if (!out->useFillColorStop()) {
       if (!contentIsHidden())
         out->fill(state);
@@ -2611,6 +2626,13 @@ void Gfx::doAxialShFill(GfxAxialShading *shading) {
   }
 
   if (out->useFillColorStop()) {
+    if (!needExtend) {
+      state->moveTo(xMin, yMin);
+      state->lineTo(xMin, yMax);
+      state->lineTo(xMax, yMax);
+      state->lineTo(xMax, yMin);
+      state->closePath();
+    }
     if (!contentIsHidden())
       out->fill(state);
     state->clearPath();
diff --git a/poppler/OutputDev.h b/poppler/OutputDev.h
index 76d3611..d1cb2b0 100644
--- a/poppler/OutputDev.h
+++ b/poppler/OutputDev.h
@@ -199,8 +199,12 @@ public:
     { return gFalse; }
   virtual GBool axialShadedFill(GfxState * /*state*/, GfxAxialShading * /*shading*/, double /*tMin*/, double /*tMax*/)
     { return gFalse; }
+  virtual GBool axialShadedSupportExtend(GfxState * /*state*/, GfxAxialShading * /*shading*/)
+    { return gFalse; }
   virtual GBool radialShadedFill(GfxState * /*state*/, GfxRadialShading * /*shading*/)
     { return gFalse; }
+  virtual GBool radialShadedSupportExtend(GfxState * /*state*/, GfxRadialShading * /*shading*/)
+    { return gFalse; }
 
   //----- path clipping
   virtual void clip(GfxState * /*state*/) {}

Attachment: signature.asc
Description: Esta parte del mensaje está firmada digitalmente

_______________________________________________
poppler mailing list
[email protected]
http://lists.freedesktop.org/mailman/listinfo/poppler

Reply via email to