1 26 27 package org.nightlabs.editor2d.impl; 28 29 import java.awt.Rectangle ; 30 import java.awt.geom.AffineTransform ; 31 import java.awt.image.AffineTransformOp ; 32 import java.awt.image.BufferedImage ; 33 34 import org.nightlabs.editor2d.DrawComponent; 35 import org.nightlabs.editor2d.DrawComponentContainer; 36 import org.nightlabs.editor2d.ImageDrawComponent; 37 import org.nightlabs.editor2d.j2d.GeneralShape; 38 import org.nightlabs.editor2d.j2d.GeneralShapeFactory; 39 import org.nightlabs.editor2d.util.EditorModelUtil; 40 41 public class ImageDrawComponentImpl 42 extends DrawComponentImpl 43 implements ImageDrawComponent 44 { 45 47 protected static final BufferedImage IMAGE_EDEFAULT = null; 48 protected BufferedImage image = IMAGE_EDEFAULT; 49 50 public ImageDrawComponentImpl() { 51 super(); 52 } 53 54 57 public BufferedImage getImage() { 58 return image; 59 } 60 61 67 public void setImage(BufferedImage newImage) 68 { 69 BufferedImage oldImage = image; 70 primSetImage(newImage); 71 firePropertyChange(PROP_IMAGE, oldImage, image); 72 } 73 74 77 public GeneralShape getImageShape() { 78 return imageShape; 79 } 80 81 84 public void setImageShape(GeneralShape newImageShape) { 85 imageShape = newImageShape; 86 } 87 88 protected BufferedImage originalImage; 89 90 93 public BufferedImage getOriginalImage() { 94 return originalImage; 95 } 96 97 protected void primSetImage(BufferedImage newImage) 98 { 99 image = newImage; 100 originalImage = cloneImage(image); 101 bounds = null; 102 imageShape = GeneralShapeFactory.createRectangle(getBounds().x, getBounds().y, getBounds().width, getBounds().height); 103 } 104 105 public String toString() 106 { 107 StringBuffer result = new StringBuffer (super.toString()); 108 result.append(" (image: "); 109 result.append(image); 110 result.append(')'); 111 return result.toString(); 112 } 113 114 public Rectangle getBounds() 115 { 116 if (bounds == null) 117 { 118 if (image != null) 119 bounds = new Rectangle (x, y, image.getWidth(), image.getHeight()); 120 else 121 return super.getBounds(); 122 } 123 return bounds; 124 } 125 126 protected void primSetX(int x) 127 { 128 if (x == getBounds().x) 129 return; 130 131 bounds = null; 132 133 if (imageShape != null) { 134 atUtil.setToIdentity(); 135 atUtil.translate(x - getBounds().x, 0); 136 imageShape.transform(atUtil); 137 } 139 } 140 141 protected void primSetY(int y) 142 { 143 if (y == getBounds().y) 144 return; 145 146 bounds = null; 147 148 if (imageShape != null) { 149 atUtil.setToIdentity(); 150 atUtil.translate(0, y - getBounds().y); 151 imageShape.transform(atUtil); 152 } 154 } 155 156 protected void primSetLocation(int newX, int newY, boolean transformRotationCenter) 157 { 158 if (imageShape != null) 159 { 160 x = newX; 161 y = newY; 162 atUtil.setToIdentity(); 163 atUtil.translate((float)newX - (float)getX(), (float)newY - (float)getY()); 164 165 if (transformRotationCenter) 166 transformRotationCenter(atUtil); 167 168 imageShape.transform(atUtil); 169 } 170 bounds = null; 171 } 172 173 public void setLocation(int newX, int newY) 174 { 175 primSetLocation(newX, newY, true); 176 } 177 178 protected void setSize(int newWidth, int newHeight) 179 { 180 atUtil.setToIdentity(); 181 float ratioY = (float)newHeight / (float)getHeight(); 182 ratioY = EditorModelUtil.checkFactor(ratioY); 183 float ratioX = (float)newWidth / (float)getWidth(); 184 ratioX = EditorModelUtil.checkFactor(ratioX); 185 atUtil.scale(ratioX, ratioY); 186 187 transformRotationCenter(atUtil); 188 transform(atUtil); 189 } 190 191 255 protected void primSetRotation(double newRotation) 256 { 257 double oldRotation = rotation; 258 rotation = EditorModelUtil.getConstrainedValue(newRotation, rotationLimit); 259 260 if (oldRotation == newRotation) 261 return; 262 263 double degreesToRotate = EditorModelUtil.calcDiffRotation(rotation, oldRotation); 264 double degreesToRotateInRadians = Math.toRadians(degreesToRotate); 265 266 if (degreesToRotate != 0) 267 { 268 if (imageShape != null && originalImage != null) 269 { 270 Rectangle imageShapeBounds = imageShape.getBounds(); 271 int sx = imageShapeBounds.width; 272 int sy = imageShapeBounds.height; 273 atUtil.setToIdentity(); 274 atUtil.rotate(degreesToRotateInRadians, getRotationX(), getRotationY()); 275 Rectangle shapeBounds = getTransformedShapeBounds(atUtil); 276 int dx = shapeBounds.width; 277 int dy = shapeBounds.height; 278 279 atUtil.setToIdentity(); 281 atUtil.setToTranslation(dx / 2, dy / 2); 282 atUtil.rotate(degreesToRotateInRadians); 283 atUtil.translate(-sx / 2, -sy / 2); 284 285 BufferedImage dest = new BufferedImage (dx, dy, BufferedImage.TYPE_INT_ARGB); 286 affineTransform.preConcatenate(atUtil); 287 AffineTransformOp op = new AffineTransformOp (affineTransform, interpolationType); 288 image = op.filter(originalImage, dest); 289 dest = null; 290 bounds = null; 291 292 int diffX = (dx - sx) / 2; 294 int diffY = (dy - sy) / 2; 295 296 primSetLocation(getX()-diffX, getY()-diffY, false); 297 } 298 } 299 } 300 301 protected AffineTransformOp op; 302 protected int interpolationType = AffineTransformOp.TYPE_BILINEAR; 303 public void transform(AffineTransform newAT) 304 { 305 affineTransform.preConcatenate(newAT); 306 op = new AffineTransformOp (affineTransform, interpolationType); 307 if (image != null) { 308 Rectangle shapeBounds = getTransformedShapeBounds(newAT); 309 BufferedImage bi = createCompatibleImage(affineTransform, shapeBounds.width, shapeBounds.height); 310 image = op.filter(originalImage, bi); 311 } 312 if (getParent() != null) 313 getParent().notifyChildTransform(this); 314 } 315 316 324 protected BufferedImage createCompatibleImage(AffineTransform at, int width, int height) 325 { 326 return new BufferedImage (width, height, BufferedImage.TYPE_INT_ARGB); 327 } 328 329 protected GeneralShape imageShape; 330 protected Rectangle getTransformedShapeBounds(AffineTransform at) 331 { 332 imageShape.transform(at); 333 return imageShape.getBounds(); 334 } 335 336 protected BufferedImage cloneImage(BufferedImage src) { 337 return src.getSubimage(0, 0, src.getWidth(), src.getHeight()); 338 } 339 340 public Class getRenderModeClass() { 341 return ImageDrawComponent.class; 342 } 343 344 public String getTypeName() { 345 return "Image"; 346 } 347 348 358 public Object clone(DrawComponentContainer parent) 359 { 360 ImageDrawComponentImpl imageDC = (ImageDrawComponentImpl) super.clone(parent); 361 imageDC.image = cloneImage(this.image); 362 imageDC.imageShape = (GeneralShape) this.imageShape.clone(); 363 imageDC.op = new AffineTransformOp (op.getTransform(), interpolationType); 364 imageDC.originalImage = cloneImage(this.originalImage); 365 imageDC.interpolationType = interpolationType; 366 return imageDC; 367 } 368 369 } | Popular Tags |