<cfset sliceWidth = 600>
<cfset sliceHeight = 60>
<cfset sourceImage = ImageNew( ExpandPath("combustion.jpg") )>
<cfset sliceImage = ImageCopy(sourceImage, 30, 192, sliceWidth, sliceHeight)>
As you can see this is source image I used. To make it easier to visualize, the rectangular slice area is outlined in white.
Next I created a new image and drew my text on it, using antialiasing to produce smoother text edges. It is worth noting the text color does not matter since the text will ultimately be filled with the image slice graphic.
<cfset maskImage = ImageNew("", sliceWidth, sliceHeight, "argb")>
<cfset ImageSetAntiAliasing( maskImage, "on") >
<cfset ImageSetDrawingColor( maskImage, "white")>
<cfset attr = { Size = 35, Font = "Arial", Style= "boldItalic" }>
<cfset ImageDrawText(maskImage, "FLAME AND COMBUSTION", 65, 40, attr)>
Finally, I used a little java to achieve the fill effect. This was done by using an AlphaComposite when drawing the image over the text mask. The result is only the parts of the image that overlap with the text are rendered.
<cfscript>
maskGraphics = ImageGetBufferedImage(maskImage).getGraphics();
AlphaComposite = createObject("java", "java.awt.AlphaComposite");
maskGraphics.setComposite( AlphaComposite.SrcIn );
maskGraphics.drawImage( ImageGetBufferedImage(sliceImage),
javacast("int", 0),
javacast("int", 0),
javacast("null", ""));
maskGraphics.dispose();
</cfscript>
<div style="background-color: black; ">
<cfimage source="#maskImage#" action="writeToBrowser">
</div>
Here is the result. For this image I used a black background for better contrast.

Now if it does not matter which part of the image is used, you could skip the ImageCopy and simply draw the graphic over the text at position (0, 0) like this:
<cfset sourceImage = ImageNew( "c:\img\myImage640x480.jpg" )>
<cfset maskImage = ImageNew("", 500, 70, "argb")>
<cfset ImageSetAntiAliasing( maskImage, "on") >
<cfset ImageSetDrawingColor( maskImage, "white")>
<cfset attr = { Size = 30, Font = "Arial", Style= "boldItalic" }>
<cfset ImageDrawText(maskImage, "HORIZON OF SKY AND CLOUDS", 20, 40, attr)>
<cfscript>
// cfSeaching: use a composite to render only the parts of the image that overlap with the text mask
maskGraphics = ImageGetBufferedImage(maskImage).getGraphics();
AlphaComposite = createObject("java", "java.awt.AlphaComposite");
maskGraphics.setComposite( AlphaComposite.SrcIn );
maskGraphics.drawImage( ImageGetBufferedImage(sourceImage),
javacast("int", 0),
javacast("int", 0),
javacast("null", ""));
maskGraphics.dispose();
</cfscript>
<!--- show original and mask image side by side --->
<cfimage source="#sourceImage#" action="writeToBrowser">
<cfimage source="#maskImage#" action="writeToBrowser">
Hope you found this useful. Comments, suggestions, corrections are always welcome.
it did not woeked as suggested by you, the image text appears bu the background image get disaapear, is some logic behind this:
ReplyDelete@Gary,
ReplyDeleteYes, that is the idea here. ie To display the text only, without the background.
Perhaps you are trying to achieve something different.. Can explain more about what you are trying to do with the code?
I would like to do something similar but instead of an select an image as the background fill for the text, I would like to have a transparent background. ie. only show a border from the text. Similar to the nofill function in publisher. Any suggestions?
ReplyDelete@Nick,
ReplyDeleteSo everything is transparent, except for the outline of the text?
Yes, that is possible. Let me write up an example .. just because it is a cool technique ;)
-Leigh
@Nick,
ReplyDeleteI wrote up an example here:
href="http://cfsearching.blogspot.com/2009/10/coldfusion-draw-text-outline-on-image.html
-Leigh