Playing a Flash movie from memory (no temporary files)

Share your advanced PureBasic knowledge/code with the community.
Esteban1
User
User
Posts: 37
Joined: Sat Jul 16, 2005 4:39 pm
Location: Uruguay

Playing a Flash movie from memory (no temporary files)

Post by Esteban1 »

This is a little trick I recently discovered. It can be adapted to load a movie from resources.

Code: Select all

; 
; Embedded flash player example (ActiveX) 
; 
; By AlphaSND 
; 
; Translated to PB4 by Flype
; Playing from included data by Esteban1
;
; Flash ActiveX interface definition 
; 

Interface IShockwaveFlash Extends IDispatch 
  get_ReadyState(a) 
  get_TotalFrames(a) 
  get_Playing(a) 
  put_Playing(a) 
  get_Quality(a) 
  put_Quality(a) 
  get_ScaleMode(a) 
  put_ScaleMode(a) 
  get_AlignMode(a) 
  put_AlignMode(a) 
  get_BackgroundColor(a) 
  put_BackgroundColor(a) 
  get_Loop(a) 
  put_Loop(a) 
  get_Movie(a) 
  put_Movie(a) 
  get_FrameNum(a) 
  put_FrameNum(a) 
  SetZoomRect(a,b,c,d) 
  Zoom(a) 
  Pan(a,b,c) 
  Play() 
  Stop() 
  Back() 
  Forward() 
  Rewind() 
  StopPlay() 
  GotoFrame(a) 
  CurrentFrame(a) 
  IsPlaying(a) 
  PercentLoaded(a) 
  FrameLoaded(a,b) 
  FlashVersion(a) 
  get_WMode(a) 
  put_WMode(a) 
  get_SAlign(a) 
  put_SAlign(a) 
  get_Menu(a) 
  put_Menu(a) 
  get_Base(a) 
  put_Base(a) 
  get_scale(a) 
  put_scale(a) 
  get_DeviceFont(a) 
  put_DeviceFont(a) 
  get_EmbedMovie(a) 
  put_EmbedMovie(a) 
  get_BGColor(a) 
  put_BGColor(a) 
  get_Quality2(a) 
  put_Quality2(a) 
  LoadMovie(a,b.p-bstr) 
  TGotoFrame(a,b) 
  TGotoLabel(a,b) 
  TCurrentFrame(a,b) 
  TCurrentLabel(a,b) 
  TPlay(a) 
  TStopPlay(a) 
  SetVariable(a,b.p-bstr) 
  GetVariable(a,b.p-bstr) 
  TSetProperty(a,b,c) 
  TGetProperty(a,b,c) 
  TCallFrame(a,b) 
  TCallLabel(a,b) 
  TSetPropertyNum(a,b,c) 
  TGetPropertyNum(a,b,c) 
  get_SWRemote(a) 
  put_SWRemote(a) 
  get_Stacking(a) 
  put_Stacking(a) 
EndInterface 

Prototype AtlAxWinInit() 
Prototype AtlAxCreateControl(a.p-bstr,b.l,c.l,d.l) 
Prototype AtlAxGetControl(a.l,b.l) 

Procedure.l FlashLoadFromData(SwfStart.l,SwfEnd.l,*FlashObject.IShockwaveFlash)
  FlashBuffer=AllocateMemory(SwfEnd-SwfStart+8) ; let's make room
  If FlashBuffer
    PokeL(FlashBuffer,$55665566) ;now write the header
    PokeL(FlashBuffer+4,SwfEnd-SwfStart) ; and the file size
    CopyMemory(SwfStart,FlashBuffer+8,SwfEnd-SwfStart) ; then copy the whole file.
    If CreateStreamOnHGlobal_(FlashBuffer,#True,@FlashStream.IStream)=0 ;Create a stream.
      *FlashObject\QueryInterface(?IID_IPersistStreamInit,@FlashPSI.IPersistStreamInit) ; Ask for IPersistStreamInit interface     
      If FlashPSI 
        If FlashPSI\load(FlashStream)=0 ;load the stream we created
          ReturnValue=1
        EndIf
        FlashPSI\Release(); self explained
      EndIf  
      FlashStream\Release() ; idem
    EndIf
    FreeMemory(FlashBuffer) ;idem
  EndIf
  ProcedureReturn ReturnValue
EndProcedure

If OpenLibrary(0,"atl.dll") 
  AtlAxWinInit.AtlAxWinInit             = GetFunction(0, "AtlAxWinInit") 
  AtlAxCreateControl.AtlAxCreateControl = GetFunction(0, "AtlAxCreateControl") 
  AtlAxGetControl.AtlAxGetControl       = GetFunction(0, "AtlAxGetControl") 
Else 
  MessageRequester("Error", "OpenLibrary() failed.") 
  End 
EndIf 

;Movie$ = "c:\clock.swf" 
;Movie$ = "c:\\WINDOWS\\Help\\Tours\\mmTour\\segment1.swf" 

CoInitialize_(0) 

If OpenWindow(0, 100, 100, 300, 315, "") 
  
  CreateGadgetList(WindowID(0)) 
  ContainerGadget(0, 0, 0, 300, 275) ; This will be our container window, where the ActiveX will be rendered 
  CloseGadgetList() 
  
  ButtonGadget(1, 10, 285, 70, 25, "Play", #PB_Button_Toggle) 
  ;ButtonGadget(2, 90, 285, 70, 25, "Play") 
  
  If AtlAxWinInit() 
    
    AtlAxCreateControl("ShockwaveFlash.ShockwaveFlash", GadgetID(0), 0, @Container.IUnknown) ; It always create the IE control even if flash isn't found 
    
    If Container 
      
      AtlAxGetControl(GadgetID(0),@oFlash.IShockwaveFlash) 
      
      If oFlash 
        
        If oFlash\QueryInterface(?IID_ShockwaveFlash, @oFlash) = 0 ; Be sure it's a flash object in the IE container 
          
          ;oFlash\LoadMovie(0, Movie$)
          FlashLoadFromData(?FlashFileStart,?FlashFileEnd,oFlash) ; Let's get it from included data
          oFlash\get_ReadyState(@state)   ; 0=Loading, 1=Uninitialized, 2=Loaded, 3=Interactive, 4=Complete.  
          
          Select state 
            Case 4 , 3 
              ;oFlash\Play() 
              oFlash\FlashVersion(@Version) 
              Debug "Flash Version: " + Hex(Version) 
              ;oFlash\put_BackgroundColor($000000) 
              oFlash\get_BackgroundColor(@BackColor) 
              Debug "BackColor: " + Hex(BackColor) 
            Default 
              Debug state 
              MessageRequester("Error", "The movie can't be loaded ("+Movie$+")") 
          EndSelect 
          oFlash\put_Quality(0) 
          Repeat 
            Select WaitWindowEvent(50) 
              Case #PB_Event_CloseWindow 
                Break 
              Case #PB_Event_SizeWindow 
                ResizeGadget(0, #PB_Ignore, #PB_Ignore, WindowWidth(0), WindowHeight(0)-35) 
                ResizeGadget(1, #PB_Ignore, WindowHeight(0)-30, #PB_Ignore, #PB_Ignore) 
                ;ResizeGadget(2, #PB_Ignore, WindowHeight(0)-30, #PB_Ignore, #PB_Ignore) 
              Case #PB_Event_Gadget 
                Select EventGadget() 
                  Case 1 
                    Select GetGadgetState(1) 
                      Case 0 : oFlash\Stop() 
                      Case 1 : oFlash\Play() 
                    EndSelect 
                EndSelect 
            EndSelect 
            oFlash\CurrentFrame(@frame) 
            SetWindowTitle(0, "Frame " + Str(frame)) 
          ForEver 
          
          oFlash\Release() 
          
        EndIf 
        
        oFlash\Release() 
        
      EndIf 
      
    EndIf 
    
  EndIf 
  
  CloseWindow(0)   ; Don't forget this one, else the program will crash 
  
EndIf 

CoUninitialize_() 

End 

DataSection 
IID_ShockwaveFlash: Data.q $11CFAE6DD27CDB6C,$000054534544B896 
IID_IPersistStreamInit:
Data.l $7FD52380
Data.w $4E07,$101B
Data.b $AE,$2D,$08,$00,$2B,$2E,$C7,$13
FlashFileStart:
IncludeBinary "c:\\WINDOWS\\Help\\Tours\\mmTour\\segment1.swf"
FlashFileEnd:
EndDataSection
I don't know if it works for Flash versions other than 8.
User avatar
Rings
Moderator
Moderator
Posts: 1402
Joined: Sat Apr 26, 2003 1:11 am

Post by Rings »

i got an PoLink-Error while compiling:

Unresolved external Symbol:

'_SYS_ToBSTR'


anything missing ?
SPAMINATOR NR.1
J. Baker
Addict
Addict
Posts: 2098
Joined: Sun Apr 27, 2003 8:12 am
Location: USA
Contact:

Post by J. Baker »

Works fine here with flash player 9. :wink:
www.posemotion.com

PureBasic Tools for OS X: PureMonitor, plist Tool, Data Maker & App Chef

Mac: 10.13.6 / 1.4GHz Core 2 Duo / 2GB DDR3 / Nvidia 320M
PC: Win 7 / AMD 64 4000+ / 3GB DDR / Nvidia 720GT


Even the vine knows it surroundings but the man with eyes does not.
Esteban1
User
User
Posts: 37
Joined: Sat Jul 16, 2005 4:39 pm
Location: Uruguay

Post by Esteban1 »

Rings wrote:i got an PoLink-Error while compiling:

Unresolved external Symbol:

'_SYS_ToBSTR'


anything missing ?
Oops...
My only contribution in the previous code is the FlashLoadFromData procedure. Did you try the original source?
http://www.purebasic.fr/english/viewtopic.php?t=20428
User avatar
Rings
Moderator
Moderator
Posts: 1402
Joined: Sat Apr 26, 2003 1:11 am

Post by Rings »

the bug is in:

Prototype AtlAxCreateControl(a.p-bstr,b.l,c.l,d.l)

and the call

AtlAxCreateControl("ShockwaveFlash.ShockwaveFlash", GadgetID(0), 0, @Container.IUnknown)

its the p-bstr typecasting
SPAMINATOR NR.1
User avatar
Rings
Moderator
Moderator
Posts: 1402
Joined: Sat Apr 26, 2003 1:11 am

Post by Rings »

solved with an update from Beta11 to a Releaseversion.
SPAMINATOR NR.1
User avatar
bingo
Enthusiast
Enthusiast
Posts: 210
Joined: Fri Apr 02, 2004 12:21 pm
Location: germany/thueringen
Contact:

Post by bingo »

:D also works in VISTA :!:
["1:0>1"]
J. Baker
Addict
Addict
Posts: 2098
Joined: Sun Apr 27, 2003 8:12 am
Location: USA
Contact:

Post by J. Baker »

EDIT Better code, a couple post down. ;)
Last edited by J. Baker on Fri Feb 08, 2008 1:42 am, edited 2 times in total.
www.posemotion.com

PureBasic Tools for OS X: PureMonitor, plist Tool, Data Maker & App Chef

Mac: 10.13.6 / 1.4GHz Core 2 Duo / 2GB DDR3 / Nvidia 320M
PC: Win 7 / AMD 64 4000+ / 3GB DDR / Nvidia 720GT


Even the vine knows it surroundings but the man with eyes does not.
wilbert
PureBasic Expert
PureBasic Expert
Posts: 3715
Joined: Sun Aug 08, 2004 5:21 am
Location: Netherlands

Post by wilbert »

I'm trying to display a flash movie with a transparent background.
I used AtlAxAttachControl and set wmode to transparent but the background keeps black all the time.

Does someone know what I'm doing wrong ?

Code: Select all

Interface IShockwaveFlash Extends IDispatch
  get_ReadyState(a)
  get_TotalFrames(a)
  get_Playing(a)
  put_Playing(a)
  get_Quality(a)
  put_Quality(a)
  get_ScaleMode(a)
  put_ScaleMode(a)
  get_AlignMode(a)
  put_AlignMode(a)
  get_BackgroundColor(a)
  put_BackgroundColor(a)
  get_Loop(a)
  put_Loop(a)
  get_Movie(a)
  put_Movie(a)
  get_FrameNum(a)
  put_FrameNum(a)
  SetZoomRect(a,b,c,d)
  Zoom(a)
  Pan(a,b,c)
  Play()
  Stop()
  Back()
  Forward()
  Rewind()
  StopPlay()
  GotoFrame(a)
  CurrentFrame(a)
  IsPlaying(a)
  PercentLoaded(a)
  FrameLoaded(a,b)
  FlashVersion(a)
  get_WMode(a)
  put_WMode(a.p-bstr)
  get_SAlign(a)
  put_SAlign(a)
  get_Menu(a)
  put_Menu(a)
  get_Base(a)
  put_Base(a)
  get_scale(a)
  put_scale(a)
  get_DeviceFont(a)
  put_DeviceFont(a)
  get_EmbedMovie(a)
  put_EmbedMovie(a)
  get_BGColor(a)
  put_BGColor(a)
  get_Quality2(a)
  put_Quality2(a)
  LoadMovie(a,b.p-bstr)
  TGotoFrame(a,b)
  TGotoLabel(a,b)
  TCurrentFrame(a,b)
  TCurrentLabel(a,b)
  TPlay(a)
  TStopPlay(a)
  SetVariable(a,b.p-bstr)
  GetVariable(a,b.p-bstr)
  TSetProperty(a,b,c)
  TGetProperty(a,b,c)
  TCallFrame(a,b)
  TCallLabel(a,b)
  TSetPropertyNum(a,b,c)
  TGetPropertyNum(a,b,c)
  get_SWRemote(a)
  put_SWRemote(a)
  get_Stacking(a)
  put_Stacking(a)
EndInterface

Prototype AtlAxAttachControl(a.l,b.l,c.l)

Procedure.l FlashLoadFromData(SwfStart.l,SwfEnd.l,*FlashObject.IShockwaveFlash)
  FlashBuffer=AllocateMemory(SwfEnd-SwfStart+8) ; let's make room
  If FlashBuffer
    PokeL(FlashBuffer,$55665566) ;now write the header
    PokeL(FlashBuffer+4,SwfEnd-SwfStart) ; and the file size
    CopyMemory(SwfStart,FlashBuffer+8,SwfEnd-SwfStart) ; then copy the whole file.
    If CreateStreamOnHGlobal_(FlashBuffer,#True,@FlashStream.IStream)=0 ;Create a stream.
      *FlashObject\QueryInterface(?IID_IPersistStreamInit,@FlashPSI.IPersistStreamInit) ; Ask for IPersistStreamInit interface     
      If FlashPSI
        If FlashPSI\load(FlashStream)=0 ;load the stream we created
          ReturnValue=1
        EndIf
        FlashPSI\Release(); self explained
      EndIf 
      FlashStream\Release() ; idem
    EndIf
    FreeMemory(FlashBuffer) ;idem
  EndIf
  ProcedureReturn ReturnValue
EndProcedure

If OpenLibrary(0,"atl.dll")
  AtlAxAttachControl.AtlAxAttachControl = GetFunction(0, "AtlAxAttachControl")
Else
  MessageRequester("Error", "OpenLibrary() failed.")
  End
EndIf

CoInitialize_(0)

If OpenWindow(0, 100, 100, 370, 370,"FlashPlayer",#PB_Window_ScreenCentered | #PB_Window_BorderLess)
 
  SetWindowLong_(WindowID(0),#GWL_EXSTYLE,GetWindowLong_(WindowID(0),#GWL_EXSTYLE)|#WS_EX_TRANSPARENT)

  CoCreateInstance_(?IID_ShockwaveFlash, 0, $17, ?IID_IShockwaveFlash, @oFlash.IShockwaveFlash)

  If oFlash

    oFlash\put_WMode("Transparent")
    AtlAxAttachControl(oFlash, WindowID(0), 0)
      
    FlashLoadFromData(?FlashFileStart,?FlashFileEnd,oFlash)

    Repeat
      WaitWindowEvent()
    Until GetAsyncKeyState_(#VK_ESCAPE)
         
    oFlash\Release()
         
  EndIf
 
  CloseWindow(0)
 
EndIf

CoUninitialize_()

End

DataSection

IID_IShockwaveFlash:
Data.q $11CFAE6DD27CDB6C,$000054534544B896

IID_ShockwaveFlash:
Data.q $11CFAE6DD27CDB6E,$000054534544B896

IID_IPersistStreamInit:
Data.q $101B4E077FD52380,$13C72E2B00082DAE

FlashFileStart:
IncludeBinary "wood.swf"
FlashFileEnd:
EndDataSection
Esteban1
User
User
Posts: 37
Joined: Sat Jul 16, 2005 4:39 pm
Location: Uruguay

Post by Esteban1 »

wilbert wrote:I'm trying to display a flash movie with a transparent background.
I used AtlAxAttachControl and set wmode to transparent but the background keeps black all the time.

Does someone know what I'm doing wrong ?
Hmmm...

I'm not sure but I think that's not possible using ATL.

You should use COMFramework to make your own container because the only way to get a real transparent background is to use the windowless mode.
Take a look at this.
J. Baker
Addict
Addict
Posts: 2098
Joined: Sun Apr 27, 2003 8:12 am
Location: USA
Contact:

Post by J. Baker »

Not the best but it has transparency and you are able to click through the transparency. It's also dragable. ;)

Code: Select all

Interface IShockwaveFlash Extends IDispatch
  get_ReadyState(a)
  get_TotalFrames(a)
  get_Playing(a)
  put_Playing(a)
  get_Quality(a)
  put_Quality(a)
  get_ScaleMode(a)
  put_ScaleMode(a)
  get_AlignMode(a)
  put_AlignMode(a)
  get_BackgroundColor(a)
  put_BackgroundColor(a)
  get_Loop(a)
  put_Loop(a)
  get_Movie(a)
  put_Movie(a)
  get_FrameNum(a)
  put_FrameNum(a)
  SetZoomRect(a,b,c,d)
  Zoom(a)
  Pan(a,b,c)
  Play()
  Stop()
  Back()
  Forward()
  Rewind()
  StopPlay()
  GotoFrame(a)
  CurrentFrame(a)
  IsPlaying(a)
  PercentLoaded(a)
  FrameLoaded(a,b)
  FlashVersion(a)
  get_WMode(a)
  put_WMode(a.p-bstr)
  get_SAlign(a)
  put_SAlign(a)
  get_Menu(a)
  put_Menu(a)
  get_Base(a)
  put_Base(a)
  get_scale(a)
  put_scale(a)
  get_DeviceFont(a)
  put_DeviceFont(a)
  get_EmbedMovie(a)
  put_EmbedMovie(a)
  get_BGColor(a)
  put_BGColor(a)
  get_Quality2(a)
  put_Quality2(a)
  LoadMovie(a,b.p-bstr)
  TGotoFrame(a,b)
  TGotoLabel(a,b)
  TCurrentFrame(a,b)
  TCurrentLabel(a,b)
  TPlay(a)
  TStopPlay(a)
  SetVariable(a,b.p-bstr)
  GetVariable(a,b.p-bstr)
  TSetProperty(a,b,c)
  TGetProperty(a,b,c)
  TCallFrame(a,b)
  TCallLabel(a,b)
  TSetPropertyNum(a,b,c)
  TGetPropertyNum(a,b,c)
  get_SWRemote(a)
  put_SWRemote(a)
  get_Stacking(a)
  put_Stacking(a)
EndInterface

Prototype AtlAxAttachControl(a.l,b.l,c.l)

Procedure.l FlashLoadFromData(SwfStart.l,SwfEnd.l,*FlashObject.IShockwaveFlash)
  FlashBuffer=AllocateMemory(SwfEnd-SwfStart+8) ; let's make room
  If FlashBuffer
    PokeL(FlashBuffer,$55665566) ;now write the header
    PokeL(FlashBuffer+4,SwfEnd-SwfStart) ; and the file size
    CopyMemory(SwfStart,FlashBuffer+8,SwfEnd-SwfStart) ; then copy the whole file.
    If CreateStreamOnHGlobal_(FlashBuffer,#True,@FlashStream.IStream)=0 ;Create a stream.
      *FlashObject\QueryInterface(?IID_IPersistStreamInit,@FlashPSI.IPersistStreamInit) ; Ask for IPersistStreamInit interface     
      If FlashPSI
        If FlashPSI\load(FlashStream)=0 ;load the stream we created
          ReturnValue=1
        EndIf
        FlashPSI\Release(); self explained
      EndIf
      FlashStream\Release() ; idem
    EndIf
    FreeMemory(FlashBuffer) ;idem
  EndIf
  ProcedureReturn ReturnValue
EndProcedure

If OpenLibrary(0,"atl.dll")
  AtlAxAttachControl.AtlAxAttachControl = GetFunction(0, "AtlAxAttachControl")
Else
  MessageRequester("Error", "OpenLibrary() failed.")
  End
EndIf

CoInitialize_(0)

If OpenWindow(0,0,0,320,240,"",#PB_Window_ScreenCentered|#PB_Window_BorderLess)
 
HideWindow(0, 1)

SetWindowLong_(WindowID(0),#GWL_EXSTYLE,GetWindowLong_(WindowID(0),#GWL_EXSTYLE)|#WS_EX_LAYERED) 

SetLayeredWindowAttributes_(WindowID(0),RGB(0,0,0),0,#LWA_COLORKEY)

CoCreateInstance_(?IID_ShockwaveFlash, 0, $17, ?IID_IShockwaveFlash, @oFlash.IShockwaveFlash)

  If oFlash

    oFlash\put_WMode("Transparent")
    oFlash\put_Quality(1)
    
    AtlAxAttachControl(oFlash, WindowID(0), 0)
     
    FlashLoadFromData(?FlashFileStart,?FlashFileEnd,oFlash)
    
    Delay(100) 
    HideWindow(0, 0)

    Repeat
      Event = WaitWindowEvent()
      
      If Event = #WM_LBUTTONDOWN
       SendMessage_(WindowID(0) ,#WM_NCLBUTTONDOWN, #HTCAPTION, 0)
      EndIf
      
    Until GetAsyncKeyState_(#VK_ESCAPE)
         
    oFlash\Release()
         
  EndIf
 
  CloseWindow(0)
 
EndIf

CoUninitialize_()

End

DataSection

IID_IShockwaveFlash:
Data.q $11CFAE6DD27CDB6C,$000054534544B896

IID_ShockwaveFlash:
Data.q $11CFAE6DD27CDB6E,$000054534544B896

IID_IPersistStreamInit:
Data.q $101B4E077FD52380,$13C72E2B00082DAE

FlashFileStart:
IncludeBinary "transparent.swf"
FlashFileEnd:
EndDataSection
www.posemotion.com

PureBasic Tools for OS X: PureMonitor, plist Tool, Data Maker & App Chef

Mac: 10.13.6 / 1.4GHz Core 2 Duo / 2GB DDR3 / Nvidia 320M
PC: Win 7 / AMD 64 4000+ / 3GB DDR / Nvidia 720GT


Even the vine knows it surroundings but the man with eyes does not.
SFSxOI
Addict
Addict
Posts: 2970
Joined: Sat Dec 31, 2005 5:24 pm
Location: Where ya would never look.....

Post by SFSxOI »

I get a 'The memory pointer passed to FreeMemory() is invalid' error at FreeMemory(FlashBuffer)
J. Baker
Addict
Addict
Posts: 2098
Joined: Sun Apr 27, 2003 8:12 am
Location: USA
Contact:

Post by J. Baker »

SFSxOI wrote:I get a 'The memory pointer passed to FreeMemory() is invalid' error at FreeMemory(FlashBuffer)
Yeah, it does that sometimes. I'm not sure why. Just try it until it works.
www.posemotion.com

PureBasic Tools for OS X: PureMonitor, plist Tool, Data Maker & App Chef

Mac: 10.13.6 / 1.4GHz Core 2 Duo / 2GB DDR3 / Nvidia 320M
PC: Win 7 / AMD 64 4000+ / 3GB DDR / Nvidia 720GT


Even the vine knows it surroundings but the man with eyes does not.
User avatar
bingo
Enthusiast
Enthusiast
Posts: 210
Joined: Fri Apr 02, 2004 12:21 pm
Location: germany/thueringen
Contact:

Post by bingo »

in vista easier with SHCreateMemStream ... 8)

http://msdn2.microsoft.com/en-us/librar ... S.85).aspx
["1:0>1"]
J. Baker
Addict
Addict
Posts: 2098
Joined: Sun Apr 27, 2003 8:12 am
Location: USA
Contact:

Post by J. Baker »

I believe since fDeleteOnRelease is set to true, it automatically releases. So that line of code can be removed, I think?
www.posemotion.com

PureBasic Tools for OS X: PureMonitor, plist Tool, Data Maker & App Chef

Mac: 10.13.6 / 1.4GHz Core 2 Duo / 2GB DDR3 / Nvidia 320M
PC: Win 7 / AMD 64 4000+ / 3GB DDR / Nvidia 720GT


Even the vine knows it surroundings but the man with eyes does not.
Post Reply