~ubuntu-branches/ubuntu/oneiric/moin/oneiric-security

« back to all changes in this revision

Viewing changes to MoinMoin/web/static/htdocs/applets/FCKeditor/editor/filemanager/connectors/cfm/image.cfc

  • Committer: Bazaar Package Importer
  • Author(s): Jamie Strandboge
  • Date: 2010-03-30 12:55:34 UTC
  • mfrom: (0.1.17 sid)
  • Revision ID: james.westby@ubuntu.com-20100330125534-4c2ufc1rok24447l
Tags: 1.9.2-2ubuntu1
* Merge from Debian testing (LP: #521834). Based on work by Stefan Ebner.
  Remaining changes:
 - Remove python-xml from Suggests field, the package isn't anymore in
   sys.path.
 - Demote fckeditor from Recommends to Suggests; the code was previously
   embedded in moin, but it was also disabled, so there's no reason for us
   to pull this in by default currently. Note: This isn't necessary anymore
   but needs a MIR for fckeditor, so postpone dropping this change until
   lucid+1
* debian/rules:
  - Replace hardcoded python2.5 with python* and hardcore python2.6 for ln
* debian/control.in: drop versioned depends on cdbs

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
<!---
 
2
        image.cfc v2.19, written by Rick Root (rick@webworksllc.com)
 
3
        Derivative of work originally done originally by James Dew.
 
4
 
 
5
        Related Web Sites:
 
6
        - http://www.opensourcecf.com/imagecfc (home page)
 
7
        - http://www.cfopen.org/projects/imagecfc (project page)
 
8
 
 
9
        LICENSE
 
10
        -------
 
11
        Copyright (c) 2007, Rick Root <rick@webworksllc.com>
 
12
        All rights reserved.
 
13
 
 
14
        Redistribution and use in source and binary forms, with or
 
15
        without modification, are permitted provided that the
 
16
        following conditions are met:
 
17
 
 
18
        - Redistributions of source code must retain the above
 
19
          copyright notice, this list of conditions and the
 
20
          following disclaimer.
 
21
        - Redistributions in binary form must reproduce the above
 
22
          copyright notice, this list of conditions and the
 
23
          following disclaimer in the documentation and/or other
 
24
          materials provided with the distribution.
 
25
        - Neither the name of the Webworks, LLC. nor the names of
 
26
          its contributors may be used to endorse or promote products
 
27
          derived from this software without specific prior written
 
28
          permission.
 
29
 
 
30
        THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
 
31
        CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
 
32
        INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 
33
        MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 
34
        DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
 
35
        CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 
36
        SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
 
37
        BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 
38
        LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 
39
        HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 
40
        CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
 
41
        OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 
42
        SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
43
 
 
44
        ============================================================
 
45
        This is a derivative work.  Following is the original
 
46
        Copyright notice.
 
47
        ============================================================
 
48
 
 
49
        Copyright (c) 2004 James F. Dew <jdew@yggdrasil.ca>
 
50
 
 
51
        Permission to use, copy, modify, and distribute this software for any
 
52
        purpose with or without fee is hereby granted, provided that the above
 
53
        copyright notice and this permission notice appear in all copies.
 
54
 
 
55
        THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 
56
        WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 
57
        MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 
58
        ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 
59
        WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 
60
        ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 
61
        OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 
62
--->
 
63
<!---
 
64
        SPECIAL NOTE FOR HEADLESS SYSTEMS
 
65
        ---------------------------------
 
66
        If you get a "cannot connect to X11 server" when running certain
 
67
        parts of this component under Bluedragon (Linux), you must
 
68
        add "-Djava.awt.headless=true" to the java startup line in
 
69
        <bluedragon>/bin/StartBluedragon.sh.  This isssue is discussed
 
70
        in the Bluedragon Installation Guide section 3.8.1 for
 
71
        Bluedragon 6.2.1.
 
72
 
 
73
        Bluedragon may also report a ClassNotFound exception when trying
 
74
        to instantiate the java.awt.image.BufferedImage class.  This is
 
75
        most likely the same issue.
 
76
 
 
77
        If you get "This graphics environment can be used only in the
 
78
        software emulation mode" when calling certain parts of this
 
79
        component under Coldfusion MX, you should refer to Technote
 
80
        ID #18747:  http://www.macromedia.com/go/tn_18747
 
81
--->
 
82
 
 
83
<cfcomponent displayname="Image">
 
84
 
 
85
<cfset variables.throwOnError = "Yes">
 
86
<cfset variables.defaultJpegCompression = "90">
 
87
<cfset variables.interpolation = "bicubic">
 
88
<cfset variables.textAntiAliasing = "Yes">
 
89
<cfset variables.tempDirectory = "#expandPath(".")#">
 
90
 
 
91
<cfset variables.javanulls = "no">
 
92
<cftry>
 
93
        <cfset nullvalue = javacast("null","")>
 
94
        <cfset variables.javanulls = "yes">
 
95
        <cfcatch type="any">
 
96
                <cfset variables.javanulls = "no">
 
97
                <!--- javacast null not supported, so filters won't work --->
 
98
        </cfcatch>
 
99
</cftry>
 
100
<!---
 
101
<cfif javanulls>
 
102
        <cfset variables.blurFilter = createObject("component","blurFilter")>
 
103
        <cfset variables.sharpenFilter = createObject("component","sharpenFilter")>
 
104
        <cfset variables.posterizeFilter = createObject("component","posterizeFilter")>
 
105
</cfif>
 
106
--->
 
107
 
 
108
<cfset variables.Math = createobject("java", "java.lang.Math")>
 
109
<cfset variables.arrObj = createobject("java", "java.lang.reflect.Array")>
 
110
<cfset variables.floatClass = createobject("java", "java.lang.Float").TYPE>
 
111
<cfset variables.intClass = createobject("java", "java.lang.Integer").TYPE>
 
112
<cfset variables.shortClass = createobject("java", "java.lang.Short").TYPE>
 
113
 
 
114
<cffunction name="getImageInfo" access="public" output="true" returntype="struct" hint="Rotate an image (+/-)90, (+/-)180, or (+/-)270 degrees.">
 
115
        <cfargument name="objImage" required="yes" type="Any">
 
116
        <cfargument name="inputFile" required="yes" type="string">
 
117
 
 
118
        <cfset var retVal = StructNew()>
 
119
        <cfset var loadImage = StructNew()>
 
120
        <cfset var img = "">
 
121
 
 
122
        <cfset retVal.errorCode = 0>
 
123
        <cfset retVal.errorMessage = "">
 
124
 
 
125
        <cfif inputFile neq "">
 
126
                <cfset loadImage = readImage(inputFile, "NO")>
 
127
                <cfif loadImage.errorCode is 0>
 
128
                        <cfset img = loadImage.img>
 
129
                <cfelse>
 
130
                        <cfset retVal = throw(loadImage.errorMessage)>
 
131
                        <cfreturn retVal>
 
132
                </cfif>
 
133
                <cfset retVal.metaData = getImageMetadata(loadImage.inFile)>
 
134
        <cfelse>
 
135
                <cfset img = objImage>
 
136
                <cfset retVal.metadata = getImageMetadata("")>
 
137
        </cfif>
 
138
        <cftry>
 
139
                <cfset retVal.width = img.getWidth()>
 
140
                <cfset retVal.height = img.getHeight()>
 
141
                <cfset retVal.colorModel = img.getColorModel().toString()>
 
142
                <cfset retVal.colorspace = img.getColorModel().getColorSpace().toString()>
 
143
                <cfset retVal.objColorModel = img.getColorModel()>
 
144
                <cfset retVal.objColorspace = img.getColorModel().getColorSpace()>
 
145
                <cfset retVal.sampleModel = img.getSampleModel().toString()>
 
146
                <cfset retVal.imageType = img.getType()>
 
147
                <cfset retVal.misc = img.toString()>
 
148
                <cfset retVal.canModify = true>
 
149
                <cfreturn retVal>
 
150
                <cfcatch type="any">
 
151
                        <cfset retVal = throw( "#cfcatch.message#: #cfcatch.detail#")>
 
152
                        <cfreturn retVal>
 
153
                </cfcatch>
 
154
        </cftry>
 
155
</cffunction>
 
156
 
 
157
<cffunction name="getImageMetadata" access="private" output="false" returntype="query">
 
158
        <cfargument name="inFile" required="yes" type="Any"><!--- java.io.File --->
 
159
 
 
160
        <cfset var retQry = queryNew("dirName,tagName,tagValue")>
 
161
        <cfset var paths = arrayNew(1)>
 
162
        <cfset var loader = "">
 
163
        <cfset var JpegMetadatareader = "">
 
164
        <cfset var myMetadata = "">
 
165
        <cfset var directories = "">
 
166
        <cfset var currentDirectory = "">
 
167
        <cfset var tags = "">
 
168
        <cfset var currentTag = "">
 
169
        <cfset var tagName = "">
 
170
 
 
171
        <cftry>
 
172
        <cfscript>
 
173
                paths = arrayNew(1);
 
174
                paths[1] = expandPath("metadata-extractor-2.3.1.jar");
 
175
                loader = createObject("component", "javaloader.JavaLoader").init(paths);
 
176
 
 
177
                //at this stage we only have access to the class, but we don't have an instance
 
178
                JpegMetadataReader = loader.create("com.drew.imaging.jpeg.JpegMetadataReader");
 
179
 
 
180
                myMetaData = JpegMetadataReader.readMetadata(inFile);
 
181
                directories = myMetaData.getDirectoryIterator();
 
182
                while (directories.hasNext()) {
 
183
                        currentDirectory = directories.next();
 
184
                        tags = currentDirectory.getTagIterator();
 
185
                        while (tags.hasNext()) {
 
186
                                currentTag = tags.next();
 
187
                                if (currentTag.getTagName() DOES NOT CONTAIN "Unknown") { //leave out the junk data
 
188
                                        queryAddRow(retQry);
 
189
                                        querySetCell(retQry,"dirName",replace(currentTag.getDirectoryName(),' ','_','ALL'));
 
190
                                        tagName = replace(currentTag.getTagName(),' ','','ALL');
 
191
                                        tagName = replace(tagName,'/','','ALL');
 
192
                                        querySetCell(retQry,"tagName",tagName);
 
193
                                        querySetCell(retQry,"tagValue",currentTag.getDescription());
 
194
                                }
 
195
                        }
 
196
                }
 
197
                return retQry;
 
198
                </cfscript>
 
199
                <cfcatch type="any">
 
200
                        <cfreturn retQry />
 
201
                </cfcatch>
 
202
        </cftry>
 
203
</cffunction>
 
204
 
 
205
<cffunction name="flipHorizontal" access="public" output="true" returntype="struct" hint="Flip an image horizontally.">
 
206
        <cfargument name="objImage" required="yes" type="Any">
 
207
        <cfargument name="inputFile" required="yes" type="string">
 
208
        <cfargument name="outputFile" required="yes" type="string">
 
209
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
210
 
 
211
        <cfreturn flipflop(objImage, inputFile, outputFile, "horizontal", jpegCompression)>
 
212
</cffunction>
 
213
 
 
214
<cffunction name="flipVertical" access="public" output="true" returntype="struct" hint="Flop an image vertically.">
 
215
        <cfargument name="objImage" required="yes" type="Any">
 
216
        <cfargument name="inputFile" required="yes" type="string">
 
217
        <cfargument name="outputFile" required="yes" type="string">
 
218
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
219
 
 
220
        <cfreturn flipflop(objImage, inputFile, outputFile, "vertical", jpegCompression)>
 
221
</cffunction>
 
222
 
 
223
<cffunction name="scaleWidth" access="public" output="true" returntype="struct" hint="Scale an image to a specific width.">
 
224
        <cfargument name="objImage" required="yes" type="Any">
 
225
        <cfargument name="inputFile" required="yes" type="string">
 
226
        <cfargument name="outputFile" required="yes" type="string">
 
227
        <cfargument name="newWidth" required="yes" type="numeric">
 
228
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
229
 
 
230
        <cfreturn resize(objImage, inputFile, outputFile, newWidth, 0, "false", "false", jpegCompression)>
 
231
</cffunction>
 
232
 
 
233
<cffunction name="scaleHeight" access="public" output="true" returntype="struct" hint="Scale an image to a specific height.">
 
234
        <cfargument name="objImage" required="yes" type="Any">
 
235
        <cfargument name="inputFile" required="yes" type="string">
 
236
        <cfargument name="outputFile" required="yes" type="string">
 
237
        <cfargument name="newHeight" required="yes" type="numeric">
 
238
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
239
 
 
240
        <cfreturn resize(objImage, inputFile, outputFile, 0, newHeight, "false", "false", jpegCompression)>
 
241
</cffunction>
 
242
 
 
243
<cffunction name="resize" access="public" output="true" returntype="struct" hint="Resize an image to a specific width and height.">
 
244
        <cfargument name="objImage" required="yes" type="Any">
 
245
        <cfargument name="inputFile" required="yes" type="string">
 
246
        <cfargument name="outputFile" required="yes" type="string">
 
247
        <cfargument name="newWidth" required="yes" type="numeric">
 
248
        <cfargument name="newHeight" required="yes" type="numeric">
 
249
        <cfargument name="preserveAspect" required="no" type="boolean" default="FALSE">
 
250
        <cfargument name="cropToExact" required="no" type="boolean" default="FALSE">
 
251
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
252
 
 
253
        <cfset var retVal = StructNew()>
 
254
        <cfset var loadImage = StructNew()>
 
255
        <cfset var saveImage = StructNew()>
 
256
        <cfset var at = "">
 
257
        <cfset var op = "">
 
258
        <cfset var w = "">
 
259
        <cfset var h = "">
 
260
        <cfset var scale = 1>
 
261
        <cfset var scaleX = 1>
 
262
        <cfset var scaleY = 1>
 
263
        <cfset var resizedImage = "">
 
264
        <cfset var rh = getRenderingHints()>
 
265
        <cfset var specifiedWidth = arguments.newWidth>
 
266
        <cfset var specifiedHeight = arguments.newHeight>
 
267
        <cfset var imgInfo = "">
 
268
        <cfset var img = "">
 
269
        <cfset var cropImageResult = "">
 
270
        <cfset var cropOffsetX = "">
 
271
        <cfset var cropOffsetY = "">
 
272
 
 
273
        <cfset retVal.errorCode = 0>
 
274
        <cfset retVal.errorMessage = "">
 
275
 
 
276
        <cfif inputFile neq "">
 
277
                <cfset loadImage = readImage(inputFile, "NO")>
 
278
                <cfif loadImage.errorCode is 0>
 
279
                        <cfset img = loadImage.img>
 
280
                <cfelse>
 
281
                        <cfset retVal = throw(loadImage.errorMessage)>
 
282
                        <cfreturn retVal>
 
283
                </cfif>
 
284
        <cfelse>
 
285
                <cfset img = objImage>
 
286
        </cfif>
 
287
        <cfif img.getType() eq 0>
 
288
                <cfset img = convertImageObject(img,img.TYPE_3BYTE_BGR)>
 
289
        </cfif>
 
290
        <cfscript>
 
291
                resizedImage = CreateObject("java", "java.awt.image.BufferedImage");
 
292
                at = CreateObject("java", "java.awt.geom.AffineTransform");
 
293
                op = CreateObject("java", "java.awt.image.AffineTransformOp");
 
294
 
 
295
                w = img.getWidth();
 
296
                h = img.getHeight();
 
297
 
 
298
                if (preserveAspect and cropToExact and newHeight gt 0 and newWidth gt 0)
 
299
                {
 
300
                        if (w / h gt newWidth / newHeight){
 
301
                                newWidth = 0;
 
302
                        } else if (w / h lt newWidth / newHeight){
 
303
                                newHeight = 0;
 
304
                    }
 
305
                } else if (preserveAspect and newHeight gt 0 and newWidth gt 0) {
 
306
                        if (w / h gt newWidth / newHeight){
 
307
                                newHeight = 0;
 
308
                        } else if (w / h lt newWidth / newHeight){
 
309
                                newWidth = 0;
 
310
                    }
 
311
                }
 
312
                if (newWidth gt 0 and newHeight eq 0) {
 
313
                        scale = newWidth / w;
 
314
                        w = newWidth;
 
315
                        h = round(h*scale);
 
316
                } else if (newHeight gt 0 and newWidth eq 0) {
 
317
                        scale = newHeight / h;
 
318
                        h = newHeight;
 
319
                        w = round(w*scale);
 
320
                } else if (newHeight gt 0 and newWidth gt 0) {
 
321
                        w = newWidth;
 
322
                        h = newHeight;
 
323
                } else {
 
324
                        retVal = throw( retVal.errorMessage);
 
325
                        return retVal;
 
326
                }
 
327
                resizedImage.init(javacast("int",w),javacast("int",h),img.getType());
 
328
 
 
329
                w = w / img.getWidth();
 
330
                h = h / img.getHeight();
 
331
 
 
332
 
 
333
 
 
334
                op.init(at.getScaleInstance(javacast("double",w),javacast("double",h)), rh);
 
335
                // resizedImage = op.createCompatibleDestImage(img, img.getColorModel());
 
336
                op.filter(img, resizedImage);
 
337
 
 
338
                imgInfo = getimageinfo(resizedImage, "");
 
339
                if (imgInfo.errorCode gt 0)
 
340
                {
 
341
                        return imgInfo;
 
342
                }
 
343
 
 
344
                cropOffsetX = max( Int( (imgInfo.width/2) - (newWidth/2) ), 0 );
 
345
                cropOffsetY = max( Int( (imgInfo.height/2) - (newHeight/2) ), 0 );
 
346
                // There is a chance that the image is exactly the correct
 
347
                // width and height and don't need to be cropped
 
348
                if
 
349
                        (
 
350
                        preserveAspect and cropToExact
 
351
                        and
 
352
                        (imgInfo.width IS NOT specifiedWidth OR imgInfo.height IS NOT specifiedHeight)
 
353
                        )
 
354
                {
 
355
                        // Get the correct offset to get the center of the image
 
356
                        cropOffsetX = max( Int( (imgInfo.width/2) - (specifiedWidth/2) ), 0 );
 
357
                        cropOffsetY = max( Int( (imgInfo.height/2) - (specifiedHeight/2) ), 0 );
 
358
 
 
359
                        cropImageResult = crop( resizedImage, "", "", cropOffsetX, cropOffsetY, specifiedWidth, specifiedHeight );
 
360
                        if ( cropImageResult.errorCode GT 0)
 
361
                        {
 
362
                                return cropImageResult;
 
363
                        } else {
 
364
                                resizedImage = cropImageResult.img;
 
365
                        }
 
366
                }
 
367
                if (outputFile eq "")
 
368
                {
 
369
                        retVal.img = resizedImage;
 
370
                        return retVal;
 
371
                } else {
 
372
                        saveImage = writeImage(outputFile, resizedImage, jpegCompression);
 
373
                        if (saveImage.errorCode gt 0)
 
374
                        {
 
375
                                return saveImage;
 
376
                        } else {
 
377
                                return retVal;
 
378
                        }
 
379
                }
 
380
        </cfscript>
 
381
</cffunction>
 
382
 
 
383
<cffunction name="crop" access="public" output="true" returntype="struct" hint="Crop an image.">
 
384
        <cfargument name="objImage" required="yes" type="Any">
 
385
        <cfargument name="inputFile" required="yes" type="string">
 
386
        <cfargument name="outputFile" required="yes" type="string">
 
387
        <cfargument name="fromX" required="yes" type="numeric">
 
388
        <cfargument name="fromY" required="yes" type="numeric">
 
389
        <cfargument name="newWidth" required="yes" type="numeric">
 
390
        <cfargument name="newHeight" required="yes" type="numeric">
 
391
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
392
 
 
393
        <cfset var retVal = StructNew()>
 
394
        <cfset var loadImage = StructNew()>
 
395
        <cfset var saveImage = StructNew()>
 
396
        <cfset var croppedImage = "">
 
397
        <cfset var rh = getRenderingHints()>
 
398
        <cfset var img = "">
 
399
 
 
400
        <cfset retVal.errorCode = 0>
 
401
        <cfset retVal.errorMessage = "">
 
402
 
 
403
        <cfif inputFile neq "">
 
404
                <cfset loadImage = readImage(inputFile, "NO")>
 
405
                <cfif loadImage.errorCode is 0>
 
406
                        <cfset img = loadImage.img>
 
407
                <cfelse>
 
408
                        <cfset retVal = throw(loadImage.errorMessage)>
 
409
                        <cfreturn retVal>
 
410
                </cfif>
 
411
        <cfelse>
 
412
                <cfset img = objImage>
 
413
        </cfif>
 
414
        <cfif img.getType() eq 0>
 
415
                <cfset img = convertImageObject(img,img.TYPE_3BYTE_BGR)>
 
416
        </cfif>
 
417
        <cfscript>
 
418
                if (fromX + newWidth gt img.getWidth()
 
419
                        OR
 
420
                        fromY + newHeight gt img.getHeight()
 
421
                        )
 
422
                {
 
423
                        retval = throw( "The cropped image dimensions go beyond the original image dimensions.");
 
424
                        return retVal;
 
425
                }
 
426
                croppedImage = img.getSubimage(javaCast("int", fromX), javaCast("int", fromY), javaCast("int", newWidth), javaCast("int", newHeight) );
 
427
                if (outputFile eq "")
 
428
                {
 
429
                        retVal.img = croppedImage;
 
430
                        return retVal;
 
431
                } else {
 
432
                        saveImage = writeImage(outputFile, croppedImage, jpegCompression);
 
433
                        if (saveImage.errorCode gt 0)
 
434
                        {
 
435
                                return saveImage;
 
436
                        } else {
 
437
                                return retVal;
 
438
                        }
 
439
                }
 
440
        </cfscript>
 
441
</cffunction>
 
442
 
 
443
<cffunction name="rotate" access="public" output="true" returntype="struct" hint="Rotate an image (+/-)90, (+/-)180, or (+/-)270 degrees.">
 
444
        <cfargument name="objImage" required="yes" type="Any">
 
445
        <cfargument name="inputFile" required="yes" type="string">
 
446
        <cfargument name="outputFile" required="yes" type="string">
 
447
        <cfargument name="degrees" required="yes" type="numeric">
 
448
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
449
 
 
450
        <cfset var retVal = StructNew()>
 
451
        <cfset var img = "">
 
452
        <cfset var loadImage = StructNew()>
 
453
        <cfset var saveImage = StructNew()>
 
454
        <cfset var at = "">
 
455
        <cfset var op = "">
 
456
        <cfset var w = 0>
 
457
        <cfset var h = 0>
 
458
        <cfset var iw = 0>
 
459
        <cfset var ih = 0>
 
460
        <cfset var x = 0>
 
461
        <cfset var y = 0>
 
462
        <cfset var rotatedImage = "">
 
463
        <cfset var rh = getRenderingHints()>
 
464
 
 
465
        <cfset retVal.errorCode = 0>
 
466
        <cfset retVal.errorMessage = "">
 
467
 
 
468
        <cfif inputFile neq "">
 
469
                <cfset loadImage = readImage(inputFile, "NO")>
 
470
                <cfif loadImage.errorCode is 0>
 
471
                        <cfset img = loadImage.img>
 
472
                <cfelse>
 
473
                        <cfset retVal = throw(loadImage.errorMessage)>
 
474
                        <cfreturn retVal>
 
475
                </cfif>
 
476
        <cfelse>
 
477
                <cfset img = objImage>
 
478
        </cfif>
 
479
        <cfif img.getType() eq 0>
 
480
                <cfset img = convertImageObject(img,img.TYPE_3BYTE_BGR)>
 
481
        </cfif>
 
482
        <cfif ListFind("-270,-180,-90,90,180,270",degrees) is 0>
 
483
                <cfset retVal = throw( "At this time, image.cfc only supports rotating images in 90 degree increments.")>
 
484
                <cfreturn retVal>
 
485
        </cfif>
 
486
 
 
487
        <cfscript>
 
488
                rotatedImage = CreateObject("java", "java.awt.image.BufferedImage");
 
489
                at = CreateObject("java", "java.awt.geom.AffineTransform");
 
490
                op = CreateObject("java", "java.awt.image.AffineTransformOp");
 
491
 
 
492
                iw = img.getWidth(); h = iw;
 
493
                ih = img.getHeight(); w = ih;
 
494
 
 
495
                if(arguments.degrees eq 180) { w = iw; h = ih; }
 
496
 
 
497
                x = (w/2)-(iw/2);
 
498
                y = (h/2)-(ih/2);
 
499
 
 
500
                rotatedImage.init(javacast("int",w),javacast("int",h),img.getType());
 
501
 
 
502
                at.rotate(arguments.degrees * 0.0174532925,w/2,h/2);
 
503
                at.translate(x,y);
 
504
                op.init(at, rh);
 
505
 
 
506
                op.filter(img, rotatedImage);
 
507
 
 
508
                if (outputFile eq "")
 
509
                {
 
510
                        retVal.img = rotatedImage;
 
511
                        return retVal;
 
512
                } else {
 
513
                        saveImage = writeImage(outputFile, rotatedImage, jpegCompression);
 
514
                        if (saveImage.errorCode gt 0)
 
515
                        {
 
516
                                return saveImage;
 
517
                        } else {
 
518
                                return retVal;
 
519
                        }
 
520
                }
 
521
        </cfscript>
 
522
</cffunction>
 
523
 
 
524
<cffunction name="convert" access="public" output="true" returntype="struct" hint="Convert an image from one format to another.">
 
525
        <cfargument name="objImage" required="yes" type="Any">
 
526
        <cfargument name="inputFile" required="yes" type="string">
 
527
        <cfargument name="outputFile" required="yes" type="string">
 
528
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
529
 
 
530
        <cfset var retVal = StructNew()>
 
531
        <cfset var loadImage = StructNew()>
 
532
        <cfset var saveImage = StructNew()>
 
533
        <cfset var img = "">
 
534
 
 
535
        <cfset retVal.errorCode = 0>
 
536
        <cfset retVal.errorMessage = "">
 
537
 
 
538
        <cfif inputFile neq "">
 
539
                <cfset loadImage = readImage(inputFile, "NO")>
 
540
                <cfif loadImage.errorCode is 0>
 
541
                        <cfset img = loadImage.img>
 
542
                <cfelse>
 
543
                        <cfset retVal = throw(loadImage.errorMessage)>
 
544
                        <cfreturn retVal>
 
545
                </cfif>
 
546
        <cfelse>
 
547
                <cfset img = objImage>
 
548
        </cfif>
 
549
 
 
550
        <cfscript>
 
551
                if (outputFile eq "")
 
552
                {
 
553
                        retVal = throw( "The convert method requires a valid output filename.");
 
554
                        return retVal;
 
555
                } else {
 
556
                        saveImage = writeImage(outputFile, img, jpegCompression);
 
557
                        if (saveImage.errorCode gt 0)
 
558
                        {
 
559
                                return saveImage;
 
560
                        } else {
 
561
                                return retVal;
 
562
                        }
 
563
                }
 
564
        </cfscript>
 
565
</cffunction>
 
566
 
 
567
<cffunction name="setOption" access="public" output="true" returnType="void" hint="Sets values for allowed CFC options.">
 
568
        <cfargument name="key" type="string" required="yes">
 
569
        <cfargument name="val" type="string" required="yes">
 
570
 
 
571
        <cfset var validKeys = "interpolation,textantialiasing,throwonerror,defaultJpegCompression">
 
572
        <cfset arguments.key = lcase(trim(arguments.key))>
 
573
        <cfset arguments.val = lcase(trim(arguments.val))>
 
574
        <cfif listFind(validKeys, arguments.key) gt 0>
 
575
                <cfset variables[arguments.key] = arguments.val>
 
576
        </cfif>
 
577
</cffunction>
 
578
 
 
579
<cffunction name="getOption" access="public" output="true" returnType="any" hint="Returns the current value for the specified CFC option.">
 
580
        <cfargument name="key" type="string" required="yes">
 
581
 
 
582
        <cfset var validKeys = "interpolation,textantialiasing,throwonerror,defaultJpegCompression">
 
583
        <cfset arguments.key = lcase(trim(arguments.key))>
 
584
        <cfif listFindNoCase(validKeys, arguments.key) gt 0>
 
585
                <cfreturn variables[arguments.key]>
 
586
        <cfelse>
 
587
                <cfreturn "">
 
588
        </cfif>
 
589
</cffunction>
 
590
 
 
591
<cffunction name="getRenderingHints" access="private" output="true" returnType="any" hint="Internal method controls various aspects of rendering quality.">
 
592
        <cfset var rh = CreateObject("java","java.awt.RenderingHints")>
 
593
        <cfset var initMap = CreateObject("java","java.util.HashMap")>
 
594
        <cfset initMap.init()>
 
595
        <cfset rh.init(initMap)>
 
596
        <cfset rh.put(rh.KEY_ALPHA_INTERPOLATION, rh.VALUE_ALPHA_INTERPOLATION_QUALITY)> <!--- QUALITY, SPEED, DEFAULT --->
 
597
        <cfset rh.put(rh.KEY_ANTIALIASING, rh.VALUE_ANTIALIAS_ON)> <!--- ON, OFF, DEFAULT --->
 
598
        <cfset rh.put(rh.KEY_COLOR_RENDERING, rh.VALUE_COLOR_RENDER_QUALITY)>  <!--- QUALITY, SPEED, DEFAULT --->
 
599
        <cfset rh.put(rh.KEY_DITHERING, rh.VALUE_DITHER_DEFAULT)> <!--- DISABLE, ENABLE, DEFAULT --->
 
600
        <cfset rh.put(rh.KEY_RENDERING, rh.VALUE_RENDER_QUALITY)> <!--- QUALITY, SPEED, DEFAULT --->
 
601
        <cfset rh.put(rh.KEY_FRACTIONALMETRICS, rh.VALUE_FRACTIONALMETRICS_DEFAULT)> <!--- DISABLE, ENABLE, DEFAULT --->
 
602
        <cfset rh.put(rh.KEY_STROKE_CONTROL, rh.VALUE_STROKE_DEFAULT)>
 
603
 
 
604
        <cfif variables.textAntiAliasing>
 
605
                <cfset rh.put(rh.KEY_TEXT_ANTIALIASING, rh.VALUE_TEXT_ANTIALIAS_ON)>
 
606
        <cfelse>
 
607
                <cfset rh.put(rh.KEY_TEXT_ANTIALIASING, rh.VALUE_TEXT_ANTIALIAS_OFF)>
 
608
        </cfif>
 
609
 
 
610
        <cfif variables.interpolation eq "nearest_neighbor">
 
611
                <cfset rh.put(rh.KEY_INTERPOLATION, rh.VALUE_INTERPOLATION_NEAREST_NEIGHBOR)>
 
612
        <cfelseif variables.interpolation eq "bilinear">
 
613
                <cfset rh.put(rh.KEY_INTERPOLATION, rh.VALUE_INTERPOLATION_BILINEAR)>
 
614
        <cfelse>
 
615
                <cfset rh.put(rh.KEY_INTERPOLATION, rh.VALUE_INTERPOLATION_BICUBIC)>
 
616
        </cfif>
 
617
 
 
618
        <cfreturn rh>
 
619
</cffunction>
 
620
 
 
621
<cffunction name="readImage" access="public" output="true" returntype="struct" hint="Reads an image from a local file.  Requires an absolute path.">
 
622
        <cfargument name="source" required="yes" type="string">
 
623
        <cfargument name="forModification" required="no" type="boolean" default="yes">
 
624
 
 
625
        <cfif isURL(source)>
 
626
                <cfreturn readImageFromURL(source, forModification)>
 
627
        <cfelse>
 
628
                <cfreturn readImageFromFile(source, forModification)>
 
629
        </cfif>
 
630
</cffunction>
 
631
 
 
632
<cffunction name="readImageFromFile" access="private" output="true" returntype="struct" hint="Reads an image from a local file.  Requires an absolute path.">
 
633
        <cfargument name="inputFile" required="yes" type="string">
 
634
        <cfargument name="forModification" required="no" type="boolean" default="yes">
 
635
 
 
636
        <cfset var retVal = StructNew()>
 
637
        <cfset var img = "">
 
638
        <cfset var inFile = "">
 
639
        <cfset var filename = getFileFromPath(inputFile)>
 
640
        <cfset var extension = lcase(listLast(inputFile,"."))>
 
641
        <cfset var imageIO = CreateObject("java", "javax.imageio.ImageIO")>
 
642
        <cfset var validExtensionsToRead = ArrayToList(imageIO.getReaderFormatNames())>
 
643
 
 
644
        <cfset retVal.errorCode = 0>
 
645
        <cfset retVal.errorMessage = "">
 
646
 
 
647
        <cfif not fileExists(arguments.inputFile)>
 
648
                <cfset retVal = throw("The specified file #Chr(34)##arguments.inputFile##Chr(34)# could not be found.")>
 
649
                <cfreturn retVal>
 
650
        <cfelseif listLen(filename,".") lt 2>
 
651
                <cfset retVal = throw("Sorry, image files without extensions cannot be manipulated.")>
 
652
                <cfreturn retVal>
 
653
        <cfelseif listFindNoCase(validExtensionsToRead, extension) is 0>
 
654
                <cfset retVal = throw("Java is unable to read #extension# files.")>
 
655
                <cfreturn retVal>
 
656
        <cfelseif NOT fileExists(arguments.inputFile)>
 
657
                <cfset retVal = throw("The specified input file does not exist.")>
 
658
                <cfreturn retVal>
 
659
        <cfelse>
 
660
                <cfset img = CreateObject("java", "java.awt.image.BufferedImage")>
 
661
                <cfset inFile = CreateObject("java", "java.io.File")>
 
662
                <cfset inFile.init(arguments.inputFile)>
 
663
                <cfif NOT inFile.canRead()>
 
664
                        <cfset retVal = throw("Unable to open source file #Chr(34)##arguments.inputFile##Chr(34)#.")>
 
665
                        <cfreturn retVal>
 
666
                <cfelse>
 
667
                        <cftry>
 
668
                                <cfset img = imageIO.read(inFile)>
 
669
                                <cfcatch type="any">
 
670
                                        <cfset retval = throw("An error occurred attempting to read the specified image.  #cfcatch.message# - #cfcatch.detail#")>
 
671
                                        <cfreturn retVal>
 
672
                                </cfcatch>
 
673
                        </cftry>
 
674
                        <cfset retVal.img = img>
 
675
                        <cfset retVal.inFile = inFile>
 
676
                        <cfreturn retVal>
 
677
                </cfif>
 
678
        </cfif>
 
679
</cffunction>
 
680
 
 
681
<cffunction name="readImageFromURL" access="private" output="true" returntype="struct" hint="Read an image from a URL.  Requires an absolute URL.">
 
682
        <cfargument name="inputURL" required="yes" type="string">
 
683
        <cfargument name="forModification" required="no" type="boolean" default="yes">
 
684
 
 
685
        <cfset var retVal = StructNew()>
 
686
        <cfset var img = CreateObject("java", "java.awt.image.BufferedImage")>
 
687
        <cfset var inURL        = CreateObject("java", "java.net.URL")>
 
688
        <cfset var imageIO = CreateObject("java", "javax.imageio.ImageIO")>
 
689
 
 
690
        <cfset retVal.errorCode = 0>
 
691
        <cfset retVal.errorMessage = "">
 
692
 
 
693
 
 
694
        <cfset inURL.init(arguments.inputURL)>
 
695
        <cftry>
 
696
                <cfset img = imageIO.read(inURL)>
 
697
                <cfcatch type="any">
 
698
                        <cfset retval = throw("An error occurred attempting to read the specified image.  #cfcatch.message# - #cfcatch.detail#")>
 
699
                        <cfreturn retVal>
 
700
                </cfcatch>
 
701
        </cftry>
 
702
        <cfset retVal.img = img>
 
703
        <cfreturn retVal>
 
704
</cffunction>
 
705
 
 
706
<cffunction name="writeImage" access="public" output="true" returntype="struct" hint="Write an image to disk.">
 
707
        <cfargument name="outputFile" required="yes" type="string">
 
708
        <cfargument name="img" required="yes" type="any">
 
709
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
710
 
 
711
        <cfset var retVal = StructNew()>
 
712
        <cfset var outFile = "">
 
713
        <cfset var filename = getFileFromPath(outputFile)>
 
714
        <cfset var extension = lcase(listLast(filename,"."))>
 
715
        <cfset var imageIO = CreateObject("java", "javax.imageio.ImageIO")>
 
716
        <cfset var validExtensionsToWrite = ArrayToList(imageIO.getWriterFormatNames())>
 
717
        <!--- used for jpeg output method --->
 
718
        <cfset var out = "">
 
719
        <cfset var fos = "">
 
720
        <cfset var JPEGCodec = "">
 
721
        <cfset var encoder = "">
 
722
        <cfset var param = "">
 
723
        <cfset var quality = javacast("float", jpegCompression/100)>
 
724
        <cfset var tempOutputFile = "#variables.tempDirectory#\#createUUID()#.#extension#">
 
725
 
 
726
        <cfset retVal.errorCode = 0>
 
727
        <cfset retVal.errorMessage = "">
 
728
 
 
729
        <cfif listFindNoCase(validExtensionsToWrite, extension) eq 0>
 
730
                <cfset throw("Java is unable to write #extension# files.  Valid formats include: #validExtensionsToWrite#")>
 
731
        </cfif>
 
732
 
 
733
        <cfif extension neq "jpg" and extension neq "jpeg">
 
734
                <!---
 
735
                        Simple output method for non jpeg images
 
736
                --->
 
737
                <cfset outFile = CreateObject("java", "java.io.File")>
 
738
                <cfset outFile.init(tempOutputFile)>
 
739
                <cfset imageIO.write(img, extension, outFile)>
 
740
        <cfelse>
 
741
                <cfscript>
 
742
                        /*
 
743
                                JPEG output method handles compression
 
744
                        */
 
745
                        out = createObject("java", "java.io.BufferedOutputStream");
 
746
                        fos = createObject("java", "java.io.FileOutputStream");
 
747
                        fos.init(tempOutputFile);
 
748
                        out.init(fos);
 
749
                        JPEGCodec = createObject("java", "com.sun.image.codec.jpeg.JPEGCodec");
 
750
                        encoder = JPEGCodec.createJPEGEncoder(out);
 
751
                    param = encoder.getDefaultJPEGEncodeParam(img);
 
752
                    param.setQuality(quality, false);
 
753
                    encoder.setJPEGEncodeParam(param);
 
754
                    encoder.encode(img);
 
755
                    out.close();
 
756
                </cfscript>
 
757
        </cfif>
 
758
        <!--- move file to its final destination --->
 
759
        <cffile action="MOVE" source="#tempOutputFile#" destination="#arguments.outputFile#">
 
760
        <cfreturn retVal>
 
761
</cffunction>
 
762
 
 
763
<cffunction name="flipflop" access="private" output="true" returntype="struct" hint="Internal method used for flipping and flopping images.">
 
764
        <cfargument name="objImage" required="yes" type="Any">
 
765
        <cfargument name="inputFile" required="yes" type="string">
 
766
        <cfargument name="outputFile" required="yes" type="string">
 
767
        <cfargument name="direction" required="yes" type="string"><!--- horizontal or vertical --->
 
768
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
769
 
 
770
        <cfset var retVal = StructNew()>
 
771
        <cfset var loadImage = StructNew()>
 
772
        <cfset var saveImage = StructNew()>
 
773
        <cfset var flippedImage = "">
 
774
        <cfset var rh = getRenderingHints()>
 
775
        <cfset var img = "">
 
776
 
 
777
        <cfset retVal.errorCode = 0>
 
778
        <cfset retVal.errorMessage = "">
 
779
 
 
780
        <cfif inputFile neq "">
 
781
                <cfset loadImage = readImage(inputFile, "NO")>
 
782
                <cfif loadImage.errorCode is 0>
 
783
                        <cfset img = loadImage.img>
 
784
                <cfelse>
 
785
                        <cfset retVal = throw(loadImage.errorMessage)>
 
786
                        <cfreturn retVal>
 
787
                </cfif>
 
788
        <cfelse>
 
789
                <cfset img = objImage>
 
790
        </cfif>
 
791
        <cfif img.getType() eq 0>
 
792
                <cfset img = convertImageObject(img,img.TYPE_3BYTE_BGR)>
 
793
        </cfif>
 
794
        <cfscript>
 
795
                flippedImage = CreateObject("java", "java.awt.image.BufferedImage");
 
796
                at = CreateObject("java", "java.awt.geom.AffineTransform");
 
797
                op = CreateObject("java", "java.awt.image.AffineTransformOp");
 
798
 
 
799
                flippedImage.init(img.getWidth(), img.getHeight(), img.getType());
 
800
 
 
801
                if (direction eq "horizontal") {
 
802
                        at = at.getScaleInstance(-1, 1);
 
803
                        at.translate(-img.getWidth(), 0);
 
804
                } else {
 
805
                        at = at.getScaleInstance(1,-1);
 
806
                        at.translate(0, -img.getHeight());
 
807
                }
 
808
                op.init(at, rh);
 
809
                op.filter(img, flippedImage);
 
810
 
 
811
                if (outputFile eq "")
 
812
                {
 
813
                        retVal.img = flippedImage;
 
814
                        return retVal;
 
815
                } else {
 
816
                        saveImage = writeImage(outputFile, flippedImage, jpegCompression);
 
817
                        if (saveImage.errorCode gt 0)
 
818
                        {
 
819
                                return saveImage;
 
820
                        } else {
 
821
                                return retVal;
 
822
                        }
 
823
                }
 
824
        </cfscript>
 
825
</cffunction>
 
826
 
 
827
 
 
828
 
 
829
<cffunction name="filterFastBlur" access="public" output="true" returntype="struct" hint="Internal method used for flipping and flopping images.">
 
830
        <cfargument name="objImage" required="yes" type="Any">
 
831
        <cfargument name="inputFile" required="yes" type="string">
 
832
        <cfargument name="outputFile" required="yes" type="string">
 
833
        <cfargument name="blurAmount" required="yes" type="numeric">
 
834
        <cfargument name="iterations" required="yes" type="numeric">
 
835
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
836
 
 
837
        <cfset var retVal = StructNew()>
 
838
        <cfset var loadImage = StructNew()>
 
839
        <cfset var saveImage = StructNew()>
 
840
        <cfset var srcImage = "">
 
841
        <cfset var destImage = "">
 
842
        <cfset var rh = getRenderingHints()>
 
843
 
 
844
        <cfset retVal.errorCode = 0>
 
845
        <cfset retVal.errorMessage = "">
 
846
 
 
847
        <cfif NOT variables.javanulls>
 
848
                <cfset throw("Sorry, but the blur filter is not supported on this platform.")>
 
849
        </cfif>
 
850
        <cfif inputFile neq "">
 
851
                <cfset loadImage = readImage(inputFile, "NO")>
 
852
                <cfif loadImage.errorCode is 0>
 
853
                        <cfset srcImage = loadImage.img>
 
854
                <cfelse>
 
855
                        <cfset retVal = throw(loadImage.errorMessage)>
 
856
                        <cfreturn retVal>
 
857
                </cfif>
 
858
        <cfelse>
 
859
                <cfset srcImage = objImage>
 
860
        </cfif>
 
861
        <cfif srcImage.getType() eq 0>
 
862
                <cfset srcImage = convertImageObject(srcImage,srcImage.TYPE_3BYTE_BGR)>
 
863
        </cfif>
 
864
 
 
865
        <cfscript>
 
866
 
 
867
                // initialize the blur filter
 
868
                variables.blurFilter.init(arguments.blurAmount);
 
869
                // move the source image into the destination image
 
870
                // so we can repeatedly blur it.
 
871
                destImage = srcImage;
 
872
 
 
873
                for (i=1; i lte iterations; i=i+1)
 
874
                {
 
875
                        // do the blur i times
 
876
                        destImage = variables.blurFilter.filter(destImage);
 
877
                }
 
878
 
 
879
 
 
880
                if (outputFile eq "")
 
881
                {
 
882
                        // return the image object
 
883
                        retVal.img = destImage;
 
884
                        return retVal;
 
885
                } else {
 
886
                        // write the image object to the specified file.
 
887
                        saveImage = writeImage(outputFile, destImage, jpegCompression);
 
888
                        if (saveImage.errorCode gt 0)
 
889
                        {
 
890
                                return saveImage;
 
891
                        } else {
 
892
                                return retVal;
 
893
                        }
 
894
                }
 
895
        </cfscript>
 
896
</cffunction>
 
897
 
 
898
<cffunction name="filterSharpen" access="public" output="true" returntype="struct" hint="Internal method used for flipping and flopping images.">
 
899
        <cfargument name="objImage" required="yes" type="Any">
 
900
        <cfargument name="inputFile" required="yes" type="string">
 
901
        <cfargument name="outputFile" required="yes" type="string">
 
902
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
903
 
 
904
        <cfset var retVal = StructNew()>
 
905
        <cfset var loadImage = StructNew()>
 
906
        <cfset var saveImage = StructNew()>
 
907
        <cfset var srcImage = "">
 
908
        <cfset var destImage = "">
 
909
        <cfset var rh = getRenderingHints()>
 
910
 
 
911
        <cfset retVal.errorCode = 0>
 
912
        <cfset retVal.errorMessage = "">
 
913
 
 
914
        <cfif NOT variables.javanulls>
 
915
                <cfset throw("Sorry, but the blur filter is not supported on this platform.")>
 
916
        </cfif>
 
917
 
 
918
        <cfif inputFile neq "">
 
919
                <cfset loadImage = readImage(inputFile, "NO")>
 
920
                <cfif loadImage.errorCode is 0>
 
921
                        <cfset srcImage = loadImage.img>
 
922
                <cfelse>
 
923
                        <cfset retVal = throw(loadImage.errorMessage)>
 
924
                        <cfreturn retVal>
 
925
                </cfif>
 
926
        <cfelse>
 
927
                <cfset srcImage = objImage>
 
928
        </cfif>
 
929
        <cfif srcImage.getType() eq 0>
 
930
                <cfset srcImage = convertImageObject(srcImage,srcImage.TYPE_3BYTE_BGR)>
 
931
        </cfif>
 
932
 
 
933
        <cfscript>
 
934
                // initialize the sharpen filter
 
935
                variables.sharpenFilter.init();
 
936
 
 
937
                destImage = variables.sharpenFilter.filter(srcImage);
 
938
 
 
939
 
 
940
                if (outputFile eq "")
 
941
                {
 
942
                        // return the image object
 
943
                        retVal.img = destImage;
 
944
                        return retVal;
 
945
                } else {
 
946
                        // write the image object to the specified file.
 
947
                        saveImage = writeImage(outputFile, destImage, jpegCompression);
 
948
                        if (saveImage.errorCode gt 0)
 
949
                        {
 
950
                                return saveImage;
 
951
                        } else {
 
952
                                return retVal;
 
953
                        }
 
954
                }
 
955
        </cfscript>
 
956
</cffunction>
 
957
 
 
958
 
 
959
<cffunction name="filterPosterize" access="public" output="true" returntype="struct" hint="Internal method used for flipping and flopping images.">
 
960
        <cfargument name="objImage" required="yes" type="Any">
 
961
        <cfargument name="inputFile" required="yes" type="string">
 
962
        <cfargument name="outputFile" required="yes" type="string">
 
963
        <cfargument name="amount" required="yes" type="string">
 
964
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
965
 
 
966
        <cfset var retVal = StructNew()>
 
967
        <cfset var loadImage = StructNew()>
 
968
        <cfset var saveImage = StructNew()>
 
969
        <cfset var srcImage = "">
 
970
        <cfset var destImage = "">
 
971
        <cfset var rh = getRenderingHints()>
 
972
 
 
973
        <cfset retVal.errorCode = 0>
 
974
        <cfset retVal.errorMessage = "">
 
975
 
 
976
        <cfif NOT variables.javanulls>
 
977
                <cfset throw("Sorry, but the blur filter is not supported on this platform.")>
 
978
        </cfif>
 
979
 
 
980
        <cfif inputFile neq "">
 
981
                <cfset loadImage = readImage(inputFile, "NO")>
 
982
                <cfif loadImage.errorCode is 0>
 
983
                        <cfset srcImage = loadImage.img>
 
984
                <cfelse>
 
985
                        <cfset retVal = throw(loadImage.errorMessage)>
 
986
                        <cfreturn retVal>
 
987
                </cfif>
 
988
        <cfelse>
 
989
                <cfset srcImage = objImage>
 
990
        </cfif>
 
991
        <cfif srcImage.getType() eq 0>
 
992
                <cfset srcImage = convertImageObject(srcImage,srcImage.TYPE_3BYTE_BGR)>
 
993
        </cfif>
 
994
        <cfif srcImage.getType() neq 5>
 
995
                <cfset throw("ImageCFC cannot posterize this image type (#srcImage.getType()#)")>
 
996
        </cfif>
 
997
        <cfscript>
 
998
                // initialize the posterize filter
 
999
                variables.posterizeFilter.init(arguments.amount);
 
1000
 
 
1001
                destImage = variables.posterizeFilter.filter(srcImage);
 
1002
 
 
1003
 
 
1004
                if (outputFile eq "")
 
1005
                {
 
1006
                        // return the image object
 
1007
                        retVal.img = destImage;
 
1008
                        return retVal;
 
1009
                } else {
 
1010
                        // write the image object to the specified file.
 
1011
                        saveImage = writeImage(outputFile, destImage, jpegCompression);
 
1012
                        if (saveImage.errorCode gt 0)
 
1013
                        {
 
1014
                                return saveImage;
 
1015
                        } else {
 
1016
                                return retVal;
 
1017
                        }
 
1018
                }
 
1019
        </cfscript>
 
1020
</cffunction>
 
1021
 
 
1022
 
 
1023
<cffunction name="addText" access="public" output="true" returntype="struct" hint="Add text to an image.">
 
1024
        <cfargument name="objImage" required="yes" type="Any">
 
1025
        <cfargument name="inputFile" required="yes" type="string">
 
1026
        <cfargument name="outputFile" required="yes" type="string">
 
1027
        <cfargument name="x" required="yes" type="numeric">
 
1028
        <cfargument name="y" required="yes" type="numeric">
 
1029
        <cfargument name="fontDetails" required="yes" type="struct">
 
1030
        <cfargument name="content" required="yes" type="String">
 
1031
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
1032
 
 
1033
        <cfset var retVal = StructNew()>
 
1034
        <cfset var loadImage = StructNew()>
 
1035
        <cfset var img = "">
 
1036
        <cfset var saveImage = StructNew()>
 
1037
        <cfset var g2d = "">
 
1038
        <cfset var bgImage = "">
 
1039
        <cfset var fontImage = "">
 
1040
        <cfset var overlayImage = "">
 
1041
        <cfset var Color = "">
 
1042
        <cfset var font = "">
 
1043
        <cfset var font_stream = "">
 
1044
        <cfset var ac = "">
 
1045
        <cfset var rgb = "">
 
1046
 
 
1047
        <cfset retVal.errorCode = 0>
 
1048
        <cfset retVal.errorMessage = "">
 
1049
 
 
1050
        <cfparam name="arguments.fontDetails.size" default="12">
 
1051
        <cfparam name="arguments.fontDetails.color" default="black">
 
1052
        <cfparam name="arguments.fontDetails.fontFile" default="">
 
1053
        <cfparam name="arguments.fontDetails.fontName" default="serif">
 
1054
 
 
1055
        <cfif arguments.fontDetails.fontFile neq "" and not fileExists(arguments.fontDetails.fontFile)>
 
1056
                <cfset retVal = throw("The specified font file #Chr(34)##arguments.inputFile##Chr(34)# could not be found on the server.")>
 
1057
                <cfreturn retVal>
 
1058
        </cfif>
 
1059
        <cftry>
 
1060
                <cfset rgb = getRGB(arguments.fontDetails.color)>
 
1061
                <cfcatch type="any">
 
1062
                        <cfset retVal = throw("Invalid color #Chr(34)##arguments.fontDetails.color##Chr(34)#")>
 
1063
                        <cfreturn retVal>
 
1064
                </cfcatch>
 
1065
        </cftry>
 
1066
        <cfif inputFile neq "">
 
1067
                <cfset loadImage = readImage(inputFile, "NO")>
 
1068
                <cfif loadImage.errorCode is 0>
 
1069
                        <cfset img = loadImage.img>
 
1070
                <cfelse>
 
1071
                        <cfset retVal = throw(loadImage.errorMessage)>
 
1072
                        <cfreturn retVal>
 
1073
                </cfif>
 
1074
        <cfelse>
 
1075
                <cfset img = objImage>
 
1076
        </cfif>
 
1077
        <cfif img.getType() eq 0>
 
1078
                <cfset img = convertImageObject(img,img.TYPE_3BYTE_BGR)>
 
1079
        </cfif>
 
1080
        <cfscript>
 
1081
                // load objects
 
1082
                bgImage = CreateObject("java", "java.awt.image.BufferedImage");
 
1083
                fontImage = CreateObject("java", "java.awt.image.BufferedImage");
 
1084
                overlayImage = CreateObject("java", "java.awt.image.BufferedImage");
 
1085
                Color = CreateObject("java","java.awt.Color");
 
1086
                font = createObject("java","java.awt.Font");
 
1087
                font_stream = createObject("java","java.io.FileInputStream");
 
1088
                ac = CreateObject("Java", "java.awt.AlphaComposite");
 
1089
 
 
1090
                // set up basic needs
 
1091
                fontColor = Color.init(javacast("int", rgb.red), javacast("int", rgb.green), javacast("int", rgb.blue));
 
1092
 
 
1093
                if (fontDetails.fontFile neq "")
 
1094
                {
 
1095
                        font_stream.init(arguments.fontDetails.fontFile);
 
1096
                        font = font.createFont(font.TRUETYPE_FONT, font_stream);
 
1097
                        font = font.deriveFont(javacast("float",arguments.fontDetails.size));
 
1098
                } else {
 
1099
                        font.init(fontDetails.fontName, evaluate(fontDetails.style), fontDetails.size);
 
1100
                }
 
1101
                // get font metrics using a 1x1 bufferedImage
 
1102
                fontImage.init(1,1,img.getType());
 
1103
                g2 = fontImage.createGraphics();
 
1104
                g2.setRenderingHints(getRenderingHints());
 
1105
                fc = g2.getFontRenderContext();
 
1106
                bounds = font.getStringBounds(content,fc);
 
1107
 
 
1108
                g2 = img.createGraphics();
 
1109
                g2.setRenderingHints(getRenderingHints());
 
1110
                g2.setFont(font);
 
1111
                g2.setColor(fontColor);
 
1112
                // in case you want to change the alpha
 
1113
                // g2.setComposite(ac.getInstance(ac.SRC_OVER, 0.50));
 
1114
 
 
1115
                // the location (arguments.fontDetails.size+y) doesn't really work
 
1116
                // the way I want it to.
 
1117
                g2.drawString(content,javacast("int",x),javacast("int",arguments.fontDetails.size+y));
 
1118
 
 
1119
                if (outputFile eq "")
 
1120
                {
 
1121
                        retVal.img = img;
 
1122
                        return retVal;
 
1123
                } else {
 
1124
                        saveImage = writeImage(outputFile, img, jpegCompression);
 
1125
                        if (saveImage.errorCode gt 0)
 
1126
                        {
 
1127
                                return saveImage;
 
1128
                        } else {
 
1129
                                return retVal;
 
1130
                        }
 
1131
                }
 
1132
        </cfscript>
 
1133
</cffunction>
 
1134
 
 
1135
<cffunction name="watermark" access="public" output="false">
 
1136
        <cfargument name="objImage1" required="yes" type="Any">
 
1137
        <cfargument name="objImage2" required="yes" type="Any">
 
1138
        <cfargument name="inputFile1" required="yes" type="string">
 
1139
        <cfargument name="inputFile2" required="yes" type="string">
 
1140
        <cfargument name="alpha" required="yes" type="numeric">
 
1141
        <cfargument name="placeAtX" required="yes" type="numeric">
 
1142
        <cfargument name="placeAtY" required="yes" type="numeric">
 
1143
        <cfargument name="outputFile" required="yes" type="string">
 
1144
        <cfargument name="jpegCompression" required="no" type="numeric" default="#variables.defaultJpegCompression#">
 
1145
 
 
1146
        <cfset var retVal = StructNew()>
 
1147
        <cfset var loadImage = StructNew()>
 
1148
        <cfset var originalImage = "">
 
1149
        <cfset var wmImage = "">
 
1150
        <cfset var saveImage = StructNew()>
 
1151
        <cfset var ac = "">
 
1152
        <cfset var rh = getRenderingHints()>
 
1153
 
 
1154
        <cfset retVal.errorCode = 0>
 
1155
        <cfset retVal.errorMessage = "">
 
1156
 
 
1157
        <cfif inputFile1 neq "">
 
1158
                <cfset loadImage = readImage(inputFile1, "NO")>
 
1159
                <cfif loadImage.errorCode is 0>
 
1160
                        <cfset originalImage = loadImage.img>
 
1161
                <cfelse>
 
1162
                        <cfset retVal = throw(loadImage.errorMessage)>
 
1163
                        <cfreturn retVal>
 
1164
                </cfif>
 
1165
        <cfelse>
 
1166
                <cfset originalImage = objImage1>
 
1167
        </cfif>
 
1168
        <cfif originalImage.getType() eq 0>
 
1169
                <cfset originalImage = convertImageObject(originalImage,originalImage.TYPE_3BYTE_BGR)>
 
1170
        </cfif>
 
1171
 
 
1172
        <cfif inputFile2 neq "">
 
1173
                <cfset loadImage = readImage(inputFile2, "NO")>
 
1174
                <cfif loadImage.errorCode is 0>
 
1175
                        <cfset wmImage = loadImage.img>
 
1176
                <cfelse>
 
1177
                        <cfset retVal = throw(loadImage.errorMessage)>
 
1178
                        <cfreturn retVal>
 
1179
                </cfif>
 
1180
        <cfelse>
 
1181
                <cfset wmImage = objImage2>
 
1182
        </cfif>
 
1183
        <cfif wmImage.getType() eq 0>
 
1184
                <cfset wmImage = convertImageObject(wmImage,wmImage.TYPE_3BYTE_BGR)>
 
1185
        </cfif>
 
1186
 
 
1187
 
 
1188
        <cfscript>
 
1189
                at = CreateObject("java", "java.awt.geom.AffineTransform");
 
1190
                op = CreateObject("java", "java.awt.image.AffineTransformOp");
 
1191
                ac = CreateObject("Java", "java.awt.AlphaComposite");
 
1192
                gfx = originalImage.getGraphics();
 
1193
                gfx.setComposite(ac.getInstance(ac.SRC_OVER, alpha));
 
1194
 
 
1195
                at.init();
 
1196
                // op.init(at,op.TYPE_BILINEAR);
 
1197
                op.init(at, rh);
 
1198
 
 
1199
                gfx.drawImage(wmImage, op, javaCast("int",arguments.placeAtX), javacast("int", arguments.placeAtY));
 
1200
 
 
1201
                gfx.dispose();
 
1202
 
 
1203
                if (outputFile eq "")
 
1204
                {
 
1205
                        retVal.img = originalImage;
 
1206
                        return retVal;
 
1207
                } else {
 
1208
                        saveImage = writeImage(outputFile, originalImage, jpegCompression);
 
1209
                        if (saveImage.errorCode gt 0)
 
1210
                        {
 
1211
                                return saveImage;
 
1212
                        } else {
 
1213
                                return retVal;
 
1214
                        }
 
1215
                }
 
1216
        </cfscript>
 
1217
</cffunction>
 
1218
 
 
1219
<cffunction name="isURL" access="private" output="false" returnType="boolean">
 
1220
        <cfargument name="stringToCheck" required="yes" type="string">
 
1221
        <cfif REFindNoCase("^(((https?:)\/\/))[-[:alnum:]\?%,\.\/&##!@:=\+~_]+[A-Za-z0-9\/]$",stringToCheck) NEQ 0>
 
1222
                <cfreturn true>
 
1223
        <cfelse>
 
1224
                <cfreturn false>
 
1225
        </cfif>
 
1226
</cffunction>
 
1227
 
 
1228
<!--- function returns RGB values in a structure for hex or the 16
 
1229
        HTML named colors --->
 
1230
<cffunction name="getRGB" access="private" output="true" returnType="struct">
 
1231
        <cfargument name="color" type="string" required="yes">
 
1232
 
 
1233
        <cfset var retVal = structNew()>
 
1234
        <cfset var cnt = 0>
 
1235
        <cfset var namedColors = "aqua,black,blue,fuchsia,gray,green,lime,maroon,navy,olive,purple,red,silver,teal,white,yellow">
 
1236
        <cfset var namedColorsHexValues = "00ffff,000000,0000ff,ff00ff,808080,008000,00ff00,800000,000080,808080,ff0000,c0c0c0,008080,ffffff,ffff00">
 
1237
 
 
1238
        <cfset retVal.red = 0>
 
1239
        <cfset retVal.green = 0>
 
1240
        <cfset retVal.blue = 0>
 
1241
 
 
1242
        <cfset arguments.color = trim(arguments.color)>
 
1243
        <cfif len(arguments.color) is 0>
 
1244
                <cfreturn retVal>
 
1245
        <cfelseif listFind(namedColors, arguments.color) gt 0>
 
1246
                <cfset arguments.color = listGetAt(namedColorsHexValues, listFind(namedColors, arguments.color))>
 
1247
        </cfif>
 
1248
        <cfif left(arguments.color,1) eq "##">
 
1249
                <cfset arguments.color = right(arguments.color,len(arguments.color)-1)>
 
1250
        </cfif>
 
1251
        <cfif len(arguments.color) neq 6>
 
1252
                <cfreturn retVal>
 
1253
        <cfelse>
 
1254
                <cftry>
 
1255
                        <cfset retVal.red = InputBaseN(mid(arguments.color,1,2),16)>
 
1256
                        <cfset retVal.green = InputBaseN(mid(arguments.color,3,2),16)>
 
1257
                        <cfset retVal.blue = InputBaseN(mid(arguments.color,5,2),16)>
 
1258
                        <cfcatch type="any">
 
1259
                                <cfset retVal.red = 0>
 
1260
                                <cfset retVal.green = 0>
 
1261
                                <cfset retVal.blue = 0>
 
1262
                                <cfreturn retVal>
 
1263
                        </cfcatch>
 
1264
                </cftry>
 
1265
        </cfif>
 
1266
        <cfreturn retVal>
 
1267
</cffunction>
 
1268
 
 
1269
<cffunction name="throw" access="private" output="false" returnType="struct">
 
1270
        <cfargument name="detail" type="string" required="yes">
 
1271
        <cfargument name="force" type="boolean" required="no" default="no">
 
1272
 
 
1273
        <cfset var retVal = StructNew()>
 
1274
 
 
1275
        <cfif variables.throwOnError or arguments.force>
 
1276
                <cfthrow detail="#arguments.detail#" message="#arguments.detail#">
 
1277
        <cfelse>
 
1278
                <cfset retVal.errorCode = 1>
 
1279
                <cfset retVal.errorMessage = arguments.detail>
 
1280
                <cfreturn retVal>
 
1281
        </cfif>
 
1282
</cffunction>
 
1283
 
 
1284
<cffunction name="debugDump" access="private">
 
1285
        <cfdump var="#arguments#"><cfabort>
 
1286
</cffunction>
 
1287
 
 
1288
<cffunction name="convertImageObject" access="private" output="false" returnType="any">
 
1289
        <cfargument name="bImage" type="Any" required="yes">
 
1290
        <cfargument name="type" type="numeric" required="yes">
 
1291
 
 
1292
        <cfscript>
 
1293
        // convert the image to a specified BufferedImage type and return it
 
1294
 
 
1295
        var width = bImage.getWidth();
 
1296
        var height = bImage.getHeight();
 
1297
        var newImage = createObject("java","java.awt.image.BufferedImage").init(javacast("int",width), javacast("int",height), javacast("int",type));
 
1298
        // int[] rgbArray = new int[width*height];
 
1299
        var rgbArray = variables.arrObj.newInstance(variables.intClass, javacast("int",width*height));
 
1300
 
 
1301
        bImage.getRGB(
 
1302
                javacast("int",0),
 
1303
                javacast("int",0),
 
1304
                javacast("int",width),
 
1305
                javacast("int",height),
 
1306
                rgbArray,
 
1307
                javacast("int",0),
 
1308
                javacast("int",width)
 
1309
                );
 
1310
        newImage.setRGB(
 
1311
                javacast("int",0),
 
1312
                javacast("int",0),
 
1313
                javacast("int",width),
 
1314
                javacast("int",height),
 
1315
                rgbArray,
 
1316
                javacast("int",0),
 
1317
                javacast("int",width)
 
1318
                );
 
1319
        return newImage;
 
1320
        </cfscript>
 
1321
 
 
1322
</cffunction>
 
1323
 
 
1324
</cfcomponent>