Tải bản đầy đủ - 0 (trang)
Hack 5. Add a Watermark to a Text Component

Hack 5. Add a Watermark to a Text Component

Tải bản đầy đủ - 0trang









publicclassWatermarkTextFieldextendsJTextField{



BufferedImageimg;



TexturePainttexture;







































}



publicWatermarkTextField(Filefile)throwsIOE



super();



img=ImageIO.read(file);



Rectanglerect=newRectangle(0,0,





img.getWidth(null),img.getHeigh



texture=newTexturePaint(img,rect);



setOpaque(false);

}



Example1-10createsaclasscalledWatermarkTextField.Itisa

subclassofJTextFieldwithacustomconstructorthatacceptsa

Fileobjectcontaininganimage.Italsodefinestwomember

variables:imgandtexture.Aftertheobligatorycalltosuper(),the

constructorreadsthefileintotheBufferedImagevariable,img.If

thefileisn'tavalidimageorcan'tbereadforsomeother

reasonthemethodwillthrowanexception(hencethetHRows

IOExceptionclauseontheconstructordefinition).

Aftertheimageisloadedsuccessfully,theconstructorcreatesa

TexturePaint.TexturePaintsmustbecreatedwithasourceimage

andarectangle.Therectangledefinestheportionofthesource

tobetiled.Inthiscase,youwanttheentireimagetobeused,

sotherectangleisthesamesizeastheimage.



Ifyouwantedtousejustaportionoftheimage,youcouldmakethe

rectanglesmaller.Thiswouldalsogiveyoutheabilitytostoreallof

yourtexturesinasinglelargeimage,whichcouldsaveloadingtime

andmemory.



ThelastthingtheWatermarkTextFieldconstructordoesbefore

returningiscallsetOpaque(false).Asyouhaveseenearlierinthis

chapter(andwillseeagain),thesetOpaque()methodisoneofthe

coretoolsforhackingSwing.Inthiscase,itisusedtoturnoff

thedefaultbackgroundoftheTextField,allowingyouto

substituteyourown.

Withthesubclasscreated,youcanaddamethodtodothe

actualdrawing:















publicvoidpaintComponent(Graphicsg){



Graphics2Dg2=(Graphics2D)g;



g2.setPaint(texture);



g.fillRect(0,0,getWidth(),getHeight());



super.paintComponent(g);

}



WatermarkTextFieldoverridestheparentclass'spaintComponent()



methodwithitsownversion.Theactualdrawingispretty

simple:casttoaGraphics2Dobject(whichunderstandshowto

workwithPaintclasses),thenfillinthebackgroundwiththe

texturepaintandcallsuper().

Earlier,Isaidthatyouwilloverridetheparentclasspartially

ratherthancompletely.Thisisbecausethecodestillcallsthe

parentclass'spaintComponent()method,butitdoesitafter

paintingthenewbackground.Becausetheopaquepropertyisset

tofalse,theparentclasswillnotdrawitsownbackground,

allowingyourcustomonetoshowthrough.Thecomponentwill

drawthetext,selections,andcursorsasnormalontopofthe

custombackground.

Withtheclassready,it'stimetopulltogetheran



exampleExample1-11.



Example1-11.Tryingoutthewatermarkedtext

field







publicstaticvoidmain(String[]args)throwsException



JFrameframe=newJFrame("WatermarkJTextField















JTextFieldtextfield=newWatermarkTextField(n

textfield.setText("ATextField");



frame.getContentPane().add(textfield);





frame.pack();





frame.show();



}



Themain()methodcreatesaJFramewithonechild:thecustom

textfield.ItcreatesanewWatermarkTextFieldwithanimagefilein

theconstructor,thenitpacksandshowstheframe.Thetext

fieldiseverybitanormalJTextFieldexceptfortheconstructor,

soyoucanuseavariableoftypeJTextFieldwithnoproblem.

Theimage,red.png,lookslikeFigure1-19.



Figure1-19.red.png,thebackgroundimage



Oncetiledacrossthebackgroundofthecomponent,itlookslike



Figure1-20.Therunningprogram



GoingFurther

Overridingacomponent'sbackgroundwithcustomdrawingcodeisasimple

techniquethatcanbeusedinsomesurprisingways.Thenexthackwillreusethe

watermarkcodetocreateaJTextPanewithlightcloudsinthebackgroundanda

smallimagebadgeintheupper-righthandcorner.Withcustombackgroundsyou

couldalsoaddanimation,statusreports,orevenrotatingspaceimages(see

"PutaNASAPhotointotheBackgroundofaTextArea"[Hack#7]).



Hack6.WatermarkYourScrollPanes



Thishackcreatesatextareawithatiledbackground

imagethatisfixed,evenwhenthetextareascrolls,and

alsoafixedforegroundimagethatappearsabovethe

text,muchlikethestationbadgesnowaffixedtothe

lower-righthandcornerofmostTVbroadcasts.

TheSwingframeworkwasdesignedtoletdevelopersoverride

portionsofeverycomponent,boththevisualappearance(the

view)andthebehavior(themodelandcontroller).Thisdesign

givesdevelopersgreatflexibility.Oneofmyfavoritesisthe

JScrollPane.Itsnestedcompositedesignallowsdevelopersto

createsomestunningeffects.

Onceagain,theideaistooverridethedrawingcodeofa

standardcomponenttocreatethevisualeffects[Hack#5].

Thedifferencehereisthatyoumustdealwithacomposite

object,theJScrollPane.AJScrollPaneisnotasingleSwing

componentit'sactuallyawrapperaroundtwoscrollbarsandthe

componentthatdoestherealscrollingisaJViewport.This

viewportistheactualtargetcomponent;youwillsubclassitto

drawbothaboveandbelowtheViewcomponent(asseenin

Example1-12).TheViewistheSwingwidgetbeingscrolled;in

thiscase,itisaJTextArea.



Example1-12.Modifyingtheviewportfor

watermarking

publicclassScrollPaneWatermarkextendsJViewport{

BufferedImagefgimage,bgimage;

TexturePainttexture;



publicvoidsetBackgroundTexture(URLurl)throwsIOExcep

bgimage=ImageIO.read(url);

Rectanglerect=newRectangle(0,0,

bgimage.getWidth(null),bgimage.getHeight(null));

texture=newTexturePaint(bgimage,rect);

}



publicvoidsetForegroundBadge(URLurl)throwsIOException

fgimage=ImageIO.read(url);

}



TheScrollPaneWatermarkclassinheritsfromJViewport,addingtwo

methods:setBackgroundTexture()andsetForegroundBadge().Each

takesaURLinsteadofaFiletoallowforimagesloadedfrom

placesotherthanthelocaldisk,suchasawebserverorJAR

file.

setBackgroundTexture()doesthesamethingthatthe

WatermarkTextFielddidintheprevioushack.Itloadstheimage,



createsasame-sizerectangle,theninitializesaTexturePaintfor

lateruse.setForegroundBadge()isevensimpler,onlyloadingthe

imageandstoringitinthefgimagevariable.

Withtheclasssetup,it'stimetodraw.Thecodebelowcalls

super.paintComponent()first,andthendrawsthetextureontopof

thecomponent.Thisisbecausetheexistingbackgroundmight

needtoshowthroughincasethetexturehastranslucent

sections.Thiswouldbeespeciallyimportantifthestandard

viewbackgroundisn'tjustasolidcolor.UnderMacOSX,for

example,thebackgroundisoftenastriped,lightbluepattern.

Here'sthecodetohandletexturing:

publicvoidpaintComponent(Graphicsg){

//dothesuperclassbehaviorfirst

super.paintComponent(g);



Tài liệu bạn tìm kiếm đã sẵn sàng tải về

Hack 5. Add a Watermark to a Text Component

Tải bản đầy đủ ngay(0 tr)

×