<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<!DOCTYPE bugzilla SYSTEM "https://bugs.webkit.org/page.cgi?id=bugzilla.dtd">

<bugzilla version="5.0.4.1"
          urlbase="https://bugs.webkit.org/"
          
          maintainer="admin@webkit.org"
>

    <bug>
          <bug_id>105300</bug_id>
          
          <creation_ts>2012-12-18 07:57:55 -0800</creation_ts>
          <short_desc>[Skia] Animated transformations on bitmap images shake</short_desc>
          <delta_ts>2013-04-09 13:30:16 -0700</delta_ts>
          <reporter_accessible>1</reporter_accessible>
          <cclist_accessible>1</cclist_accessible>
          <classification_id>1</classification_id>
          <classification>Unclassified</classification>
          <product>WebKit</product>
          <component>SVG</component>
          <version>528+ (Nightly build)</version>
          <rep_platform>All</rep_platform>
          <op_sys>All</op_sys>
          <bug_status>RESOLVED</bug_status>
          <resolution>WONTFIX</resolution>
          
          
          <bug_file_loc>http://codepen.io/joe/full/KnCkz</bug_file_loc>
          <status_whiteboard></status_whiteboard>
          <keywords></keywords>
          <priority>P2</priority>
          <bug_severity>Normal</bug_severity>
          <target_milestone>---</target_milestone>
          
          
          <everconfirmed>1</everconfirmed>
          <reporter name="Matt Hinchliffe">matt.hinchliffe</reporter>
          <assigned_to name="Nobody">webkit-unassigned</assigned_to>
          <cc>fmalita</cc>
    
    <cc>krit</cc>
    
    <cc>pdr</cc>
    
    <cc>schenney</cc>
    
    <cc>senorblanco</cc>
    
    <cc>zimmermann</cc>
          

      

      

      

          <comment_sort_order>oldest_to_newest</comment_sort_order>  
          <long_desc isprivate="0" >
    <commentid>793645</commentid>
    <comment_count>0</comment_count>
    <who name="Matt Hinchliffe">matt.hinchliffe</who>
    <bug_when>2012-12-18 07:57:55 -0800</bug_when>
    <thetext>Animating a transform property (scale, translate etc.) of a bitmap image is shaky. The wobble as it transforms is pretty uncomfortable to view.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>793653</commentid>
    <comment_count>1</comment_count>
    <who name="Matt Hinchliffe">matt.hinchliffe</who>
    <bug_when>2012-12-18 08:02:26 -0800</bug_when>
    <thetext>Confirmed issue on iOS 6</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>793887</commentid>
    <comment_count>2</comment_count>
    <who name="Philip Rogers">pdr</who>
    <bug_when>2012-12-18 11:44:27 -0800</bug_when>
    <thetext>Confirmed. Likely an integer clamping issue.

Downstream bug: crbug.com/166638</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794253</commentid>
    <comment_count>3</comment_count>
    <who name="Philip Rogers">pdr</who>
    <bug_when>2012-12-18 18:30:39 -0800</bug_when>
    <thetext>(In reply to comment #1)
&gt; Confirmed issue on iOS 6

Can you double-check this?</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794319</commentid>
    <comment_count>4</comment_count>
    <who name="Philip Rogers">pdr</who>
    <bug_when>2012-12-18 21:10:18 -0800</bug_when>
    <thetext>Looks like the issue is constrained to Skia-backed platforms (not CG / iOS). ImageSkia&apos;s RESAMPLE_AWESOME clamps to integer boundaries which is great for beautiful static images but not that awesome for animations (see http://trac.webkit.org/browser/trunk/Source/WebCore/platform/graphics/skia/ImageSkia.cpp#L268). Forcing linear resampling fixes this and the bouncing goes away.

A couple ideas:
1) Add an additional resampling parameter to GraphicsContext::drawImage so we would have something like LOW (nearestneighbor), DEFAULT (linear), and STATIC_HIGH (bilinear awesome).
2) Only RESAMPLE_AWESOME for identity matrices (alternatively, only for integer scales or translates). I have a simple patch to do this but the problem will still exist for animations of width/height.

@fmalita, @schenney, opinions here?</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794463</commentid>
    <comment_count>5</comment_count>
    <who name="Matt Hinchliffe">matt.hinchliffe</who>
    <bug_when>2012-12-19 02:13:36 -0800</bug_when>
    <thetext>(In reply to comment #3)
&gt; (In reply to comment #1)
&gt; &gt; Confirmed issue on iOS 6
&gt; 
&gt; Can you double-check this?

Yes, the issue also effects iOS 6.0.1 (checking on an iPad). I&apos;ve made a better example where the issue is more apparent: http://codepen.io/joe/full/oinzb</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794567</commentid>
    <comment_count>6</comment_count>
    <who name="Stephen Chenney">schenney</who>
    <bug_when>2012-12-19 05:30:11 -0800</bug_when>
    <thetext>One typical way to solve this is to use fast and dirty resampling while moving and then clean it up when static. I doubt that&apos;s practical here, as we would have to detect and redraw the last frame of an animation.

Why does Skia enforce integral boundaries for bilinear resampling? That just seems pointless as the algoritihm should be able to handle any boundary position for the output. Is the issue here clamping of the input image rectangle?</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794588</commentid>
    <comment_count>7</comment_count>
    <who name="Florin Malita">fmalita</who>
    <bug_when>2012-12-19 05:53:52 -0800</bug_when>
    <thetext>(In reply to comment #4)
&gt; Looks like the issue is constrained to Skia-backed platforms (not CG / iOS). ImageSkia&apos;s RESAMPLE_AWESOME clamps to integer boundaries which is great for beautiful static images but not that awesome for animations (see http://trac.webkit.org/browser/trunk/Source/WebCore/platform/graphics/skia/ImageSkia.cpp#L268). Forcing linear resampling fixes this and the bouncing goes away.
&gt; 
&gt; A couple ideas:
&gt; 1) Add an additional resampling parameter to GraphicsContext::drawImage so we would have something like LOW (nearestneighbor), DEFAULT (linear), and STATIC_HIGH (bilinear awesome).
&gt; 2) Only RESAMPLE_AWESOME for identity matrices (alternatively, only for integer scales or translates). I have a simple patch to do this but the problem will still exist for animations of width/height.
&gt; 
&gt; @fmalita, @schenney, opinions here?

We&apos;re already limiting RESAMPLE_AWESOME to scaling/translation matrices. I guess we could limit it further to identity-only but that would diminish its awesomeness :)

I don&apos;t think making it dependent on integer scales/translations would be good though - switching between different interpolation methods during animation as we&apos;re hitting integer values is going to look much worse than what&apos;s going on now.

Maybe there&apos;s a way to pass back clamping info and adjust the sizing/position to compensate with subpixel positioning?</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794592</commentid>
    <comment_count>8</comment_count>
    <who name="Florin Malita">fmalita</who>
    <bug_when>2012-12-19 05:57:53 -0800</bug_when>
    <thetext>(In reply to comment #6)
&gt; One typical way to solve this is to use fast and dirty resampling while moving and then clean it up when static. I doubt that&apos;s practical here, as we would have to detect and redraw the last frame of an animation.

Wouldn&apos;t we have the same issue when animating with JS? There&apos;s no way to really know when the image turns static (if at all).</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>794703</commentid>
    <comment_count>9</comment_count>
    <who name="Stephen White">senorblanco</who>
    <bug_when>2012-12-19 08:40:21 -0800</bug_when>
    <thetext>(In reply to comment #8)
&gt; (In reply to comment #6)
&gt; &gt; One typical way to solve this is to use fast and dirty resampling while moving and then clean it up when static. I doubt that&apos;s practical here, as we would have to detect and redraw the last frame of an animation.
&gt; 
&gt; Wouldn&apos;t we have the same issue when animating with JS? There&apos;s no way to really know when the image turns static (if at all).

Regular DOM content uses the timer-based resize which animates using bilinear and switches to Lanczos when the animation is complete, as Stephen C describes.  Take a look at the ImageQualityController in RenderBoxModelObject.cpp.  The basic algorithm is: 

1)  When an object is first resized, use high-quality resampling, stash the RBMO in a hash table and set a 500ms timer.
2)  If another resize request for the same object comes in before the timer expires, it&apos;s considered to be animating, and drawn using bilinear.  The timer is kicked forward.
3)  When the timer expires without further resize requests, all hashed objects are redrawn using Lanczos.

Not sure if SVG can use this directly, but perhaps it could do something similar.</thetext>
  </long_desc>
      
      

    </bug>

</bugzilla>