Where exactly is the code? I don't see anything about image resizing
here.

Thanks,
Strom

On Jan 15, 2:50 pm, Timothy Perrett <timo...@getintheloop.eu> wrote:
> I've added the code here:
>
> http://github.com/dpp/liftweb/tree/wip_tim_285
>
> Cheers, Tim
>
> On Jan 15, 8:52 pm, Ross Mellgren <dri...@gmail.com> wrote:
>
> > This is already on the main list, I moved it there after Peter mentioned 
> > it. Sorry, I have a bad habit of starting conversations on lift-committers 
> > I'm trying to break before David breaks it for me ;-)
>
> > GIF resizing was a huge sticking point for the project here at Paytronix 
> > that this code was originally written for. I'd prefer it if 
> > allresizetransforms couldresizeinto the same format as the source (right 
> > now it's GIF -> PNG, and most everything else is source type -> dest type), 
> > but:
> >   - Shrunk GIFs are ugly due to the limited color palette and single-bit 
> > transparency.
> >   - Calculating an ideal palette and doing any dithering is not trivial, 
> > and for the application I had it was fine to change the format.
>
> > -Ross
>
> > On Jan 15, 2010, at 3:47 PM, Jonathan Hoffman wrote:
>
> > > Hi Ross,
>
> > > That looks good.  It seems you're doing a much better job of handling
> > > gif than I would have.  Maybe we should move this discussion to the
> > > main list to get everyone's input on what features would be useful.
>
> > > Tim, If you've already created a branch, let me know and I'll get my
> > > stuff in there too-- Myresizecode uses the sanselan project to read
> > > exif orientation information.
>
> > > On Fri, Jan 15, 2010 at 10:33 AM, Ross Mellgren <dri...@gmail.com> wrote:
> > >> Well, it has to keep the whole source (packed) in memory and the target 
> > >> (unpacked / 32 bit RGBA) in memory, so I would assume that as long as 
> > >> AffineTransformOp is not doing something untoward it's probably around 
> > >> (src width * src height * src bytes/pixel) + (dest width * dest height * 
> > >> 4 bytes) plus a little bit extra.
>
> > >> I'm not a Java2D guru or anything, so I'm not sure how that could be 
> > >> improved offhand.
>
> > >> If you want to wrap it up and put it in, that'd be awesome!
>
> > >> -Ross
>
> > >> On Jan 15, 2010, at 10:17 AM, Timothy Perrett wrote:
>
> > >>> Cool stuff Ross, whats the overhead like in terms of memory etc?
>
> > >>> I might have a bit of time to put this into a module and stuff it on 
> > >>> review board.
>
> > >>> Cheers, Tim
>
> > >>> On 15 Jan 2010, at 15:03, Ross Mellgren wrote:
>
> > >>>> According to Jon on the call, he said he was putting together just 
> > >>>> such a lift module (forimagestuff), so I figured I'd toss this over in 
> > >>>> case it was of use to him in that module.
>
> > >>>> If anyone else wants to use it independently, consider it a 
> > >>>> contribution to lift, and licensed the same way.
>
> > >>>> -Ross
>
> > >>>> On Jan 15, 2010, at 9:51 AM, Peter Robinett wrote:
>
> > >>>>> Ross, this looks nice. Imagine resizing code is something that I've
> > >>>>> personally had to do many times and is always annoying, so perhaps
> > >>>>> this would make a good Lift module? Anyway, this is probably best
> > >>>>> discussed on the main list...
>
> > >>>>> Peter
>
> > >>>>> On Jan 14, 3:01 am, Ross Mellgren <dri...@gmail.com> wrote:
> > >>>>>> Oh I nearly forgot I said on the conference call the other day that 
> > >>>>>> I'd send theimageresizecode we built at work, in case it would be 
> > >>>>>> helpful. Here it is:
>
> > >>>>>> import java.awt.{Graphics, RenderingHints, Transparency}
> > >>>>>> import java.awt.geom.AffineTransform
> > >>>>>> import java.awt.image.{AffineTransformOp, BufferedImage, ColorModel, 
> > >>>>>> IndexColorModel}
>
> > >>>>>> /**
> > >>>>>> * Helpers for manipulating images
> > >>>>>> */
> > >>>>>> object ImageHelpers
> > >>>>>> {
> > >>>>>> // Some code here omitted -- Ed.
>
> > >>>>>>   /** Rendering hints set up for the highest quality rendering */
> > >>>>>>   val highQualityHints = {
> > >>>>>>       val h = new RenderingHints(null)
> > >>>>>>       h.put(RenderingHints.KEY_ALPHA_INTERPOLATION, 
> > >>>>>> RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY)
> > >>>>>>       h.put(RenderingHints.KEY_COLOR_RENDERING, 
> > >>>>>> RenderingHints.VALUE_COLOR_RENDER_QUALITY)
> > >>>>>>       h.put(RenderingHints.KEY_INTERPOLATION, 
> > >>>>>> RenderingHints.VALUE_INTERPOLATION_BICUBIC)
> > >>>>>>       h.put(RenderingHints.KEY_ANTIALIASING, 
> > >>>>>> RenderingHints.VALUE_ANTIALIAS_ON)
> > >>>>>>       h.put(RenderingHints.KEY_RENDERING, 
> > >>>>>> RenderingHints.VALUE_RENDER_QUALITY)
> > >>>>>>       h
> > >>>>>>   }
>
> > >>>>>> // Some code here omitted -- Ed.
>
> > >>>>>>   /**
> > >>>>>>    *Resizeanimageof the given source type by the given ratios, 
> > >>>>>> properly handling GIF transparency, giving back the resized
> > >>>>>>    *imageand the newimageformat type that should be used.
> > >>>>>>    *
> > >>>>>>    * Theimagetype might change if the input type is an indexed color 
> > >>>>>> model, because it is a hard problem to choose an optimized
> > >>>>>>    * palette, and currently we don't. This function will return 
> > >>>>>> "png" as the new type in this case.
> > >>>>>>    *
> > >>>>>>    * If the inputimageis not using an indexed color model with 
> > >>>>>> transparency, then the target format and color model will be
> > >>>>>>    * identical to the source.
> > >>>>>>    */
> > >>>>>>   defresize(source: BufferedImage, inputFormat: String, dx: Double, 
> > >>>>>> dy: Double): (BufferedImage, String) = {
> > >>>>>>       var sourceColorModel = source.getColorModel
> > >>>>>>       val targetColorModel = source.getColorModel
> > >>>>>>       val standardColorModel = ColorModel.getRGBdefault
>
> > >>>>>>       val (targetWidth, targetHeight) = (((source.getWidth: Double) 
> > >>>>>> * dx).asInstanceOf[Int], ((source.getHeight: Double) * 
> > >>>>>> dy).asInstanceOf[Int])
>
> > >>>>>>       defresize(src: BufferedImage, dst: BufferedImage) {
> > >>>>>>           val g = dst.createGraphics
> > >>>>>>           try {
> > >>>>>>               g.setRenderingHints(highQualityHints)
> > >>>>>>               g.drawImage(src, new 
> > >>>>>> AffineTransformOp(AffineTransform.getScaleInstance(dx, dy), 
> > >>>>>> AffineTransformOp.TYPE_BICUBIC), 0, 0)
> > >>>>>>           } finally {
> > >>>>>>               g.dispose
> > >>>>>>           }
> > >>>>>>       }
>
> > >>>>>>       // GIF support in Java is very ornery. For GIFs we have to 
> > >>>>>> manually do the masking on input, and then just punt on outputting 
> > >>>>>> GIFs and instead output PNGs.
> > >>>>>>       if (sourceColorModel.isInstanceOf[IndexColorModel] &&
> > >>>>>>           sourceColorModel.hasAlpha &&
> > >>>>>>           sourceColorModel.getTransparency == Transparency.BITMASK &&
> > >>>>>>           
> > >>>>>> sourceColorModel.asInstanceOf[IndexColorModel].getTransparentPixel 
> > >>>>>> >= 0) {
>
> > >>>>>>           val indexColorModel = 
> > >>>>>> sourceColorModel.asInstanceOf[IndexColorModel]
> > >>>>>>           val transparent = 
> > >>>>>> indexColorModel.getRGB(indexColorModel.getTransparentPixel)
>
> > >>>>>>           val masked = new BufferedImage(standardColorModel, 
> > >>>>>> standardColorModel.createCompatibleWritableRaster(source.getWidth, 
> > >>>>>> source.getHeight), standardColorModel.isAlphaPremultiplied, null)
> > >>>>>>           var w = masked.getWidth
> > >>>>>>           var h = masked.getHeight
>
> > >>>>>>           val buf  = new Array[Int](w)
>
> > >>>>>>           var y = 0
> > >>>>>>           while (y < h) {
> > >>>>>>               source.getRGB(0, y, w, 1, buf,  0, 1)
>
> > >>>>>>               var x = 0
> > >>>>>>               while (x < w) {
> > >>>>>>                   val c = buf(x)
> > >>>>>>                   if (c == transparent) {
> > >>>>>>                       buf(x) = 0
> > >>>>>>                   }
> > >>>>>>                   x += 1
> > >>>>>>               }
>
> > >>>>>>               masked.setRGB(0, y, w, 1, buf, 0, 1)
> > >>>>>>               y += 1
> > >>>>>>           }
>
> > >>>>>>           val resized = new BufferedImage(standardColorModel, 
> > >>>>>> standardColorModel.createCompatibleWritableRaster(targetWidth, 
> > >>>>>> targetHeight), standardColorModel.isAlphaPremultiplied, null)
> > >>>>>>          resize(masked, resized)
> > >>>>>>           (resized, "png")
> > >>>>>>       } else if (sourceColorModel.isInstanceOf[IndexColorModel]) {
> > >>>>>>           // The input color model is indexed, and we know we won't 
> > >>>>>> be able to generate a tolerable palette to make another indexed 
> > >>>>>> color model, so use sRGB and upgrade to PNG.
> > >>>>>>           val resized = new BufferedImage(standardColorModel, 
> > >>>>>> standardColorModel.createCompatibleWritableRaster(targetWidth, 
> > >>>>>> targetHeight), standardColorModel.isAlphaPremultiplied, null)
> > >>>>>>          resize(source, resized)
> > >>>>>>           (resized, "png")
> > >>>>>>       } else {
> > >>>>>>           val resized = new BufferedImage(targetColorModel, 
> > >>>>>> targetColorModel.createCompatibleWritableRaster(targetWidth, 
> > >>>>>> targetHeight), targetColorModel.isAlphaPremultiplied, null)
> > >>>>>>          resize(source, resized)
> > >>>>>>           (resized, inputFormat)
> > >>>>>>       }
> > >>>>>>   }
>
> > >>>>>> }
>
> > >>>>>> It isn't perhaps the ideal implementation, as mentioned in some of 
> > >>>>>> the comments, but perhaps Jon or others might find it useful in 
> > >>>>>> whole or part.
>
> > >>>>>> -Ross
> > >>>>> --
> > >>>>> You received this message because you are subscribed to the Google 
> > >>>>> Groups "Lift-committers" group.
> > >>>>> To post to this group, send email to lift-committ...@googlegroups.com.
> > >>>>> To unsubscribe from this group, send email to 
> > >>>>> lift-committers+unsubscr...@googlegroups.com.
> > >>>>> For more options, visit this group 
> > >>>>> athttp://groups.google.com/group/lift-committers?hl=en.
>
> > >>>> --
> > >>>> You received this message because you are subscribed to the Google 
> > >>>> Groups "Lift" group.
> > >>>> To post to this group, send email to lift...@googlegroups.com.
> > >>>> To unsubscribe from this group, send email to 
> > >>>> liftweb+unsubscr...@googlegroups.com.
> > >>>> For more options, visit this group 
> > >>>> athttp://groups.google.com/group/liftweb?hl=en.
>
> > >>> --
> > >>> You received this message because you are subscribed to the Google 
> > >>> Groups "Lift" group.
> > >>> To post to this group, send email to lift...@googlegroups.com.
> > >>> To unsubscribe from this group, send email to
>
> ...
>
> read more »

-- 
You received this message because you are subscribed to the Google Groups 
"Lift" group.
To post to this group, send email to lift...@googlegroups.com.
To unsubscribe from this group, send email to 
liftweb+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/liftweb?hl=en.

Reply via email to