anchor.diff:      }
     }
   
  +  /// If buf is non-null it must have size 4*w*h elements
     Float32List ExtractFloatData(Float32List buf, int x, int y, int w, int h) {
       _cgl.bindFramebuffer(GL_FRAMEBUFFER, _framebuffer);
  -    final FramebufferFormat f = FramebufferFormat.fromActive(_cgl);
  -    print("READ FORMAT $f");
  -    if (f.type != GL_FLOAT) {
  -      print("unexpcted non float type: $f");
  +    if (buf == null) {
  +      buf = Float32List(4 * w * h);
       }
  -    if (buf == null) {
  -      buf = Float32List(f.channels * w * h);
  -    }
  -    _cgl.readPixels(x, y, w, h, f.format, GL_FLOAT, buf);
  +    _cgl.readPixels(
  +        x,
  +        y,
  +        w,
  +        h,
  +        GL_RGBA,
  +        GL_FLOAT,
  +        buf);
       _cgl.bindFramebuffer(GL_FRAMEBUFFER, null);
       return buf;
     }
   
  +  /// If buf is non-null it must have size 4*w*h elements
     Uint8List ExtractByteData(Uint8List buf, int x, int y, int w, int h) {
       _cgl.bindFramebuffer(GL_FRAMEBUFFER, _framebuffer);
  -    final FramebufferFormat f = FramebufferFormat.fromActive(_cgl);
  -    print("READ FORMAT $f");
  -    assert(f.type == GL_UNSIGNED_BYTE);
       if (buf == null) {
  -      buf = Uint8List(f.channels * w * h);
  +      buf = Uint8List(4 * w * h);
       }
  -    _cgl.readPixels(x, y, w, h, f.format, f.type, buf);
  +    _cgl.readPixels(
  +        x,
  +        y,
  +        w,
  +        h,
  +        GL_RGBA,
  +        GL_UNSIGNED_BYTE,
  +        buf);
       _cgl.bindFramebuffer(GL_FRAMEBUFFER, null);
       return buf;
     }
  
positive.code:   }
  }
  
  class Framebuffer {
    ChronosGL _cgl;
  
  
negative.code: part of core;
  
  const int GL_CLEAR_ALL =
  GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT;
  
  int TextureChannelsByType(int format) {
    switch (format) {
  