Or here's another one I found on my HD:
Save this as "Test Fades.bb"
And save this include as "INC Fades.bb"
Save this as "Test Fades.bb"
; Screen fades (30/11/03) ; - Seeing as ordinary fades are too slow. Blitz+ only, ; though B2D and B3D users could rem out fades using lockpixels and still use others fades. ; ; Load the "INC fade.bb" for more information. AppTitle "Real time screen wipes" Graphics 640,480,16 ; feel free to mess about with any res. ; You'll need this early in your own code, sometime after calling Graphics Include "INC fades.bb" ; Set up some timers Dim time(100000) timenum=0 ; which fade to show in the demo fade=0 SetBuffer BackBuffer() ; Well, seeing as the last Lord of the Rings movie is out soon.... IMback=LoadImage("Gandalf.jpg") ; Resize the image is the wrong size for the screen. If ImageWidth(IMback)<>SCRwid Then ResizeImage IMback,SCRwid,SCRhi DrawImage IMback,0,0 : Flip : DrawImage IMback,0,0 txt$="Press any key..." : go=False : x=SCRwid Repeat Cls DrawImage IMback,0,0 Color 0,0,$080808 : Text 2,2,"1-9: Try fades" Text 2,14,"SPACE: Cycle demo" Text 2,26,"Any other: Random." ; Text 2,38,AvailVidMem() key=GetKey() If key>0 spd#=Rand(-10,10) ; Doesn't have to be a whole number, but usually works better as such. acl#=Rnd(0,0.4) ;acl#=0 Select key Case 32 ; press space to cycle through demo fades fade=fade+1 If fade>18 Then Restore demodata : fade=1 Read f : Read spd : Read acl# SetFade(f,spd,acl) Case 49,50,51,52,53,54,55,56,57 ; press 1-9 to demo a particular fade SetFade(key-48,spd,acl) Default ; any other key set's up a random fade. SetFade(Rand(1,8),spd,acl) End Select txt$="Working...(spd:"+spd+", acl:"+acl+")" go=True : TIMEnum=0 : TIMEshort=0 : TIMElong=0 : TIMEav#=0 EndIf If go=True m=MilliSecs() done=DoFade() time(TIMEnum)=MilliSecs()-m : TIMEnum=TIMEnum+1 ; Unrem to test the fade frame by frame (press space) ;Repeat : VWait : Until KeyDown(57) EndIf If done=True ; get timing results For n=0 To timenum-1 TIMEav=TIMEav+time(n) If time(n)>TIMElong Then TIMElong=time(n) If time(n)<TIMEshort Then TIMEshort=time(n) Next TIMEav=TIMEav/timenum ; Show the average milliseconds per frame taken for the last fade operation. txt$="Average:"+TIMEav+"ms, Longest:"+TIMElong+"ms" : go=False : done=False EndIf If KeyDown(66) Then SaveBuffer(BackBuffer,"fade shot.bmp") : VWait 25 Color 8,8,8 : Text x,201,txt$ Color $FF,$FF,$FF : Text x,200,txt$ x=x-1 : If x<0 Then x=SCRwid-StringWidth(txt$) Flip Until KeyDown(1)=True End .demodata Data FADcircle,-1,0.7 Data FADcircle,6,0.3 Data FADhatch,-6,0.4 Data FADhatch,6,0.4 Data FADbox,-8,0.5 Data FADbox,1,0.9 Data FADdropdown,-10,0.5 Data FADdropdown,10,0.9 Data FADragged,-10,0.2 Data FADragged,10,0.2 Data FADpixelST,-3,0.2 Data FADpixelST,0.3,0.1 Data FADrgbfadeST,-4,0 Data FADrgbfadeST,4,0 Data FADrgbdrop,-6,0.3 Data FADrgbdrop,6,0.3 Data FADrgbdropST,-4,0 Data FADrgbdropST,4,0
And save this include as "INC Fades.bb"
; Screen fades ; - Simon Smith, Nov 2003 ; simonisfound@... ; ; Updated very infrequently, and now available to the Blitz community. ; ; Feel free to add your own fades, I'm sure there are plenty of effective fades I've missed out. ; Send them on and I'll most likely add then to the available source. ; Also this code is Freeware, and you can feel free to use or modify to your own uses, as long ; as you give me a credit for the original code. An e-mail about it would be a nice ; bonus too. ; To use this just include this document with source. ; Then start a fade you just call SetFade() (check "Test Fades.bb" for examples) ; and then call DoFade() just before each display update. It will return a flag to say ; whether it's finished or not, a useful trigger for exiting a loop. ; The last frame of DoFade() will clean up any used system or graphics RAM. ; If you call a fade without any spd or acl parameters it will set a default for you. ; Values can be quite varying for different fades, it's trial and error for what looks good. ; The functions have a reasonable amount of correction for bad values. ; ; It's best to set the graphics buffer to Backbuffer() before Setting or doing fades. You can ; write your fades to a seperate image but it must be screen sized. This may change at some point. ; ---------------------------------------------------- ; Now on to the code.... ; * color to black out without being transparent in 16bit. ; Or feel free to change it to some other value for fadeout. Const COLshadow=$050605 Global SCRwid=GraphicsWidth(),SCRhi=GraphicsHeight(),SCRdep=GraphicsDepth() Global SCRbytes=SCRdep/8 ; You can choose from these fades, all are intended to work real time, unless noted otherwise ; * all time results recorded on a Geforce2MX / 16 bit 640x480 / Athlon 1.33ghz ; Screen just appears. I use this as default for low detail mode in my games. Feel free to ignore ; Uses no memory obviously Const FADnone=0 ; Mario style circle fade ; Time <1ms av per function call ; Screen sized image created, held in graphics RAM. Const FADcircle=1 ; Hatching passes down then up the screen, boring but effective in high resolutions. ; Time 1.1 ms av ; Uses <10k of graphics RAM for a small hatched image. Const FADhatch=2 ; Boring shrinking box ; Time 0.4 ms av ; Requires no extra memory. Const FADbox=3 ; Cute drop down with bounce. ; Time <1 ms av ; Requires no extra memory. Const FADdropdown=4 ; Ragged Chrono Trigger style fade. ; Time 0.2 ms av ; Requires an image sized 1/16th the screen held in graphics RAM. Const FADragged=5 ; SNES style pixellation, Static not Realtime ; Time 24ms av, 40ms when busy ; Requires a copy of the back buffer held in system RAM. Const FADpixelST=6 ; Slow fullscreen fadeout, Static not Realtime ; Time 22ms av, 33ms in 32bit ; Requires screen sized image in graphics RAM and static RAM Const FADrgbfadeST=7 ; Faded bar drops down the screen and wipes it. ; Time 12ms av ; Requires no extra memory. Const FADrgbdrop=8 ; Static screen version of rgbdrop, much nicer fade. ; Time 10ms av ; Requires screen sized image in graphics RAM and static RAM Const FADrgbdropST=9 Type fade Field x#,y#,ox#,oy# ; x,y plus alternate x,y Field xspd#,yspd# ; possible speed for both Field spd#,size#,acl# ; measure speed, size and acceleration Field flag1#,flag2# ; 2 general purpose flags Field IMbuffer ; for effects that need a copy of the buffer info Field BNKbuffer ; a bank to hold copy of buffer info Field IM ; temp imagefile Field channel ; Channel for sound effects Field kind ; Style of fade as set by constants FADxxx Field done ; Is it finished? End Type ; Set up all the necessary variables to start a fade ; -- Set SPD to negative to fade in ; -- acl is acceleration of fade, obviously Function SetFade(fadetype,spd#=0,acl#=0) buf=GraphicsBuffer() ; quick check to see if screenmodes have changed at some point If SCRwid<>GraphicsWidth() Then SCRwid=GraphicsWidth() : SCRhi=GraphicsHeight() : SCRdep=GraphicsDepth() ; rem this out if you want to try multiple fades. For f.fade=Each fade f\IM=FreeAllImage(f\IM) f\IMbuffer=FreeAllImage(f\IMbuffer) If f\BNKbuffer<>0 Then FreeBank f\BNKbuffer : f\BNKbuffer=0 Delete f Next ; If you use a low detail in your game, here would be a good place to filter out cpu heavy fades f.fade=New fade f\spd=spd : f\acl=acl ; * Set em up Select fadetype Case FADnone Case FADcircle ; a few defaults to fix bogus values If f\spd=0 Then f\spd=4 : f\acl=0.05 If f\acl=0 Then f\acl=f\spd/80 If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 f\IMbuffer=CreateImage(SCRwid,SCRhi,1,2) If f\spd>0 Then f\size=SCRwid*1.25 Else f\size=0 ; get starting size of circle Case FADhatch ; default value If f\spd=0 Then f\spd=10 : f\acl=0 If f\spd>0 f\y=0 : f\flag1=False : f\flag2=SCRhi Else f\y=SCRhi : f\flag1=True : f\flag2=0 : f\acl=f\acl*-1 EndIf ; create a 2 px high hatched image f\IM=CreateImage(SCRwid+5,1) SetBuffer ImageBuffer(f\IM) ClsColor 0,0,COLshadow : Cls LockBuffer() : For x=0 To SCRwid+4 Step 2 : WritePixelFast x,y,0 : Next : UnlockBuffer() Case FADbox ; * WARNING: this assumes normal 4:3 screen ratios (640x480, 800x600 ect) ; Set default or check values will work If f\spd=0 Then f\spd=6 : f\acl=0.08 If f\acl=0 Then f\acl=f\spd/80 Else f\acl=acl If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 ; prevents failed (i.e. reversing) box fades ; set up fade If f\spd>0 Then f\size=SCRwid Else f\size=0 Case FADdropdown ; set default (but f\spd=-10 : f\acl=0.5 is very cool) If f\spd=0 Then f\spd=1 : f\acl=0.5 If f\acl=0 Then f\acl=0.5 If f\acl<0 Then f\acl=f\acl*-1 If f\spd>0 f\y=-SCRhi :f\flag1=True Else f\y=0 : f\flag1=False EndIf Case FADragged If f\spd=0 Then f\spd=10 : f\acl=0.1 ; default If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 ; prevent failure of fade wid=20 If f\spd>0 Then f\x=-wid-(SCRwid/7) Else f\x=SCRwid+wid+(SCRwid/7) f\IM=CreateImage(wid,SCRhi,1,2) SetBuffer ImageBuffer(f\IM) Color 0,0,COLshadow If f\spd>0 Then x=0 : dir=0 Else x=wid : dir=1 ; Create ragged edge. For y=0 To SCRhi If dir=0 Then r=Rand(0,1) Else r=Rnd(-1,0) If Rand(0,15)=10 Then r=Rand(-8,8) If Rand(0,30)=10 Then dir=1-dir x=x+r If x=>wid Then x=wid : dir=1-dir If x<0 Then x=0 : dir=1-dir Rect 0,y,x,1 Next ; Nice point to play a swishy sound effect. Case FADpixelST ; Simple but fast pixellation. f\BNKbuffer=ImagetoBank(buf) ; set the default, very low values work best for fadeouts, around 3 or so is good for fadeins. If f\spd=0 Then f\spd=0.3 If f\spd>0 f\size=2 : f\flag1=0 Else f\acl=0.05 f\size=90 : f\flag1=255 EndIf Case FADrgbfadeST ; alright, fade to black, but uses a static screen copy for speed. f\BNKbuffer=ImagetoBank(buf) f\IMbuffer=CreateImage(SCRwid,SCRhi,1,2) SetBuffer(ImageBuffer(f\IMbuffer)) ; set defaults, this fade is less impressive with high acceleration. If f\spd=0 Then f\spd=10 : f\acl=0.05 If f\spd>0 f\flag1=0 ; set destination rgb CopyRect 0,0,SCRwid,SCRhi,0,0,BackBuffer(),ImageBuffer(f\IMbuffer) Else f\flag1=255 Color 0,0,COLshadow : Rect 0,0,SCRwid,SCRhi,True EndIf If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 ; prevents failed (i.e. reversing) fades Case FADrgbdrop ; fade to black using a bar down the screen f\flag1=25 ; size of bar If f\spd>0 f\y=-f\flag1 Else f\y=SCRhi EndIf If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 ; prevents failed (i.e. reversing) fades Case FADrgbdropST ; fade to black using a bar down the screen f\flag1=160 ; size of bar f\BNKbuffer=ImagetoBank(buf) f\IMbuffer=CreateImage(SCRwid,SCRhi,1,2) If f\spd=0 Then f\spd=3 If f\spd>0 f\y=0 Else f\y=SCRhi EndIf If Sgn(f\spd)<>Sgn(f\acl) Then f\acl=f\acl*-1 ; prevents failed (i.e. reversing) fades Default RuntimeError "Fade "+fade+" is an unknown number for SetFade()" End Select SetBuffer buf f\kind=fadetype : f\done=False End Function ; Main fade loop, call me once pre game frame. Function Dofade() buf=GraphicsBuffer() ; Technically you can combine fades, but in reality there is little compatible with each other. done=0 For f.fade=Each fade num=num+1 ; count the fades If f\done=True Then f\kind=FADnone ; Decide wheter to clear the screen copy each frame If f\IMbuffer<>0 SetBuffer ImageBuffer(f\IMbuffer) Select f\kind Case FADrgbfadeST ; not all screen fades should clear the image buffer Default ClsColor 0,0,0 : Cls End Select EndIf Select f\kind Case FADnone ; None, SetBuffer buf : Cls : Flip : Cls f\done=True Case FADcircle ; * Mario style CIRCLE fade ClsColor 0,0,COLshadow : Cls If f\size>0 Color 0,0,0 : Oval (SCRwid-f\size)/2,(SCRhi-f\size)/2,f\size,f\size,True EndIf f\spd=f\spd+f\acl f\size=f\size-f\spd If f\spd>0 And f\size<-(f\spd*4) Then f\done=True If f\spd<1 And f\size>SCRwid*1.25 Then f\done=True Case FADhatch ; * Hatched double pass fade SetBuffer buf f\spd=f\spd+f\acl For y=0 To f\y DrawImage f\IM,-1+f\x,y : f\x=1-f\x Next If f\flag1=False f\y=f\y+f\spd If f\spd>0 And f\y>SCRhi+(f\spd*4) Then f\flag1=True If f\spd<0 And f\y<(f\spd*4) Then f\done=True Else f\flag2=f\flag2-f\spd If f\spd>0 And f\flag2<-(f\spd*4) Then f\done=True If f\spd<0 And f\flag2>SCRhi Then f\flag1=False Color 0,0,COLshadow : Rect 0,f\flag2,SCRwid,SCRhi*1.5,True EndIf Case FADbox ; * Boring box fade SetBuffer buf Color 0,0,COLshadow If f\size>0 Rect 0,0,SCRwid,((SCRhi-(f\size*0.75))/2),True ; top Rect ((SCRwid-f\size)/2)+f\size,0,SCRwid,SCRhi,True ; right Rect 0,((SCRhi-(f\size*0.75))/2)+f\size*0.75,SCRwid,SCRhi,True ; bottom Rect 0,0,(SCRwid-f\size)/2,SCRhi,True ; left Else Rect 0,0,SCRwid,SCRhi,True EndIf f\spd=f\spd+f\acl f\size=f\size-f\spd : f\y=f\y-f\spd If f\spd>0 And f\size<-(f\spd*6) Then f\done=True If f\spd<0 And f\size>SCRwid Then f\done=True Case FADdropdown ; * Screen drops down / off SetBuffer buf CopyRect 0,0,SCRwid,SCRhi,0,f\y,buf,buf : Color 0,0,COLshadow Rect 0,f\y+SCRhi,SCRwid,SCRhi-f\y f\spd=f\spd+f\acl If f\flag1=True f\y=f\y+f\spd If f\y>0 If f\spd<1 f\spd=0 : f\y=0 : f\done=True Else f\y=0 : f\spd=f\spd*-0.75 ; good point to play any bouncing sfx for the screen. EndIf EndIf Else Rect 0,0,SCRwid,f\y f\y=f\y+f\spd If f\y>SCRhi*1.25 Then f\done=True EndIf Case FADragged ; Chrono Trigger style screen wipe SetBuffer buf Color 0,0,COLshadow : Rect 0,0,f\x,SCRhi DrawImage f\IM,f\x,0 f\spd=f\spd+f\acl : f\x=f\x+f\spd If f\spd>0 And f\x>SCRwid+120 Then f\done=True If f\spd<0 And f\x<-20 Then f\done=True ; Good point to pan any swish sounds you played Case FADpixelST ; SNES style pixellation f\x=0 : size%=Int(f\size) ; figure out how far through the fade we are from 0-1 prop#=1-Float(f\flag1/255) LockBuffer buf ClsColor 0,0,COLshadow : Cls Repeat f\y=0 Repeat x=f\x : If x>SCRwid-1 Then x=SCRwid-1 y=f\y : If y>SCRhi-1 Then y=SCRhi-1 adr=((y*SCRwid)+x)*(SCRdep/8) If SCRdep=32 rgb=PeekInt(f\BNKbuffer,adr) ; a neat little sum to cut out any if statements rgb=((rgb And $FF)*prop)+((((rgb Shr 8) And $FF)*prop) Shl 8)+((((rgb Shr 16) And $FF)*prop) Shl 16) Else rgb=PeekShort(f\BNKbuffer,adr) rgb=((rgb And $1F)*prop*8)+((((rgb Shr 5) And $3F)*prop*4) Shl 8)+((((rgb Shr 11) And $1F)*prop*8) Shl 16) EndIf centre#=Float(size)/1.5 : x=f\x-centre : y=f\y-centre size=size-1 : wid=SCRwid : hi=SCRhi For ax=0 To size For ay=0 To size If x+ax<wid And y+ay<hi And x+ax>-1 And y+ay>-1 WritePixelFast x+ax,y+ay,rgb EndIf Next Next size=size+1 f\y=f\y+size Until f\y=>SCRhi+size f\x=f\x+size Until f\x=>SCRwid+size UnlockBuffer() ; check colour fade and set an appropriate alpha If f\spd>0 Then f\flag1=f\flag1+(f\spd*3) Else f\flag1=f\flag1+(f\spd*3) If f\flag1>255 Then f\flag1=255 If f\flag1<0 Then f\flag1=0 ; Figure out if it's finished If f\spd>0 And f\size>90 Then f\done=True If f\spd<0 And f\size=2 Then f\done=True f\spd=f\spd+f\acl If f\spd<0 And f\spd>-0.6 Then f\spd=-0.6 f\size=f\size+f\spd : If f\size<2 Then f\size=2 Case FADrgbfadeST ; Static screen RGB fadeout prop#=1-(f\flag1/255) LockBuffer(ImageBuffer(f\IMbuffer)) wid=SCRwid-1 : hi=SCRhi-1 ; how many pixels to skip this pass, 1,2,3 and 6 are good values. f\size=2 ; certain sizes need this fix to ensure hatching alternates pixels each frame If f\size=1 Or f\size=3 f\flag2=f\flag2+1 : If f\flag2>f\size Then f\flag2=0 EndIf For x=0 To wid For y=0+f\flag2 To hi adr=((y*SCRwid)+x)*SCRbytes If SCRdep=32 rgb=PeekInt(f\BNKbuffer,adr) WritePixelFast x,y,((rgb And $FF)*prop)+((((rgb Shr 8) And $FF)*prop) Shl 8)+((((rgb Shr 16) And $FF)*prop) Shl 16) Else rgb=PeekShort(f\BNKbuffer,adr) WritePixelFast x,y,((rgb And $1F)*prop*8)+((((rgb Shr 5) And $3F)*prop*4) Shl 8)+((((rgb Shr 11) And $1F)*prop*8) Shl 16) EndIf y=y+f\size Next f\flag2=f\flag2+1 : If f\flag2>f\size Then f\flag2=0 Next UnlockBuffer() f\flag1=Int(f\flag1+f\spd) f\spd=f\spd+f\acl If f\flag1<0 Then f\flag1=0 : f\done=True If f\flag1>255 Then f\flag1=255 : f\done=True Case FADrgbdrop ; Thin fading bar wiping the screen ; first decide if the bar is coming up or down. If f\spd>0 y=f\y-f\flag1 Else y=f\y+f\flag1 EndIf hi=0 LockBuffer(BackBuffer()) For n=1 To f\flag1 ; okay let's decided how big the bar is. If y>-1 And y<SCRhi prop=0.99-((Abs(f\y-y))/f\flag1) If prop<0 Then prop=0 If f\spd<0 Then prop=0.99-prop If prop>0.2 For x=0 To SCRwid-1 rgb=ReadPixelFast(x,y) WritePixelFast x,y,((rgb And $FF)*prop)+((((rgb Shr 8) And $FF)*prop) Shl 8)+((((rgb Shr 16) And $FF)*prop) Shl 16) Next Else ; find out where we draw the black retangle to. If f\spd>0 Then hi=y ElseIf hi=0 Then hi=y EndIf EndIf y=y+Sgn(f\spd) Next UnlockBuffer() Color 0,0,COLshadow f\y=f\y+f\spd f\spd=f\spd+f\acl If f\spd>0 Rect 0,0,SCRwid,hi+1,True If f\y=>SCRhi+f\flag1 Then f\done=True Else Rect 0,0,SCRwid,hi+1,True If f\y<-f\flag1 Then f\done=True EndIf Case FADrgbdropST ; Large fading effect passing downscreen, Static screen only. ; first decide if the bar is coming down or up, If f\spd>0 y=f\y-f\flag1 Else y=f\y+f\flag1 EndIf hi=0 LockBuffer(ImageBuffer(f\IMbuffer)) For n=1 To f\flag1 ; okay let's decided how big the bar is. If y>-1 And y<SCRhi prop=1-((Abs(f\y-y))/f\flag1) If prop<0 Then prop=0 If f\spd<0 Then prop=1-prop If prop>0.11 For x=0+f\flag2 To SCRwid-1 adr=((y*SCRwid)+x)*SCRbytes If SCRdep=32 rgb=PeekInt(f\BNKbuffer,adr) WritePixelFast x,y,((rgb And $FF)*prop)+((((rgb Shr 8) And $FF)*prop) Shl 8)+((((rgb Shr 16) And $FF)*prop) Shl 16) Else rgb=PeekShort(f\BNKbuffer,adr) WritePixelFast x,y,((rgb And $1F)*prop*8)+((((rgb Shr 5) And $3F)*prop*4) Shl 8)+((((rgb Shr 11) And $1F)*prop*8) Shl 16) EndIf Next Else If f\spd>0 Then hi=y ElseIf hi=0 Then hi=y EndIf EndIf y=y+Sgn(f\spd) Next UnlockBuffer() Color 0,0,COLshadow If f\spd>0 Rect 0,0,SCRwid,hi+1,True If f\y=>SCRhi+f\flag1 Then f\done=True Else Rect 0,0,SCRwid,hi+1,True If f\y<-f\flag1 Then f\done=True EndIf f\y=f\y+f\spd f\spd=f\spd+f\acl Default RuntimeError "You haven't specified a valid fade type for SetFade()" End Select ; The fade is done, but let's make extra sure it's blacked out the screen. If f\spd>0 And f\done=True Then Color 0,0,COLshadow : Rect 0,0,SCRwid,SCRhi SetBuffer(buf) If f\IMbuffer<>0 Select f\kind Case FADrgbfadeST DrawBlock f\IMbuffer,0,0 Default DrawImage f\IMbuffer,0,0 End Select EndIf If f\done=True f\IMbuffer=FreeAllImage(f\IMbuffer) : f\IM=FreeAllImage(f\IM) If f\BNKbuffer<>0 Then FreeBank f\BNKbuffer : f\BNKbuffer=0 Delete f done=done+1 EndIf Next If done=num Then done=True Else done=False Return done End Function ; create a bank using an image or backbuffer Function ImagetoBank(image) If image=BackBuffer() LockBuffer(BackBuffer()) wid=SCRwid : hi=SCRhi Else LockBuffer(ImageBuffer(image)) wid=ImageWidth(image) : hi=ImageHeight(image) EndIf bank=CreateBank(wid*SCRbytes*hi+4096) imagebank=LockedPixels() pitch=LockedPitch() imoff=0 : bnkoff=0 ; copy bank to image line by line For y=1 To hi CopyBank imagebank,imoff,bank,bnkoff,wid*SCRbytes bnkoff=bnkoff+(wid*SCRbytes) imoff=imoff+pitch Next UnlockBuffer() Return bank End Function ; Prevents the infamous memory leaks. Function FreeAllImage(IMtemp) If IMtemp<>0 Then FreeImage IMtemp Return False End Function