Lib Screen (Sprite) (PB 6.10)

Advanced game related topics
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

I don't really understand what you mean by try with if = 0 and if = 1?

"- for the color problem:
line 144: If #PB_OS_Windows:rgb=#GL_BGR_EXT:rgba=#GL_BGRA_EXT:Else:rgb=#GL_RGB:rgba=#GL_RGBA:EndIf
try with if 0... and if 1...

- for y-coordinate inversion:
line 533: If #PB_OS_Windows:codevertex=ReplaceString(codevertex,"//invertv","vuv.y=1-vuv.y;"):EndIf
try with if 0... and if 1..."

On line 141 it says - Procedure ImageToGLTextures(image,free=0)
I guessed if = 0 might mean (image, free = 0) so changed it to 1 but it doesn't run if I do that.

And on line 533 the only thing I could see was vuv.y=1 so I changed that to 0 but it made no difference.

Is there something else I should be doing? I'm not much of a programmer and my eyes are bleeding looking at your code. :)

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

I think you're not on the source code of the 1st post!!!
AZJIO
Addict
Addict
Posts: 2141
Joined: Sun May 14, 2017 1:48 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by AZJIO »

pf shadoko wrote: Tue May 21, 2024 5:51 pm @ AZJIO
I know, but the aim is to propose the code on the forum so...
I show other people so that they have a desire to program.
https://usbtor.ru/viewtopic.php?p=102929#102929
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

I just copied the first post to make sure. It's exactly the same.
I have to change the path to /usr/lib64 to run it.
The textures all work nicely but the text is in blue(I didn't know it was supposed to be another colour?).
The text is also upside down.
I don't know how to try your suggestions as I have no idea how your code works? It's way too complicated.
How do you even begin to write that stuff???
I'm struggling to work out how to get a folder of images as thumbnails.

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

@ AZJIO
I'm also trying to make people want to program
but for 3d it's not easy, it must be said that the documentation isn't updated and the examples are very old!
does my latest version work on linux?

@ moulder61
maybe your browser's cache isn't updated
here's the latest version

Code: Select all

;=======================================================
;            Lib screen (Sprite) - pf Shadoko -2024
;=======================================================

EnableExplicit

InitSprite():OpenWindow(0,0,0,10,10,""):OpenWindowedScreen(WindowID(0),0,0,10,10):CloseWindow(0);init opengl to add functions

#PB_Shader_Vector2=2
#PB_Shader_color=10
#GL_TEXTURE0=$84c0
#GL_VERTEX_SHADER = $8B31
#GL_FRAGMENT_SHADER = $8B30
CompilerIf #PB_Compiler_OS = #PB_OS_MacOS
  ImportC "-framework OpenGL"
    glActiveTexture(type.l) As "_glActiveTexture" 
    glCreateShader(type.l) As "_glCreateShader" 
    glCreateProgram() As "_glCreateProgram"
    glDeleteProgram(Program.l) As "_glDeleteProgram"
    glDeleteShader(shader.l) As "_glDeleteShader"
    glCompileShader(shader.l) As  "_glCompileShader"
    glLinkProgram(shader.l) As "_glLinkProgram" 
    glUseProgram(shader.l) As "_glUseProgram" 
    glAttachShader(Program.l, shader.l) As  "_glAttachShader"
    glShaderSource(shader.l, numOfStrings.l, *strings, *lenOfStrings) As  "_glShaderSource"
    glGetUniformLocation(Program, name.p-ascii) As  "_glGetUniformLocation"
    glUniform1i(location, v0) As "_glUniform1i"
    glUniform2i(location, v0, v1) As  "_glUniform2i"
    glUniform1f(location, v0.f) As  "_glUniform1f"
    glUniform1d(location, v0.d) As  "_glUniform1d"
    glUniform2d(location, v0.d, v1.d) As  "_glUniform2d"
    glUniform2f(location, v0.f, v1.f) As  "_glUniform2f"
    glUniform3f(location, v0.f, v1.f, v2.f) As  "_glUniform3f"
    glUniform4f(location, v0.f, v1.f, v2.f, v3.f) As  "_glUniform4f"
    glGetShaderInfoLog(shader, bufSize.l, *length_l, *infoLog) As  "_glGetShaderInfoLog"
  EndImport
  
CompilerElseIf #PB_Compiler_OS = #PB_OS_Linux  
  ImportC "/usr/lib/x86_64-linux-gnu/libGL.so"
    glActiveTexture(type.l)
    glCreateShader(type.l)
    glCreateProgram()
    glDeleteProgram(Program.l)
    glDeleteShader(shader.l)
    glCompileShader(shader.l)
    glLinkProgram(shader.l)
    glUseProgram(shader.l)
    glAttachShader(Program.l, shader.l)
    glShaderSource(shader.l, numOfStrings.l, *strings, *lenOfStrings) : 
    glGetUniformLocation(Program, name.p-ascii)
    glUniform1i(location, v0)
    glUniform2i(location, v0, v1)
    glUniform1d(location, v0.d)
    glUniform2d(location, v0.d, v1.d)
    glUniform1f(location, v0.f)
    glUniform2f(location, v0.f, v1.f)
    glUniform3f(location, v0.f, v1.f, v2.f)
    glUniform4f(location, v0.f, v1.f, v2.f, v3.f)
    glGetShaderInfoLog(shader, bufSize.l, *length_l, *infoLog)
  EndImport
  
CompilerElseIf #PB_Compiler_OS = #PB_OS_Windows
  Macro QUOTE:"
  EndMacro
  Macro _ :,:EndMacro
  Macro mPrototype (nom,params=)
    Prototype  nom(params)
    Global nom.nom=wglGetProcAddress_(QUOTE#nom#QUOTE)
  EndMacro
  
  mPrototype (glActiveTexture,type.l)
  mPrototype (glCreateShader,type.l)
  mPrototype (glCreateProgram)
  mPrototype (glDeleteProgram,Program.l)
  mPrototype (glDeleteShader,shader.l)
  mPrototype (glCompileShader,shader.l)
  mPrototype (glLinkProgram,shader.l)
  mPrototype (glUseProgram,shader.l)
  mPrototype (glAttachShader,Program.l _ shader.l)
  mPrototype (glShaderSource,shader.l _ numOfStrings.l _ *strings _ *lenOfStrings)
  mPrototype (glGetUniformLocation,Program _ name.p-ascii)
  mPrototype (glUniform1i,location _ v0)
  mPrototype (glUniform2i,location _ v0 _ v1)
  mPrototype (glUniform1d,location _ v0.d)
  mPrototype (glUniform2d,location _ v0.d _ v1.d)
  mPrototype (glUniform1f,location _ v0.f)
  mPrototype (glUniform2f,location _ v0.f _ v1.f)
  mPrototype (glUniform3f,location _ v0.f _ v1.f _ v2.f)
  mPrototype (glUniform4f,location _ v0.f _ v1.f _ v2.f _ v3.f)
  mPrototype (glGetShaderInfoLog,shader _ bufSize.l _ *lengthl _ *infoLog)
CompilerEndIf

;============================================================================================ Sprite internal

Structure f2
  x.f
  y.f
EndStructure

Structure sShaderinfo
  num.i          ;shader num
  name.s
  pg.i           ;shader program
  vcode.s
  fcode.s
  Map uloc.i()  ;uniform location
EndStructure

Structure sparam
  nom.s
  type.b
  v0.d
  v1.f
  v2.f
  v3.f
EndStructure

Structure sSpriteinfo
  num.i           ;sprite num
  sh.sShaderinfo  ;shader program
  List tx.i()     ;texture num
  Map param.sparam()
  Tdx.w:Tdy.w
  dx.w:dy.w
  x1.f:y1.f:u1.f:v1.f
  x2.f:y2.f:u2.f:v2.f
  x3.f:y3.f:u3.f:v3.f
  x4.f:y4.f:u4.f:v4.f
  zx.f:zy.f
  ag.f
  xo.f:yo.f
EndStructure

Global s_screendx,s_screendy,s_screendx2,s_screendy2
Global Shadermessage.s,codevertex.s, SHvertex
Global.f glcamx,glcamy,glcamzoom=1,glcamrot,glcami=1,glcamj
Global.f glligthx,glligthy,glligthz,glligthdist,glligthcolor.l=0,glambiantcolor.l=$ffffffff
Global NewMap SpriteInfo.sSpriteinfo()
Global NewMap ShaderInfo.sShaderinfo()

Procedure ImageToGLTextures(image,free=0)
  Protected TextureID,w,h,rgb,rgba
  
  If #PB_OS_Windows:rgb=#GL_BGR_EXT:rgba=#GL_BGRA_EXT:Else:rgb=#GL_RGB:rgba=#GL_RGBA:EndIf
  
  StartDrawing(ImageOutput(image))
  glGenTextures_(1, @TextureID)
  glBindTexture_(#GL_TEXTURE_2D, TextureID)
  glTexParameteri_(#GL_TEXTURE_2D, #GL_TEXTURE_MIN_FILTER, #GL_LINEAR)
  glTexParameteri_(#GL_TEXTURE_2D, #GL_TEXTURE_MAG_FILTER, #GL_LINEAR)
  W = OutputWidth() : H = OutputHeight()
  ;glPixelStorei_(#GL_PACK_ROW_LENGTH,DrawingBufferPitch())
  Select OutputDepth()
    Case 24:glTexImage2D_(#GL_TEXTURE_2D, 0,  #GL_RGB, W, H, 0, rgb, #GL_UNSIGNED_BYTE, DrawingBuffer());  
    Case 32:glTexImage2D_(#GL_TEXTURE_2D, 0,  #GL_RGBA, W, H, 0, rgba, #GL_UNSIGNED_BYTE, DrawingBuffer());  
  EndSelect
  StopDrawing()
  If free:FreeImage(image):EndIf
  ProcedureReturn TextureID  
EndProcedure

Procedure Spriteverif(num)
  If FindMapElement(SpriteInfo(),""+num)=0:MessageRequester("S_ Erreur","Sprite "+num+" does not exist"):CallDebugger:EndIf
EndProcedure

Procedure spritecoord(num)
  Protected.f co,si,xs,ys,xx,yy,zxo,zyo
  
  Macro rot(x,y,xs,ys)
    xx=x-zxo
    yy=y-zyo
    xs= xx*co+yy*si
    ys=-xx*si+yy*co
  EndMacro
  
  With SpriteInfo(""+num)
    co=Cos(\ag):si=Sin(\ag)
    zxo=\xo*\zx
    zyo=\yo*\zy
    rot(0  ,0  ,\x1,\y1)
    rot(\dx,0  ,\x2,\y2)
    rot(\dx,\dy,\x3,\y3)
    rot(0  ,\dy,\x4,\y4)
  EndWith
EndProcedure

Procedure screenpos(*sx.float,*sy.float)
  Protected.f xx,yy
  xx=*sx\f-glcamx-s_screendx2
  yy=*sy\f-glcamy-s_screendy2
  *sx\f= (xx*glcami+yy*glcamj+s_screendx2)
  *sy\f=(-xx*glcamj+yy*glcami+s_screendy2)
EndProcedure

Procedure shaderuniform(*sh.sShaderinfo,nom.s,type,v0.d,v1.f=0,v2.f=0,v3.f=0)
  If FindMapElement(*sh\uloc(),nom)
    Select  type
      Case #PB_Shader_Integer :glUniform1i(*sh\uloc(),v0)
      Case #PB_Shader_Float   :glUniform1f(*sh\uloc(),v0)
      Case #PB_Shader_Vector2 :glUniform2f(*sh\uloc(),v0,v1)
      Case #PB_Shader_Vector3 :glUniform3f(*sh\uloc(),v0,v1,v2)
      Case #PB_Shader_Vector4 :glUniform4f(*sh\uloc(),v0,v1,v2,v3)
      Case #PB_Shader_color   :Protected c.q=v0:glUniform4f(*sh\uloc(),Red(c)/255,Green(c)/255,Blue(c)/255,Alpha(c)/255)
    EndSelect
  EndIf
EndProcedure


;============================================================================================ Sprite public
Enumeration S_unit
  #s_unit_Pixel=0
  #s_unit_UV=1
EndEnumeration

Enumeration s_BlendingMode
  #s_BlendingMode_alphablend
  #s_BlendingMode_add
  #s_BlendingMode_custom
EndEnumeration

Enumeration s_shader2D
  #SHoverlay=1000
  #SHdefault
  #SHblend
  #SHlight
  #SHbump
  #SHflame
  #SHwater
  #SHplasma
  #SHnew
EndEnumeration

Procedure.s supspace(l.s)
  Protected i
  Protected.s ll,ac,c
  
  l=ReplaceString(l,#TAB$," ")
  l=ReplaceString(l,#LF$," ")
  l=ReplaceString(l,#CR$," ")
  i=0:While i<Len(l)
    Repeat
      i+1
      ac=c:c=Mid(l,i,1)
    Until c<>" " Or ac<>" "
    ll+c        
  Wend
  ProcedureReturn Trim(ll)
EndProcedure

Procedure ShaderCompile(shadercode.s,type=#PB_Shader_Fragment,dbg=1)
  Protected shader,gltype, *TxtPointer,Program, Textlength, message.s = Space(1024)
  
  If type=#PB_Shader_Vertex:gltype=#GL_VERTEX_SHADER:Else:gltype=#GL_FRAGMENT_SHADER:EndIf
  shadercode=ReplaceString(shadercode,"%",#CRLF$)
  shader = glCreateShader(gltype)
  *TxtPointer = Ascii(shadercode)
  glShaderSource(shader, 1, @*TxtPointer, #Null)
  glCompileShader(shader)
  glGetShaderInfoLog(shader,1023,@Textlength,@message)
  Shadermessage=PeekS(@message,1023,#PB_Ascii)
  If Shadermessage
    If dbg:Debug "error shader "+shader+#CRLF$+Shadermessage:EndIf
    ProcedureReturn
  EndIf
  ProcedureReturn shader
EndProcedure

Procedure shaderCreate(num,fshadercode.s,vshadercode.s="",name.s="",dbg=1)
  Static numauto=1000000
  Protected vshader,fshader,Program,vfcode.s,ul,txu
  If num=-1:num=numauto:numauto+1:EndIf
  
  If fshadercode="":fshader=#SHdefault:Else:fshader=ShaderCompile(fshadercode,#PB_Shader_Fragment,dbg):EndIf:If fshader=0 :ProcedureReturn :EndIf
  If vshadercode="":vshadercode=codevertex:vshader=SHvertex :Else:vshader=ShaderCompile(vshadercode,#PB_Shader_Vertex,dbg):EndIf:If vshader=0 :ProcedureReturn :EndIf
  Program = glCreateProgram()
  glAttachShader(Program,vshader)
  glAttachShader(Program,fshader)
  glLinkProgram(Program)
  glUseProgram(Program)
  
  If  FindMapElement(ShaderInfo(),""+num):DeleteMapElement(ShaderInfo(),""+num):EndIf
  With ShaderInfo(""+num)
    \num=num
    \name=name
    \pg=Program
    \vcode=vshadercode
    \fcode=fshadercode
    Protected p,pf,l.s,n.s,t.s
    vfcode=supspace(vshadercode+fshadercode)
    Repeat
      p=FindString(vfcode,"uniform",p+1)
      pf=FindString(vfcode,";",p)
      If p
        l=Mid(vfcode,p,pf-p)
        n=StringField(l,3," ")
        t=StringField(l,2," ")
        ul=glGetUniformLocation(Program,n)
        If FindString(t,"sampler"):glUniform1i(ul,txu):txu+1:Else:\uloc(n)=ul:EndIf 
      EndIf
    Until p=0  
  EndWith
  ProcedureReturn num
EndProcedure

Procedure S_Camera(x.f,y.f,zoom.f=0,rotation.f=1e10)
  glcamx=x
  glcamy=y
  If zoom<>0:glcamzoom=zoom:EndIf
  If rotation<>1e10
    glcamrot=Radian(rotation)
    glcami=Cos(glcamrot)*glcamzoom
    glcamj=Sin(glcamrot)*glcamzoom
  EndIf 
EndProcedure

Procedure S_light(x.f,y.f,z.f,dist.f,color.l,ambiantcolor.l,world=1)
  If world:screenpos(@x,@y):EndIf
  glligthx=x
  glligthy=y
  glligthz=z
  glligthdist=dist
  glligthcolor=$ff<<24 | color
  glambiantcolor=$ff<<24 | ambiantcolor
EndProcedure

Procedure S_SpriteParameter(num,parameter.s,type,v0.d,v1.f=0,v2.f=0,v3.f=0); parameter: #PB_Shader_Integer/float/vector2/vector3/vector4/color
  Protected *sh.sShaderinfo,*p.sparam
  If num=-1
    ;S_SpriteParameter(-1,"screenratio",#PB_Shader_Float,glratio)
  EndIf 
  Spriteverif(num)
  With SpriteInfo(""+num)
    *p=\param(parameter)
    *p\nom=parameter
    *p\type=type
    *p\v0=v0
    *p\v1=v1
    *p\v2=v2
    *p\v3=v3
  EndWith 
EndProcedure

Procedure S_SpriteUV(num, u1.f, v1.f, u2.f, v2.f, u3.f, v3.f, u4.f, v4.f)
  Spriteverif(num)
  With SpriteInfo(""+num)
    \u1=u1:\v1=v1
    \u2=u2:\v2=v2
    \u3=u3:\v3=v3
    \u4=u4:\v4=v4
  EndWith
EndProcedure

Procedure S_ClipSprite(num, x.f, y.f, dx.f, dy.f,mode=0)
  Spriteverif(num)
  With SpriteInfo(""+num)
    \u1=x/\Tdx:\v1=y/\Tdy
    \u2=(x+dx)/\Tdx:\v2=y/\Tdy
    \u3=(x+dx)/\Tdx:\v3=(y+dy)/\Tdy
    \u4=x/\Tdx:\v4=(y+dy)/\Tdy
    \dx=dx
    \dy=dy
  EndWith
  spritecoord(num)
EndProcedure

Procedure S_CreateSprite(num,shaderNum,image1,image2=-1,image3=-1,image4=-1); shaderNum:Enumeration S_shader2D
  If shaderNum=0:MessageRequester("Erreur S_CreateSprite","Shader invalid"):CallDebugger:EndIf
  Static numauto=1000000
  Protected u.s,txu
  
  If num=-1:num=numauto:numauto+1:EndIf
  AddMapElement(SpriteInfo(),""+num)
  SpriteInfo()\sh = ShaderInfo(""+shaderNum)
  Macro addtx(image)
    If image>=0
      If IsImage(image)=0:MessageRequester("Erreur S_CreateSprite","image"+Str(txu+1)+" isn't loaded"):CallDebugger:EndIf
      AddElement(SpriteInfo()\tx())
      SpriteInfo()\tx()= ImageToGLTextures(image)
    EndIf
  EndMacro
  addtx(image1)
  addtx(image2)
  addtx(image3)
  addtx(image4) 
  With SpriteInfo()
    \Tdx=ImageWidth(image1):\dx=\Tdx
    \Tdy=ImageHeight(image1):\dy=\Tdy
    \u2=1:\u3=1:\v3=1:\v4=1
    \x2=\Tdx:\x3=\Tdx:\y3=\Tdy:\y4=\Tdy
    \zx=1:\zy=1
  EndWith
  ProcedureReturn num
EndProcedure

Procedure S_DisplaySprite(num,x.f,y.f,Alpha=$ff,color.l=$ffffff,z.f=0)
  Spriteverif(num)
  Protected.f a=alpha/255, r=Red(color)/255, g=Green(color)/255, b=Blue(color)/255,sx,sy
  Protected txu, *sp.sSpriteinfo
  
  *sp=SpriteInfo(""+num) 
  glUseProgram(*sp\sh\pg)
  ForEach *sp\tx()     
    glActiveTexture(#GL_TEXTURE0+txu):glBindTexture_(#GL_TEXTURE_2D,*sp\tx()):txu+1
  Next
  ForEach *sp\param()
    With *sp\param()
      shaderuniform(*sp\sh,\nom,\type,\v0,\v1,\v2,\v3)
    EndWith
  Next  
  
  With *sp
    Macro glv(x,y):sx=x:sy=y:If *sp\sh\num<>#SHoverlay:screenpos(@sx,@sy):EndIf:glVertex3f_(sx, sy,z):EndMacro
    glBegin_(#GL_QUADS)
    glColor4f_(r,g,b,a)
    glNormal3f_(Cos(*sp\ag+glcamrot),Sin(*sp\ag+glcamrot),0); for tangent !
    glTexCoord2f_(\u1,\v1):glv(x+\x1,y+\y1)
    glTexCoord2f_(\u2,\v2):glv(x+\x2,y+\y2)
    glTexCoord2f_(\u3,\v3):glv(x+\x3,y+\y3)
    glTexCoord2f_(\u4,\v4):glv(x+\x4,y+\y4)
    glEnd_()   
  EndWith 
EndProcedure

Procedure S_FreeSprite(num)
  Spriteverif(num)
  glDeleteProgram(SpriteInfo(""+num)\sh\pg)
  DeleteMapElement(SpriteInfo(),""+num)
EndProcedure 

Procedure S_IsSprite(num)
  If FindMapElement(SpriteInfo(),""+num):ProcedureReturn 1:EndIf  
EndProcedure 

Procedure S_RotateSprite(num,angle.f,mode=0)
  Spriteverif(num)
  With SpriteInfo(""+num)
    angle=Radian(angle)
    If mode:\ag+angle:Else:\ag=angle:EndIf
  EndWith
  spritecoord(num)
EndProcedure 

Procedure S_SpriteOrigine(num,x.f,y.f,unit=#s_unit_UV) ; unit:Enumeration S_unit
  Spriteverif(num)
  With SpriteInfo(""+num)
    If unit=#s_unit_UV
      \xo=x*\Tdx
      \yo=y*\Tdy
    Else
      \xo=x
      \yo=y
    EndIf
  EndWith
  spritecoord(num)
EndProcedure 

Procedure S_BlendingMode(mode, modesource=#PB_Sprite_BlendSourceAlpha, modedestination=#PB_Sprite_BlendInvertSourceAlpha); mode:Enumeration S_BlendingMode,  mosesource/modedestination: cf:SpriteBlendingMode
  Protected glsrc,gldst
  Macro cvmode(pbmode,glmode)
    Select pbmode
      Case #PB_Sprite_BlendZero:glmode=#GL_ZERO
      Case #PB_Sprite_BlendOne:glmode=#GL_ONE
      Case #PB_Sprite_BlendSourceColor:glmode=#GL_SRC_COLOR
      Case #PB_Sprite_BlendInvertSourceColor:glmode=#GL_ONE_MINUS_SRC_COLOR
      Case #PB_Sprite_BlendDestinationColor:glmode=#GL_DST_COLOR
      Case #PB_Sprite_BlendInvertDestinationColor:glmode=#GL_ONE_MINUS_DST_COLOR
      Case #PB_Sprite_BlendSourceAlpha:glmode=#GL_SRC_ALPHA
      Case #PB_Sprite_BlendInvertSourceAlpha:glmode=#GL_ONE_MINUS_SRC_ALPHA
      Case #PB_Sprite_BlendDestinationAlpha:glmode=#GL_DST_ALPHA
      Case #PB_Sprite_BlendInvertDestinationAlpha:glmode=#GL_ONE_MINUS_DST_ALPHA
    EndSelect
  EndMacro
  
  Select mode
    Case #s_BlendingMode_alphablend: glBlendFunc_(#GL_SRC_ALPHA, #GL_ONE_MINUS_SRC_ALPHA)
    Case #s_BlendingMode_add       : glBlendFunc_(#GL_ONE, #GL_ONE)
    Case #s_BlendingMode_custom    :cvmode(modesource,glsrc):cvmode(modedestination,gldst):glBlendFunc_(glsrc, gldst)
  EndSelect
EndProcedure 

Procedure S_Spritecollision(num1, X1, Y1, num2, X2, Y2); !!! todo
  Spriteverif(num1)
  Spriteverif(num2)
EndProcedure 

Procedure S_TransformSprite(num, X1.f, Y1.f, X2.f, Y2.f, X3.f, Y3.f, X4.f, Y4.f)
  Spriteverif(num)
  With SpriteInfo(""+num)
    \x1=x1:\y1=y1
    \x2=x2:\y2=y2
    \x3=x3:\y3=y3
    \x4=x4:\y4=y4
    \zx=1:\zy=1
    \ag=0
  EndWith
EndProcedure

Procedure S_ZoomSprite(num, Width.f, Height.f,unit=#s_unit_UV); unit:Enumeration S_unit
  Spriteverif(num)
  With SpriteInfo(""+num)
    If unit=#s_unit_UV
      \dx=Width*\Tdx
      \dy=Height*\Tdy
    Else
      \dx=Width
      \dy=Height
    EndIf
    \zx=\dx/\tdx
    \zy=\dy/\tdy
  EndWith
  spritecoord(num)
EndProcedure

Procedure s_FlipBuffers() 
  FlipBuffers()
  ForEach ShaderInfo()
    glUseProgram(ShaderInfo()\pg)
    shaderuniform(ShaderInfo(),"screen",#PB_Shader_Vector2,s_screendx,s_screendy)
    shaderuniform(ShaderInfo(),"campos",#PB_Shader_Vector3,s_screendx2,s_screendy2,s_screendy2)
    shaderuniform(ShaderInfo(),"ambiantcolor",#PB_Shader_color,glambiantcolor)
    shaderuniform(ShaderInfo(),"lightcolor",#PB_Shader_color,glligthcolor)
    shaderuniform(ShaderInfo(),"lightinfo",#PB_Shader_Vector4,glligthx,glligthy,glligthz,glligthdist)
    shaderuniform(ShaderInfo(),"time",#PB_Shader_Float,ElapsedMilliseconds()/1000)
  Next
  glEnable_(#GL_BLEND)
EndProcedure

Procedure S_init()
  s_screendx=ScreenWidth():s_screendx2=s_screendx/2
  s_screendy=ScreenHeight():s_screendy2=s_screendy/2
  
  codevertex="#version 120 %%uniform vec2 screen;% varying vec3 vpos;% varying vec4 vcolor;% varying vec2 vuv;% varying vec2 vtan;% void main() {% vtan = gl_Normal.xy;% gl_Position = vec4( gl_Vertex.xy/screen*2-1,gl_Vertex.z, 1 );gl_Position.y*=-1;% vcolor=gl_Color;% vuv=gl_MultiTexCoord0.xy;//invertv% vpos=gl_Vertex.xyz;%}"
  If #PB_OS_Windows:codevertex=ReplaceString(codevertex,"//invertv","vuv.y=1-vuv.y;"):EndIf
  SHvertex=ShaderCompile(codevertex,#PB_Shader_Vertex)
  ;Debug ReplaceString(codevertex,"%",#LF$)
  shaderCreate(#SHoverlay,"#version 130 %%uniform sampler2D txt0;%%in  vec4 vcolor;%in  vec2 vuv;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0,vuv);%	fcolor =tcolor*vcolor;%}","","overlay")
  shaderCreate(#SHdefault,"#version 130 %%uniform sampler2D txt0;%%in  vec4 vcolor;%in  vec2 vuv;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0,vuv);%	fcolor =tcolor*vcolor;%}","","default")
  shaderCreate(#SHblend,"#version 130 %%uniform sampler2D tx0;%uniform sampler2D tx1;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%uniform float blend;%%in  vec4 vcolor;%in  vec2 vuv;%in  vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=mix(texture(tx0,vuv),texture(tx1,vuv),blend);%	float lum=max(1-distance(lightinfo.xyz,vpos)/lightinfo.w,0);%	fcolor =tcolor*vcolor*(ambiantcolor+lightcolor*lum);%}","","blend")
  shaderCreate(#SHlight,"#version 130 %%uniform sampler2D txt0;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%%in  vec4 vcolor;%in  vec2 vuv;%in  vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0,vuv);%	float lum=max(1-distance(lightinfo.xyz,vpos)/lightinfo.w,0);%	fcolor =tcolor*vcolor*(ambiantcolor+lum*lightcolor);%}","","light")
  shaderCreate(#SHbump,"#version 130 %%uniform sampler2D tx0;%uniform sampler2D tx1;%%uniform vec3 campos;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%in vec2 vtan;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcol=texture(tx0,vuv)*vcolor;%	vec3 tnor=texture(tx1,vuv).xyz-0.5;tnor.xy*=1;%	tnor.xy=vec2(vtan.x*tnor.x+vtan.y*-tnor.y,  -vtan.y*tnor.x+vtan.x*-tnor.y);%	tnor=normalize(tnor);%	vec3 ldir=normalize(lightinfo.xyz-vpos);%	vec3 cdir=normalize(campos-vpos);%	float att=max(1-distance(lightinfo.xyz,vpos)/lightinfo.w,0);%	float dif=max(dot(ldir,tnor),0)*att;%	float spe=pow(max(dot(normalize(ldir+cdir),tnor),0),50);%	fcolor =tcol*(ambiantcolor+lightcolor*(dif+spe));%}","","bump")
  shaderCreate(#SHflame,"#version 130 %%uniform sampler2D tx;%uniform float time;%%in vec2 vuv;%in vec4 vcolor;%%out vec4 fcolor;%void main()%{%float odec=1;%vec2 uv=vuv;uv.y=pow(uv.y,0.5);%vec2 pc=uv*2-1;%float h=1-dot(pc,pc);%if(h<0)discard;%float vx=time*0.08;%float vy=time*-0.2;%float lum=0.8*h*(texture(tx,uv+vec2(vx,vy+odec)).a+texture(tx,uv+vec2(-vx,vy+0.5+odec)).a);%fcolor=(lum*lum)*vcolor;%}","","flame")
  shaderCreate(#SHwater,"#version 130 %%uniform sampler2D tx;%%uniform float time;%uniform vec3 campos;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 skycolor;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%in vec2 vtan;%%out vec4 fcolor;%%void main( void ) {%	vec2 duv=vec2(time*0.02,0);%	vec3 tnor=(texture(tx,vuv+duv).xyz+texture(tx,vuv+0.5-duv).xyz-1).xyz;tnor.xy*=1;%	tnor.xy=vec2(vtan.x*tnor.x+vtan.y*-tnor.y,  -vtan.y*tnor.x+vtan.x*-tnor.y);%	tnor=normalize(tnor);%	vec3 ldir=normalize(lightinfo.xyz-vpos);%	vec3 cdir=normalize(campos-vpos);%	float spe=pow(max(dot(normalize(ldir+cdir),tnor),0),50);%	float cfresnel = 1-abs(dot(cdir, tnor));%	fcolor =mix(vcolor,skycolor,cfresnel*cfresnel)+lightcolor*spe;%}","","water")
  shaderCreate(#SHplasma,"#version 130 %%uniform sampler2D tx;%uniform float time;%uniform vec4 color1;%uniform vec4 color2;%%in vec2 vuv;%in vec4 vcolor;%%out vec4 fcolor;%void main()%{%vec2 duv=vec2(time*0.02,0);%float lum=(texture(tx,vuv+duv).a+texture(tx,vuv-duv+0.5).a);%fcolor=mix(color1,color2,mod(lum*2,1))*vcolor;%//fcolor=mix(color1,color2,(1+cos(lum*3.14*4))/2)*vcolor;%}","","plasma")
  shaderCreate(#SHnew,"#version 130 %%uniform sampler2D tx;%%// global parameters%uniform vec3 campos; // camera position%uniform vec4 ambiantcolor;%uniform vec4 lightcolor;%uniform vec4 lightinfo;  // x,y,z:position, w:range%uniform float time; // in seconds%%// keep only if you use it%in vec3 vpos; // vertex position%in vec4 vcolor; // vertex color%in vec2 vuv;  // vertex uv%in vec2 tan; // tangent (for normal mapping)%%out vec4 fcolor;%%void main()%{%vec4 tcolor=texture(tx,vuv);%fcolor=tcolor*vcolor;%}","","new")
EndProcedure

;========================================================================== shader editor
Global GSE_editor,GSE_message,GSE_list,GSE_run,GSE_savecb,  SE_window, shaderedit

Procedure shaderEditorcallback()
  Protected event,code.s
  
  Macro updateshader
    shaderCreate(shaderedit,code,"",ShaderInfo(""+shaderedit)\name,0)
    SetGadgetText(GSE_message,Shadermessage)
    If Shadermessage=""
      ForEach SpriteInfo()
        If SpriteInfo()\sh\num=shaderedit:SpriteInfo()\sh=ShaderInfo(""+shaderedit):EndIf
      Next
    EndIf
  EndMacro
  
  Select Event()
    Case #PB_Event_CloseWindow:CloseWindow(EventWindow()):SE_window=0:ReleaseMouse(0)
    Case #PB_Event_Menu
      Select EventMenu()
        Case 1111:code = GetGadgetText(GSE_editor):updateshader
        Case 1112:CloseWindow(EventWindow()):SE_window=0:ReleaseMouse(0)
      EndSelect
    Case #PB_Event_Gadget
      Select EventGadget()
        Case GSE_list:shaderedit=GetGadgetItemData(GSE_list,GetGadgetState(GSE_list)):SetGadgetText(GSE_editor,ReplaceString(ShaderInfo(""+shaderedit)\fcode,"%",#CRLF$))
        Case GSE_run:code = GetGadgetText(GSE_editor):updateshader
        Case GSE_savecb:code=GetGadgetText(GSE_editor):code=ReplaceString(code,#CRLF$,"%"):SetClipboardText(~"SHnew=shaderCreate(-1,\""+code+~"\",\"\",\""+ShaderInfo(""+shaderedit)\name+~"\")\n")
      EndSelect
  EndSelect
EndProcedure

Procedure shaderEditor(shader)  
  Protected  wdx=700,xdy=600,nf,it,ls
  
  If SE_window:ReleaseMouse(1):SetActiveWindow(SE_window): ProcedureReturn :EndIf
  shaderedit=shader
  SE_window=OpenWindow(-1,0,0,wdx,xdy,"Shader Editor")
  BindEvent(#PB_Event_Gadget,@shaderEditorcallback(),SE_window)
  BindEvent(#PB_Event_Menu,@shaderEditorcallback(),SE_window)
  BindEvent(#PB_Event_CloseWindow,@shaderEditorcallback(),SE_window)
  
  GSE_editor=EditorGadget(-1,8,30,wdx-16,xdy-30-150)
  SetGadgetText(GSE_editor,ReplaceString(ShaderInfo(""+shaderedit)\fcode,"%",#CRLF$))
  GSE_message=EditorGadget(-1,8,xdy+8-150,wdx-16,150-16,#PB_Editor_ReadOnly)
  nf=LoadFont(-1,"consolas",10)
  SetGadgetFont(GSE_editor,FontID(nf))
  SetGadgetFont(GSE_message,FontID(nf))
  
  GSE_list=ComboBoxGadget(-1,8,0,90,24):ForEach ShaderInfo():AddGadgetItem(GSE_list,-1,ShaderInfo()\name):SetGadgetItemData(GSE_list,it,ShaderInfo()\num):If ShaderInfo()\num=shader:ls=it:EndIf:it+1:Next
  SetGadgetState(GSE_list,ls)
  GSE_run=ButtonGadget(-1,108 ,0,90,24,"run [F5]")
  GSE_savecb=ButtonGadget(-1,208 ,0,90,24,"save clipboard")
  AddKeyboardShortcut(SE_window, #PB_Shortcut_F5, 1111) 
  AddKeyboardShortcut(SE_window, #PB_Shortcut_Escape, 1112) 
EndProcedure

;============================================================================================ brush
Procedure initIF(image,cx.w=-1,cy.w=-1)
  ;image : numero de l'image
  ;centerx/y : definit le centre de l'image
  Structure sImageFont
    x.b
    y.b
    col.l
  EndStructure
  
  Protected i,j,d,k,n,c,idx,idy,x,y
  idx=ImageWidth (image):If cx=-1:cx=idx/2:EndIf
  idy=ImageHeight(image):If cy=-1:cy=idy/2:EndIf
  Global Dim IFdata.sImageFont(idx * idy-1)
  n=-1
  StartDrawing(ImageOutput(image))
  DrawingMode(#PB_2DDrawing_AllChannels)  
  Macro gplot(i,j):x=cx+i:y=cy+j:If x>=0 And x<idx And y>=0 And y<idy:c=Point(x,y):If c<>0:n+1:IFdata(n)\x=x:IFdata(n)\y=y:IFdata(n)\col=c:EndIf:EndIf:EndMacro
gplot(0,0)
  For d=1 To 30
    For k=0 To d-1
      gplot(-d+k,-k)
      gplot(k,-d+k)
      gplot(d-k, k)
      gplot(-k,d-k)
    Next
  Next
  ReDim IFdata(n)
  StopDrawing() 
EndProcedure

Procedure DrawVectorTextBrush(text.s)
  Protected x.f,y.f,j,n
  x=PathCursorX()
  y=PathBoundsY()
  n=ArraySize(IFdata())
  For j=n To 0 Step -1
    MovePathCursor(x+IFdata(j)\x,y+IFdata(j)\y):VectorSourceColor(IFdata(j)\col):DrawVectorText(text)
  Next   
EndProcedure

;============================================================================================ fastfont
Procedure S_InitFont(num,name.s, height.f,style=0,brush=-1,chars.s="")
  Structure ssc
    sx.l
    sl.l
    cl.l
    co.l
  EndStructure
  
  Structure sscfont
    ns.i
    height.f
    Array c.ssc(255)
  EndStructure
  
  Global ScrennFont.sscfont
  
  Protected i,h,l,c.s,ca,im,bx,by,cx,co,cv,cl:Global nf
  If chars="":For i=32 To 128:chars+Chr(i):Next:EndIf
  
  nf=LoadFont(-1,name,height,style)
  If brush>=0:initIF(brush):bx=ImageWidth(brush):by=ImageHeight((brush)):EndIf
  IM=CreateImage(-1,1,1)
  StartDrawing(ImageOutput(im)):DrawingFont(FontID(nf))
  h=TextHeight(" ")+by
  l=TextWidth(chars)*1.3+Len(chars)*bx:cx=0
  StopDrawing()
  FreeImage(im)
  
  IM=CreateImage(-1,l,h,32,#PB_Image_Transparent):StartDrawing(ImageOutput(im)):DrawingMode(#PB_2DDrawing_AllChannels):Box(0,0,l,h,$00ffffff):StopDrawing()
  StartVectorDrawing(ImageVectorOutput(im)):VectorFont(FontID(nf))
  For i=1 To Len(chars)
    c=Mid(chars,i,1):ca=Asc(c)
    With ScrennFont\c(ca)
      co=VectorTextWidth(c,#PB_VectorText_Visible|#PB_VectorText_Offset):If ca=126:co=0:EndIf
      cv=VectorTextWidth(c,#PB_VectorText_Visible)
      cl=VectorTextWidth(c)
      \sx=cx
      \sl=cv+bx+2
      \cl=cl+bx/2
      \co=co
      ;AddPathBox(\sx,0,\sl,h):VectorSourceColor($8800ff00):FillPath()
      MovePathCursor(cx-co+1,0)
      If brush<0:VectorSourceColor($ffffffff):DrawVectorText(c):Else:DrawVectorTextBrush(c):EndIf
      cx+\sl+1
    EndWith
  Next
  StopVectorDrawing()
  
  ScrennFont\ns=S_CreateSprite(-1,#SHoverlay,im)
  ScrennFont\height=h
EndProcedure

Procedure S_DrawText(x,y,t.s,size=-1,color=$ffffffff)
  Protected i,ca,cx,c.ssc,zoom.f
  With ScrennFont
    If size=-1:size=\height:EndIf
    zoom=size/\height
    For i=1 To Len(t)
      c=\c(Asc(Mid(t,i,1)))
      S_ClipSprite(\ns,c\sx,0,c\sl,\height)
      S_ZoomSprite(\ns,c\sl*zoom,\height*zoom,#s_unit_Pixel)
      S_DisplaySprite(\ns,x+c\co*zoom,y,255,color)
      x+c\cl*zoom
    Next
  EndWith
EndProcedure

;====================================================================================================================================================
;====================================================================================================================================================
;====================================================================================================================================================


ExamineDesktops()
Define swidth=DesktopWidth(0)*0.8
Define sheight=DesktopHeight(0)*0.8
OpenWindow(0,0,0,swidth,sheight,"Lib 2D v1.0",#PB_Window_ScreenCentered)
OpenWindowedScreen(WindowID(0),0,0,swidth,sheight)
S_init()
InitKeyboard()
InitMouse()
;----------------------------- init screen font
CreateImage(100,8,8,32,#PB_Image_Transparent)
StartVectorDrawing(ImageVectorOutput(100))
VectorSourceCircularGradient(3,3,5)
VectorSourceGradientColor($ffffffff, 0.0)
VectorSourceGradientColor($ff0000ff, 0.5)
VectorSourceGradientColor($00000000, 1.0) 
AddPathCircle(4,4,4):FillPath()
StopVectorDrawing()
S_InitFont(0,"ink free",30,#PB_Font_Italic,100)

Define i,sblend,sbump,sflare,sflame,  swater,scloud,  splasma,  SHwobble,swobble

;----------------------------- load images
UseJPEGImageDecoder()
UsePNGImageDecoder()
LoadImage(1,#PB_Compiler_Home+"examples/3d/Data/Textures/water.png")
LoadImage(2,#PB_Compiler_Home+"examples/3d/Data/Textures/smoke2.png")
LoadImage(3,#PB_Compiler_Home+"examples/3d/Data/Textures/flare.png")
LoadImage(4,#PB_Compiler_Home+"examples/3d/Data/Textures/sky.png")
LoadImage(5,#PB_Compiler_Home+"examples/3d/Data/Textures/nvidia/dirt_grayrocky_diffusespecular.jpg")
LoadImage(6,#PB_Compiler_Home+"examples/3d/Data/Textures/nvidia/dirt_grayrocky_normalheight.jpg")
LoadImage(7,#PB_Compiler_Home+"examples/3d/Data/Textures/waternormal.png")
CreateImage(10,512,512,32,#PB_Image_Transparent):StartDrawing(ImageOutput(10)):DrawingMode(#PB_2DDrawing_AlphaBlend):For i=0 To 800:Circle(Random(512-64)+32,Random(512-64)+32,32,Random($44ffffff)):Next:StopDrawing()


;----------------------------- init demo1
sbump=S_CreateSprite(-1,#SHbump,5,6):S_SpriteOrigine(sbump,0.5,0.5):S_ZoomSprite(sbump,swidth*2,sheight*2,0):S_SpriteUV(sbump,0,0, 2,0, 2,2, 0,2)
sblend=S_CreateSprite(-1,#shblend,1,2):S_SpriteOrigine(sblend,0.5,0.5):S_ZoomSprite(sblend,2,2)
sflare=S_CreateSprite(-1,#SHoverlay,3):S_SpriteOrigine(sflare,0.5,0.5):S_ZoomSprite(sflare,2,2)
sflame=S_CreateSprite(-1,#SHflame,7):S_SpriteOrigine(sflame,0.5,0.5):S_ZoomSprite(sflame,1,1.5)

;----------------------------- init demo2
swater=S_CreateSprite(-1,#SHwater,7):S_SpriteParameter(swater,"skycolor",#PB_Shader_color,$ffffbb88):S_SpriteOrigine(swater,0.5,0.5):S_ZoomSprite(swater,swidth*2,swidth*2,#s_unit_Pixel)
scloud=S_CreateSprite(-1,#SHdefault,4):S_ZoomSprite(scloud,swidth*2,swidth*2,#s_unit_Pixel):S_SpriteOrigine(scloud,0.5,0.5)

;----------------------------- init demo3
splasma=S_CreateSprite(-1,#SHplasma,7):S_SpriteParameter(splasma,"color1",#PB_Shader_color,$ffff0000):S_SpriteParameter(splasma,"color2",#PB_Shader_color,$ff00ffff):S_SpriteOrigine(splasma,0.5,0.5):S_ZoomSprite(splasma,sheight*2,sheight*2,#s_unit_Pixel)

;---------------------------- init test shader
SHwobble=shaderCreate(-1,"#version 130 %%uniform sampler2D txt0;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%uniform float time;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	float fq=8,amp=0.04,ti=time*4;%	vec2 uv=vuv*(1+2*amp)-amp;%	uv=uv+vec2(sin(vuv.y*fq+ti)*amp,sin(vuv.x*fq+ti)*amp);%	if (uv.x<0 || uv.x>1 || uv.y<0 || uv.y>1) discard; %	vec4 tcolor=texture(txt0,uv);%	float lum=max(1-distance(lightinfo.xyz,vpos)/lightinfo.w,0);%	fcolor =tcolor*vcolor*(ambiantcolor+lum*lightcolor);%}","","wobble")
swobble=S_CreateSprite(-1,SHwobble,10):S_SpriteOrigine(swobble,0.5,0.5):S_ZoomSprite(swobble,sheight,sheight,#s_unit_Pixel);:S_SpriteParameter(swobble,"amp",#PB_Shader_Float,1)

Define.f sy,a,ai,py,dy,t,   rot,zw=0.5*8,zc=0.25,   example.b=0
MouseLocate(swidth/2,sheight/2)

Repeat
  t=ElapsedMilliseconds()/1000
  a=t*2
  sy=-t/10
  
  ClearScreen(0)
  
  S_BlendingMode(#s_BlendingMode_alphablend)
  Select example
    Case 0
      S_Camera(Sin(sy*5)*200,Sin(sy*7)*200,1,0)
      S_light(MouseX(),MouseY(),sheight/2,sheight*4,$ffffff,$0,0)
      
      S_DisplaySprite(sbump,swidth/2,sheight/2)
      
      S_SpriteParameter(sblend,"blend",#PB_Shader_Float,0.5+0.5*Cos(a)):S_DisplaySprite(sblend,swidth*0.25,sheight*0.25,$ff,$ffff00)
      S_SpriteParameter(sblend,"blend",#PB_Shader_Float,0.5+0.5*Sin(a)):S_DisplaySprite(sblend,swidth*0.25,sheight*0.75,$ff,$ff00ff)
      
      S_BlendingMode(#s_BlendingMode_add)
      S_DisplaySprite(sflame,swidth*0.75,sheight/2,128,$88ff)
      S_RotateSprite(sflare,2,#PB_Relative):S_DisplaySprite(sflare,MouseX(),MouseY())
      S_BlendingMode(#s_BlendingMode_alphablend)
      
    Case 1
      rot+MouseDeltaX()*0.05
      S_Camera(0,0,1+Sin(sy*4)/3,rot)
      S_light(10000,-10000,10000,0,$ffffff,$222222*4)
      
      S_SpriteUV(swater, 0,sy, zw,sy, zw,zw+sy, 0,zw+sy):S_DisplaySprite(swater,swidth/2,sheight/2,255,$443300)
      
      S_SpriteUV(scloud, 0,sy, zc*2,sy, zc*2,zc*2+sy, 0,zc*2+sy)
      S_DisplaySprite(scloud,swidth/2,sheight/2)
      S_SpriteUV(scloud, 0,sy, zc,sy, zc,zc+sy, 0,zc+sy)
      S_DisplaySprite(scloud,swidth/2,sheight/2)
      
    Case 2
      S_Camera(0,0,1,0)
      S_DisplaySprite(splasma,swidth/2,sheight/2)
      
    Case 3
      S_Camera(0,0,1,0)
      S_light(0,0,0,0,0,$ffffff,0)
      S_DisplaySprite(sbump,swidth/2,sheight/2,$ff,$888888)
      S_DisplaySprite(swobble,swidth/2,sheight/2)
      
  EndSelect
  S_DrawText(8,0,"[F1] Edit shader")
  S_DrawText(8,60,"[Space] Change example")
  S_DrawText(8,120,"[Esc] Quit")
  S_DrawText(8,180,"Use mouse",40)
  s_FlipBuffers()
  
  While WindowEvent():Wend
  ExamineKeyboard()
  ExamineMouse()    
  If KeyboardReleased(#PB_Key_F1):shaderEditor(#SHnew) :EndIf
  If KeyboardReleased(#PB_Key_Space):example=(example+1)%4:EndIf
Until KeyboardReleased(#PB_Key_Escape) Or MouseButton(3)
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

@pf shadoko

The latest version is the same. It works nicely but for the text issue. I'm guessing there is no interactive element as pressing keys or mouse buttons don't seem to affect it at all?
I'm using Void linux mostly, so have to change the path to /usr/lib64/libGL.so to get it running.
I still don't know how to test what you suggested about if = 0 and if = 1?
If you give me precise instructions I can test it out.

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
Mesa
Enthusiast
Enthusiast
Posts: 433
Joined: Fri Feb 24, 2012 10:19 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by Mesa »

I've made a module.

[Edit1 : Event management and typo]

Code: Select all

;=======================================================
;            Lib screen (Sprite) - pf Shadoko -2024
;=======================================================
;  Module : Mesa >> Everything (constant, procedure, ...) 
;                   beginning by 'S_' is PUBLIC
;=======================================================

;- TOP

CompilerIf #PB_Compiler_IsMainFile
	EnableExplicit
CompilerEndIf

;-

;- DeclareModule S_Sprite
;- ¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯
DeclareModule S_Sprite
	
	;init opengl to add functions
	InitSprite():w=OpenWindow(#PB_Any, 0, 0, 10, 10, ""):OpenWindowedScreen(WindowID(w), 0, 0, 10, 10):CloseWindow(w)
	
	;- ◄ PUBLIC ►
	
	;- Constant
	; (For purebasic only)
	#PB_Shader_Vector2	= 2
	#PB_Shader_color		= 10
	#GL_TEXTURE0				= $84c0
	#GL_VERTEX_SHADER 	= $8B31
	#GL_FRAGMENT_SHADER = $8B30
	
	; (From here is for users)
	Enumeration S_unit
		#S_unit_Pixel			= 0
		#S_unit_UV				
	EndEnumeration
	
	Enumeration S_BlendingMode
		#S_BlendingMode_alphablend
		#S_BlendingMode_add
		#S_BlendingMode_custom
	EndEnumeration
	
	Enumeration S_shader2D
		#S_Shader_Blend		= 1000
		#S_Shader_Bump
		#S_Shader_Default
		#S_Shader_Flame
		#S_Shader_Light
		#S_Shader_Overlay				
		#S_Shader_New
		#S_Shader_Plasma
		#S_Shader_Water
	EndEnumeration
	
	
	;- Declare
	Declare S_BlendingMode(mode, modesource=#PB_Sprite_BlendSourceAlpha, modedestination=#PB_Sprite_BlendInvertSourceAlpha);mode:Enumeration S_BlendingMode,  mosesource/modedestination: cf:SpriteBlendingMode
	Declare S_Camera(x.f, y.f, zoom.f=0, rotation.f=1e10)
	Declare S_ClipSprite(num, x.f, y.f, dx.f, dy.f, mode=0)
	Declare S_CreateSprite(num, shaderNum, image1, image2=-1, image3=-1, image4=-1)
	Declare S_DisplaySprite(num, x.f, y.f, Alpha=$ff, color.l=$ffffff, z.f=0)
	Declare S_DrawText(x, y, t.s, size=-1, color=$ffffffff)
	Declare S_FlipBuffers() 
	Declare S_FreeSprite(num)
	Declare S_Globalparameter()
	Declare S_Init()
	Declare S_InitFont(num, name.s, height.f, style=0, brush=-1, chars.s="")
	Declare S_IsSprite(num)
	Declare S_Light(x.f, y.f, z.f, dist.f, color.l, ambiantcolor.l, world=1)
	Declare S_RotateSprite(num, angle.f, mode=0)
	Declare S_Spritecollision(num1, X1, Y1, num2, X2, Y2); !!! todo
	Declare S_SpriteOrigine(num, x.f, y.f, unit=#S_unit_UV) ; unit:Enumeration S_unit
	Declare S_SpriteParameter(num, parameter.s, type, v0.d, v1.f=0, v2.f=0, v3.f=0); parameter: #PB_Shader_Integer/float/vector2/vector3/vector4/color
	Declare S_SpriteUV(num, u1.f, v1.f, u2.f, v2.f, u3.f, v3.f, u4.f, v4.f)
	Declare S_TransformSprite(num, X1.f, Y1.f, X2.f, Y2.f, X3.f, Y3.f, X4.f, Y4.f)
	Declare S_ZoomSprite(num, Width.f, Height.f, unit=#S_unit_UV); unit:Enumeration S_unit
	
	Declare S_ShaderCreate(num, fshadercode.s, vshadercode.s="", name.s="", dbg=1)
	Declare S_ShaderEditor(shader)
	
	
	
EndDeclareModule

;-

;- Module
;- ¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯
Module S_Sprite
	
	;- ◄ PRIVATE ►
	
	;- Prototype
	CompilerIf #PB_Compiler_OS = #PB_OS_MacOS
		ImportC "-framework OpenGL"
			glActiveTexture(type.l) As "_glActiveTexture" 
			glCreateShader(type.l) As "_glCreateShader" 
			glCreateProgram() As "_glCreateProgram"
			glDeleteProgram(Program.l) As "_glDeleteProgram"
			glDeleteShader(shader.l) As "_glDeleteShader"
			glCompileShader(shader.l) As  "_glCompileShader"
			glLinkProgram(shader.l) As "_glLinkProgram" 
			glUseProgram(shader.l) As "_glUseProgram" 
			glAttachShader(Program.l, shader.l) As  "_glAttachShader"
			glShaderSource(shader.l, numOfStrings.l, *strings, *lenOfStrings) As  "_glShaderSource"
			glGetUniformLocation(Program, name.p-ascii) As  "_glGetUniformLocation"
			glUniform1i(location, v0) As "_glUniform1i"
			glUniform2i(location, v0, v1) As  "_glUniform2i"
			glUniform1f(location, v0.f) As  "_glUniform1f"
			glUniform1d(location, v0.d) As  "_glUniform1d"
			glUniform2d(location, v0.d, v1.d) As  "_glUniform2d"
			glUniform2f(location, v0.f, v1.f) As  "_glUniform2f"
			glUniform3f(location, v0.f, v1.f, v2.f) As  "_glUniform3f"
			glUniform4f(location, v0.f, v1.f, v2.f, v3.f) As  "_glUniform4f"
			glGetShaderInfoLog(shader, bufSize.l, *length_l, *infoLog) As  "_glGetShaderInfoLog"
		EndImport
		
	CompilerElseIf #PB_Compiler_OS = #PB_OS_Linux  
		ImportC "/usr/lib/x86_64-linux-gnu/libGL.so"
			glActiveTexture(type.l)
			glCreateShader(type.l)
			glCreateProgram()
			glDeleteProgram(Program.l)
			glDeleteShader(shader.l)
			glCompileShader(shader.l)
			glLinkProgram(shader.l)
			glUseProgram(shader.l)
			glAttachShader(Program.l, shader.l)
			glShaderSource(shader.l, numOfStrings.l, *strings, *lenOfStrings) : 
			glGetUniformLocation(Program, name.p-ascii)
			glUniform1i(location, v0)
			glUniform2i(location, v0, v1)
			glUniform1d(location, v0.d)
			glUniform2d(location, v0.d, v1.d)
			glUniform1f(location, v0.f)
			glUniform2f(location, v0.f, v1.f)
			glUniform3f(location, v0.f, v1.f, v2.f)
			glUniform4f(location, v0.f, v1.f, v2.f, v3.f)
			glGetShaderInfoLog(shader, bufSize.l, *length_l, *infoLog)
		EndImport
		
	CompilerElseIf #PB_Compiler_OS = #PB_OS_Windows
		;- Macro
		Macro QUOTE:"
		EndMacro
		Macro _ :, :EndMacro
		Macro mPrototype (nom, params=)
			Prototype  nom(params)
			Global nom.nom=wglGetProcAddress_(QUOTE#nom#QUOTE)
		EndMacro
		
		mPrototype (glActiveTexture, type.l)
		mPrototype (glCreateShader, type.l)
		mPrototype (glCreateProgram)
		mPrototype (glDeleteProgram, Program.l)
		mPrototype (glDeleteShader, shader.l)
		mPrototype (glCompileShader, shader.l)
		mPrototype (glLinkProgram, shader.l)
		mPrototype (glUseProgram, shader.l)
		mPrototype (glAttachShader, Program.l _ shader.l)
		mPrototype (glShaderSource, shader.l _ numOfStrings.l _ *strings _ *lenOfStrings)
		mPrototype (glGetUniformLocation, Program _ name.p-ascii)
		mPrototype (glUniform1i, location _ v0)
		mPrototype (glUniform2i, location _ v0 _ v1)
		mPrototype (glUniform1d, location _ v0.d)
		mPrototype (glUniform2d, location _ v0.d _ v1.d)
		mPrototype (glUniform1f, location _ v0.f)
		mPrototype (glUniform2f, location _ v0.f _ v1.f)
		mPrototype (glUniform3f, location _ v0.f _ v1.f _ v2.f)
		mPrototype (glUniform4f, location _ v0.f _ v1.f _ v2.f _ v3.f)
		mPrototype (glGetShaderInfoLog, shader _ bufSize.l _ *lengthl _ *infoLog)
	CompilerEndIf
	
	;- Structure
	Structure sShaderinfo
		num.i          ;shader num
		name.s
		pg.i           ;shader program
		vcode.s
		fcode.s
		Map uloc.i()  ;uniform location
	EndStructure
	
	Structure sparam
		nom.s
		type.b
		v0.d
		v1.f
		v2.f
		v3.f
	EndStructure
	
	Structure sSpriteinfo
		num.i           ;sprite num
		sh.sShaderinfo	;shader program
		List tx.i()			;texture num
		Map param.sparam()
		Tdx.w:Tdy.w
		dx.w:dy.w
		x1.f:y1.f:u1.f:v1.f
		x2.f:y2.f:u2.f:v2.f
		x3.f:y3.f:u3.f:v3.f
		x4.f:y4.f:u4.f:v4.f
		zx.f:zy.f
		ag.f
		xo.f:yo.f
	EndStructure
	
	Structure ssc
		sx.l
		sl.l
		cl.l
		co.l
	EndStructure
	
	Structure sscfont
		ns.i
		height.f
		Array c.ssc(255)
	EndStructure
	
	Global ScrennFont.sscfont
	
	;- Global
	Global s_screendx, s_screendy, s_screendx2, s_screendy2
	Global Shadermessage.s, codevertex.s, SHvertex
	Global.f glcamx, glcamy, glcamzoom=1, glcamrot, glcami=1, glcamj
	Global.f glligthx, glligthy, glligthz, glligthdist, glligthcolor.l=0, glambiantcolor.l=$ffffffff
	Global NewMap SpriteInfo.sSpriteinfo()
	Global NewMap ShaderInfo.sShaderinfo()
	
	
	;-
	;- ■ PRIVATE PROCEDURE
	;- ¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨ 
	Procedure ImageToGLTextures(image, free=0)
		;S_CreateSprite
		
		Protected TextureID, w, h, rgb, rgba
		
		If #PB_OS_Windows:rgb=#GL_BGR_EXT:rgba=#GL_BGRA_EXT:Else:rgb=#GL_RGB:rgba=#GL_RGBA:EndIf
		
		StartDrawing(ImageOutput(image))
		glGenTextures_(1, @TextureID)
		glBindTexture_(#GL_TEXTURE_2D, TextureID)
		glTexParameteri_(#GL_TEXTURE_2D, #GL_TEXTURE_MIN_FILTER, #GL_LINEAR)
		glTexParameteri_(#GL_TEXTURE_2D, #GL_TEXTURE_MAG_FILTER, #GL_LINEAR)
		W = OutputWidth() : H = OutputHeight()
		;glPixelStorei_(#GL_PACK_ROW_LENGTH, DrawingBufferPitch())
		Select OutputDepth()
			Case 24:glTexImage2D_(#GL_TEXTURE_2D, 0,  #GL_RGB, W, H, 0, rgb, #GL_UNSIGNED_BYTE, DrawingBuffer());  
			Case 32:glTexImage2D_(#GL_TEXTURE_2D, 0,  #GL_RGBA, W, H, 0, rgba, #GL_UNSIGNED_BYTE, DrawingBuffer());  
		EndSelect
		StopDrawing()
		If free:FreeImage(image):EndIf
		ProcedureReturn TextureID  
	EndProcedure
	
	;- Brush
	Procedure initIF(image, cx.w=-1, cy.w=-1)
		;image : numero de l'image
		;centerx/y : definit le centre de l'image
		Structure sImageFont
			x.b
			y.b
			col.l
		EndStructure
		
		Protected i, j, d, k, n, c, idx, idy, x, y
		idx=ImageWidth (image):If cx=-1:cx=idx/2:EndIf
		idy=ImageHeight(image):If cy=-1:cy=idy/2:EndIf
		Global Dim IFdata.sImageFont(idx * idy-1)
		n=-1
		StartDrawing(ImageOutput(image))
		DrawingMode(#PB_2DDrawing_AllChannels)  
		Macro gplot(i, j):x=cx+i:y=cy+j:If x>=0 And x<idx And y>=0 And y<idy:c=Point(x, y):If c<>0:n+1:IFdata(n)\x=x:IFdata(n)\y=y:IFdata(n)\col=c:EndIf:EndIf:EndMacro
		gplot(0, 0)
		For d=1 To 30
			For k=0 To d-1
				gplot(-d+k, -k)
				gplot(k, -d+k)
				gplot(d-k, k)
				gplot(-k, d-k)
			Next
		Next
		ReDim IFdata(n)
		StopDrawing() 
	EndProcedure
	
	Procedure DrawVectorTextBrush(text.s)
		Protected x.f, y.f, j, n
		x=PathCursorX()
		y=PathBoundsY()
		n=ArraySize(IFdata())
		For j=n To 0 Step -1
			MovePathCursor(x+IFdata(j)\x, y+IFdata(j)\y):VectorSourceColor(IFdata(j)\col):DrawVectorText(text)
		Next   
	EndProcedure
	
	Procedure spriteverif(num)
		;Used by a lot of procedures
		
		;   If FindMapElement(SpriteInfo(), ""+num)=0:MessageRequester("S_ Erreur", "Sprite "+num+" does not exist"):CallDebugger:EndIf
		If FindMapElement(SpriteInfo(), ""+num)=0:DebuggerWarning("S_ Erreur, Sprite "+num+" does Not exist"):EndIf
		
	EndProcedure
	
	Procedure spritecoord(num)
		;S_ClipSprite, S_RotateSprite, S_SpriteOrigine, S_ZoomSprite
		
		Protected.f co, si, xs, ys, xx, yy, zxo, zyo
		
		Macro rot(x, y, xs, ys)
			xx=x-zxo
			yy=y-zyo
			xs= xx*co+yy*si
			ys=-xx*si+yy*co
		EndMacro
		
		With SpriteInfo(""+num)
			co=Cos(\ag):si=Sin(\ag)
			zxo=\xo*\zx
			zyo=\yo*\zy
			rot(0  , 0  , \x1, \y1)
			rot(\dx, 0  , \x2, \y2)
			rot(\dx, \dy, \x3, \y3)
			rot(0  , \dy, \x4, \y4)
		EndWith
		
	EndProcedure
	
	Procedure screenpos(*sx.float, *sy.float)
		;S_light, S_DisplaySprite
		
		Protected.f xx, yy
		
		xx=*sx\f-glcamx-s_screendx2
		yy=*sy\f-glcamy-s_screendy2
		*sx\f= (xx*glcami+yy*glcamj+s_screendx2)
		*sy\f=(-xx*glcamj+yy*glcami+s_screendy2)
		
	EndProcedure
	
	Procedure shaderuniform(*sh.sShaderinfo, nom.s, type, v0.d, v1.f=0, v2.f=0, v3.f=0)
		;S_DisplaySprite, s_FlipBuffers, S_globalparameter
		
		If FindMapElement(*sh\uloc(), nom)
			Select  type
				Case #PB_Shader_Integer :glUniform1i(*sh\uloc(), v0)
				Case #PB_Shader_Float   :glUniform1f(*sh\uloc(), v0)
				Case #PB_Shader_Vector2 :glUniform2f(*sh\uloc(), v0, v1)
				Case #PB_Shader_Vector3 :glUniform3f(*sh\uloc(), v0, v1, v2)
				Case #PB_Shader_Vector4 :glUniform4f(*sh\uloc(), v0, v1, v2, v3)
				Case #PB_Shader_color   :Protected c.q=v0:glUniform4f(*sh\uloc(), Red(c)/255, Green(c)/255, Blue(c)/255, Alpha(c)/255)
			EndSelect
		EndIf
	EndProcedure
	
	
	
	Procedure.s supspace(l.s)
		;ShaderCreate
		
		Protected i
		Protected.s ll, ac, c
		
		l=ReplaceString(l, #TAB$, " ")
		l=ReplaceString(l, #LF$, " ")
		l=ReplaceString(l, #CR$, " ")
		i=0:While i<Len(l)
			Repeat
				i+1
				ac=c:c=Mid(l, i, 1)
			Until c<>" " Or ac<>" "
			ll+c        
		Wend
		ProcedureReturn Trim(ll)
	EndProcedure
	
	Procedure shaderCompile(shadercode.s, type=#PB_Shader_Fragment, dbg=1)
		;ShaderCreate, S_init
		
		Protected shader, gltype, *TxtPointer, Program, Textlength, message.s = Space(1024)
		
		If type=#PB_Shader_Vertex:gltype=#GL_VERTEX_SHADER:Else:gltype=#GL_FRAGMENT_SHADER:EndIf
		shadercode=ReplaceString(shadercode, "%", #CRLF$)
		shader = glCreateShader(gltype)
		*TxtPointer = Ascii(shadercode)
		glShaderSource(shader, 1, @*TxtPointer, #Null)
		glCompileShader(shader)
		glGetShaderInfoLog(shader, 1023, @Textlength, @message)
		Shadermessage=PeekS(@message, 1023, #PB_Ascii)
		If Shadermessage
			If dbg:DebuggerWarning("error shader "+shader+#CRLF$+Shadermessage):EndIf
			ProcedureReturn
		EndIf
		ProcedureReturn shader
	EndProcedure
	
	;-
	
	;- ■ PUBLIC Procedure
	;- ¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨ 
	Procedure S_ShaderCreate(num, fshadercode.s, vshadercode.s="", name.s="", dbg=1)
		;S_init
		
		Static numauto=1000000
		Protected vshader, fshader, Program, vfcode.s, ul, txu
		If num=-1:num=numauto:numauto+1:EndIf
		
		If fshadercode="":fshader=#S_Shader_Default:Else:fshader=ShaderCompile(fshadercode, #PB_Shader_Fragment, dbg):EndIf:If fshader=0 :ProcedureReturn :EndIf
		If vshadercode="":vshadercode=codevertex:vshader=SHvertex :Else:vshader=ShaderCompile(vshadercode, #PB_Shader_Vertex, dbg):EndIf:If vshader=0 :ProcedureReturn :EndIf
		Program = glCreateProgram()
		glAttachShader(Program, vshader)
		glAttachShader(Program, fshader)
		glLinkProgram(Program)
		glUseProgram(Program)
		
		If  FindMapElement(ShaderInfo(), ""+num):DeleteMapElement(ShaderInfo(), ""+num):EndIf
		With ShaderInfo(""+num)
			\num=num
			\name=name
			\pg=Program
			\vcode=vshadercode
			\fcode=fshadercode
			Protected p, pf, l.s, n.s, t.s
			vfcode=supspace(vshadercode+fshadercode)
			Repeat
				p=FindString(vfcode, "uniform", p+1)
				pf=FindString(vfcode, ";", p)
				If p
					l=Mid(vfcode, p, pf-p)
					n=StringField(l, 3, " ")
					t=StringField(l, 2, " ")
					ul=glGetUniformLocation(Program, n)
					If FindString(t, "sampler"):glUniform1i(ul, txu):txu+1:Else:\uloc(n)=ul:EndIf 
				EndIf
			Until p=0  
		EndWith
		ProcedureReturn num
	EndProcedure
	
	;-
	;.......................................................................................
	;- └Shader editor ┘
	Global GSE_editor, GSE_message, GSE_list, GSE_run, GSE_savecb,  SE_window, shaderedit
	
	Procedure shaderEditorcallback()
		;ShaderEditor
		
		Protected event, code.s
		
		Macro updateshader
			S_ShaderCreate(shaderedit, code, "", ShaderInfo(""+shaderedit)\name, 0)
			SetGadgetText(GSE_message, Shadermessage)
			If Shadermessage=""
				ForEach SpriteInfo()
					If SpriteInfo()\sh\num=shaderedit:SpriteInfo()\sh=ShaderInfo(""+shaderedit):EndIf
				Next
			EndIf
		EndMacro
		
		Select Event()
			Case #PB_Event_CloseWindow:CloseWindow(EventWindow()):SE_window=0:ReleaseMouse(0)
			Case #PB_Event_Menu
				Select EventMenu()
					Case 1111:code = GetGadgetText(GSE_editor):updateshader
					Case 1112:CloseWindow(EventWindow()):SE_window=0:ReleaseMouse(0)
				EndSelect
			Case #PB_Event_Gadget
				Select EventGadget()
					Case GSE_list:shaderedit=GetGadgetItemData(GSE_list, GetGadgetState(GSE_list)):SetGadgetText(GSE_editor, ReplaceString(ShaderInfo(""+shaderedit)\fcode, "%", #CRLF$))
					Case GSE_run:code = GetGadgetText(GSE_editor):updateshader
					Case GSE_savecb:code=GetGadgetText(GSE_editor):code=ReplaceString(code, #CRLF$, "%"):SetClipboardText(~"SHnew=S_ShaderCreate(-1, \""+code+~"\", \"\", \""+ShaderInfo(""+shaderedit)\name+~"\")\n")
				EndSelect
		EndSelect
	EndProcedure
	
	Procedure S_ShaderEditor(shader)  
		Protected  wdx=700, xdy=600, it, ls
		
		If SE_window:ReleaseMouse(1):SetActiveWindow(SE_window): ProcedureReturn :EndIf
		shaderedit=shader
		SE_window=OpenWindow(-1, 0, 0, wdx, xdy, "Shader Editor")
		BindEvent(#PB_Event_Gadget, @shaderEditorcallback(), SE_window)
		BindEvent(#PB_Event_Menu, @shaderEditorcallback(), SE_window)
		BindEvent(#PB_Event_CloseWindow, @shaderEditorcallback(), SE_window)
		
		GSE_editor=EditorGadget(-1, 8, 30, wdx-16, xdy-30-150)
		SetGadgetText(GSE_editor, ReplaceString(ShaderInfo(""+shaderedit)\fcode, "%", #CRLF$))
		GSE_message=EditorGadget(-1, 8, xdy+8-150, wdx-16, 150-16, #PB_Editor_ReadOnly)
		
		GSE_list=ComboBoxGadget(-1, 8, 0, 90, 24):ForEach ShaderInfo():AddGadgetItem(GSE_list, -1, ShaderInfo()\name):SetGadgetItemData(GSE_list, it, ShaderInfo()\num):If ShaderInfo()\num=shader:ls=it:EndIf:it+1:Next
		SetGadgetState(GSE_list, ls)
		GSE_run=ButtonGadget(-1, 108 , 0, 90, 24, "run [F5]")
		GSE_savecb=ButtonGadget(-1, 208 , 0, 90, 24, "save clipboard")
		AddKeyboardShortcut(SE_window, #PB_Shortcut_F5, 1111) 
		AddKeyboardShortcut(SE_window, #PB_Shortcut_Escape, 1112) 
	EndProcedure
	;.......................................................................................
	
	;-
	Procedure S_BlendingMode(mode, modesource=#PB_Sprite_BlendSourceAlpha, modedestination=#PB_Sprite_BlendInvertSourceAlpha); mode:Enumeration S_BlendingMode,  mosesource/modedestination: cf:SpriteBlendingMode
		Protected glsrc, gldst
		Macro cvmode(pbmode, glmode)
			Select pbmode
				Case #PB_Sprite_BlendZero:glmode=#GL_ZERO
				Case #PB_Sprite_BlendOne:glmode=#GL_ONE
				Case #PB_Sprite_BlendSourceColor:glmode=#GL_SRC_COLOR
				Case #PB_Sprite_BlendInvertSourceColor:glmode=#GL_ONE_MINUS_SRC_COLOR
				Case #PB_Sprite_BlendDestinationColor:glmode=#GL_DST_COLOR
				Case #PB_Sprite_BlendInvertDestinationColor:glmode=#GL_ONE_MINUS_DST_COLOR
				Case #PB_Sprite_BlendSourceAlpha:glmode=#GL_SRC_ALPHA
				Case #PB_Sprite_BlendInvertSourceAlpha:glmode=#GL_ONE_MINUS_SRC_ALPHA
				Case #PB_Sprite_BlendDestinationAlpha:glmode=#GL_DST_ALPHA
				Case #PB_Sprite_BlendInvertDestinationAlpha:glmode=#GL_ONE_MINUS_DST_ALPHA
			EndSelect
		EndMacro
		
		Select mode
			Case #S_BlendingMode_alphablend: glBlendFunc_(#GL_SRC_ALPHA, #GL_ONE_MINUS_SRC_ALPHA)
			Case #S_BlendingMode_add       : glBlendFunc_(#GL_ONE, #GL_ONE)
			Case #S_BlendingMode_custom    :cvmode(modesource, glsrc):cvmode(modedestination, gldst):glBlendFunc_(glsrc, gldst)
		EndSelect
	EndProcedure 
	
	Procedure S_Camera(x.f, y.f, zoom.f=0, rotation.f=1e10)
		glcamx=x
		glcamy=y
		If zoom<>0:glcamzoom=zoom:EndIf
		If rotation<>1e10
			glcamrot=Radian(rotation)
			glcami=Cos(glcamrot)*glcamzoom
			glcamj=Sin(glcamrot)*glcamzoom
		EndIf 
	EndProcedure
	
	Procedure S_ClipSprite(num, x.f, y.f, dx.f, dy.f, mode=0)
		Spriteverif(num)
		With SpriteInfo(""+num)
			\u1=x/\Tdx:\v1=y/\Tdy
			\u2=(x+dx)/\Tdx:\v2=y/\Tdy
			\u3=(x+dx)/\Tdx:\v3=(y+dy)/\Tdy
			\u4=x/\Tdx:\v4=(y+dy)/\Tdy
			\dx=dx
			\dy=dy
		EndWith
		spritecoord(num)
	EndProcedure
	
	Procedure S_CreateSprite(num, shaderNum, image1, image2=-1, image3=-1, image4=-1); shaderNum:Enumeration S_shader2D
		If shaderNum=0:MessageRequester("Erreur S_CreateSprite", "Shader invalid"):CallDebugger:EndIf
		Static numauto=1000000
		Protected u.s, txu
		
		If num=-1:num=numauto:numauto+1:EndIf
		AddMapElement(SpriteInfo(), ""+num)
		SpriteInfo()\sh = ShaderInfo(""+shaderNum)
		Macro addtx(image)
			If image>=0
				If IsImage(image)=0:MessageRequester("Erreur S_CreateSprite", "image"+Str(txu+1)+" isn't loaded"):CallDebugger:EndIf
				AddElement(SpriteInfo()\tx())
				SpriteInfo()\tx()= ImageToGLTextures(image)
			EndIf
		EndMacro
		addtx(image1)
		addtx(image2)
		addtx(image3)
		addtx(image4) 
		With SpriteInfo()
			\Tdx=ImageWidth(image1):\dx=\Tdx
			\Tdy=ImageHeight(image1):\dy=\Tdy
			\u2=1:\u3=1:\v3=1:\v4=1
			\x2=\Tdx:\x3=\Tdx:\y3=\Tdy:\y4=\Tdy
			\zx=1:\zy=1
		EndWith
		ProcedureReturn num
	EndProcedure
	
	Procedure S_DisplaySprite(num, x.f, y.f, Alpha=$ff, color.l=$ffffff, z.f=0)
		Spriteverif(num)
		Protected.f a=alpha/255, r=Red(color)/255, g=Green(color)/255, b=Blue(color)/255, sx, sy
		Protected txu, *sp.sSpriteinfo
		
		*sp=SpriteInfo(""+num) 
		glUseProgram(*sp\sh\pg)
		ForEach *sp\tx()     
			glActiveTexture(#GL_TEXTURE0+txu):glBindTexture_(#GL_TEXTURE_2D, *sp\tx()):txu+1
		Next
		ForEach *sp\param()
			With *sp\param()
				shaderuniform(*sp\sh, \nom, \type, \v0, \v1, \v2, \v3)
			EndWith
		Next  
		
		With *sp
			Macro glv(x, y):sx=x:sy=y:If *sp\sh\num<>#S_Shader_Overlay:screenpos(@sx, @sy):EndIf:glVertex3f_(sx, sy, z):EndMacro
			glBegin_(#GL_QUADS)
			glColor4f_(r, g, b, a)
			glNormal3f_(Cos(*sp\ag+glcamrot), Sin(*sp\ag+glcamrot), 0); for tangent !
			glTexCoord2f_(\u1, \v1):glv(x+\x1, y+\y1)
			glTexCoord2f_(\u2, \v2):glv(x+\x2, y+\y2)
			glTexCoord2f_(\u3, \v3):glv(x+\x3, y+\y3)
			glTexCoord2f_(\u4, \v4):glv(x+\x4, y+\y4)
			glEnd_()   
		EndWith 
	EndProcedure
	
	Procedure S_DrawText(x, y, t.s, size=-1, color=$ffffffff)
		Protected i, ca, cx, c.ssc, zoom.f
		With ScrennFont
			If size=-1:size=\height:EndIf
			zoom=size/\height
			For i=1 To Len(t)
				c=\c(Asc(Mid(t, i, 1)))
				S_ClipSprite(\ns, c\sx, 0, c\sl, \height)
				S_ZoomSprite(\ns, c\sl*zoom, \height*zoom, #S_unit_Pixel)
				S_DisplaySprite(\ns, x+c\co*zoom, y, 255, color)
				x+c\cl*zoom
			Next
		EndWith
	EndProcedure
	
	Procedure S_FlipBuffers() 
		FlipBuffers()
		ForEach ShaderInfo()
			glUseProgram(ShaderInfo()\pg)
			shaderuniform(ShaderInfo(), "screen", #PB_Shader_Vector2, s_screendx, s_screendy)
			shaderuniform(ShaderInfo(), "campos", #PB_Shader_Vector3, s_screendx2, s_screendy2, s_screendy2)
			shaderuniform(ShaderInfo(), "ambiantcolor", #PB_Shader_color, glambiantcolor)
			shaderuniform(ShaderInfo(), "lightcolor", #PB_Shader_color, glligthcolor)
			shaderuniform(ShaderInfo(), "lightinfo", #PB_Shader_Vector4, glligthx, glligthy, glligthz, glligthdist)
			shaderuniform(ShaderInfo(), "time", #PB_Shader_Float, ElapsedMilliseconds()/1000)
		Next
		glEnable_(#GL_BLEND)
	EndProcedure
	
	Procedure S_FreeSprite(num)
		Spriteverif(num)
		glDeleteProgram(SpriteInfo(""+num)\sh\pg)
		DeleteMapElement(SpriteInfo(), ""+num)
	EndProcedure 
	
	Procedure S_Globalparameter()
		ForEach ShaderInfo()
			glUseProgram(ShaderInfo()\pg)
			shaderuniform(ShaderInfo(), "screen", #PB_Shader_Vector2, s_screendx, s_screendy)
			shaderuniform(ShaderInfo(), "campos", #PB_Shader_Vector3, s_screendx2, s_screendy2, s_screendy2)
			shaderuniform(ShaderInfo(), "ambiantcolor", #PB_Shader_color, glambiantcolor)
			shaderuniform(ShaderInfo(), "lightcolor", #PB_Shader_color, glligthcolor)
			shaderuniform(ShaderInfo(), "lightinfo", #PB_Shader_Vector4, glligthx, glligthy, glligthz, glligthdist)
			shaderuniform(ShaderInfo(), "time", #PB_Shader_Float, ElapsedMilliseconds()/1000)
		Next
	EndProcedure
	
	
	Procedure S_Init()
		s_screendx=ScreenWidth():s_screendx2=s_screendx/2
		s_screendy=ScreenHeight():s_screendy2=s_screendy/2
		
		codevertex="#version 120 %%uniform vec2 screen;% varying vec3 vpos;% varying vec4 vcolor;% varying vec2 vuv;% varying vec2 vtan;% void main() {% vtan = gl_Normal.xy;% gl_Position = vec4( gl_Vertex.xy/screen*2-1, gl_Vertex.z, 1 );gl_Position.y*=-1;% vcolor=gl_Color;% vuv=gl_MultiTexCoord0.xy;//invertv% vpos=gl_Vertex.xyz;%}"
		If #PB_OS_Windows:codevertex=ReplaceString(codevertex, "//invertv", "vuv.y=1-vuv.y;"):EndIf
		SHvertex=ShaderCompile(codevertex, #PB_Shader_Vertex)
		;Debug ReplaceString(codevertex, "%", #LF$)
		S_ShaderCreate(#S_Shader_Overlay, "#version 130 %%uniform sampler2D txt0;%%in  vec4 vcolor;%in  vec2 vuv;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0, vuv);%	fcolor =tcolor*vcolor;%}", "", "overlay")
		S_ShaderCreate(#S_Shader_Default, "#version 130 %%uniform sampler2D txt0;%%in  vec4 vcolor;%in  vec2 vuv;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0, vuv);%	fcolor =tcolor*vcolor;%}", "", "default")
		S_ShaderCreate(#S_Shader_Blend, "#version 130 %%uniform sampler2D tx0;%uniform sampler2D tx1;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%uniform float blend;%%in  vec4 vcolor;%in  vec2 vuv;%in  vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=mix(texture(tx0, vuv), texture(tx1, vuv), blend);%	float lum=max(1-distance(lightinfo.xyz, vpos)/lightinfo.w, 0);%	fcolor =tcolor*vcolor*(ambiantcolor+lightcolor*lum);%}", "", "blend")
		S_ShaderCreate(#S_Shader_Light, "#version 130 %%uniform sampler2D txt0;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%%in  vec4 vcolor;%in  vec2 vuv;%in  vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcolor=texture(txt0, vuv);%	float lum=max(1-distance(lightinfo.xyz, vpos)/lightinfo.w, 0);%	fcolor =tcolor*vcolor*(ambiantcolor+lum*lightcolor);%}", "", "light")
		S_ShaderCreate(#S_Shader_Bump, "#version 130 %%uniform sampler2D tx0;%uniform sampler2D tx1;%%uniform vec3 campos;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%in vec2 vtan;%%out vec4 fcolor;%%void main( void ) {%	vec4 tcol=texture(tx0, vuv)*vcolor;%	vec3 tnor=texture(tx1, vuv).xyz-0.5;tnor.xy*=1;%	tnor.xy=vec2(vtan.x*tnor.x+vtan.y*-tnor.y,  -vtan.y*tnor.x+vtan.x*-tnor.y);%	tnor=normalize(tnor);%	vec3 ldir=normalize(lightinfo.xyz-vpos);%	vec3 cdir=normalize(campos-vpos);%	float att=max(1-distance(lightinfo.xyz, vpos)/lightinfo.w, 0);%	float dif=max(dot(ldir, tnor), 0)*att;%	float spe=pow(max(dot(normalize(ldir+cdir), tnor), 0), 50);%	fcolor =tcol*(ambiantcolor+lightcolor*(dif+spe));%}", "", "bump")
		S_ShaderCreate(#S_Shader_Flame, "#version 130 %%uniform sampler2D tx;%uniform float time;%%in vec2 vuv;%in vec4 vcolor;%%out vec4 fcolor;%void main()%{%float odec=1;%vec2 uv=vuv;uv.y=pow(uv.y, 0.5);%vec2 pc=uv*2-1;%float h=1-dot(pc, pc);%if(h<0)discard;%float vx=time*0.08;%float vy=time*-0.2;%float lum=0.8*h*(texture(tx, uv+vec2(vx, vy+odec)).a+texture(tx, uv+vec2(-vx, vy+0.5+odec)).a);%fcolor=(lum*lum)*vcolor;%}", "", "flame")
		S_ShaderCreate(#S_Shader_Water, "#version 130 %%uniform sampler2D tx;%%uniform float time;%uniform vec3 campos;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 skycolor;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%in vec2 vtan;%%out vec4 fcolor;%%void main( void ) {%	vec2 duv=vec2(time*0.02, 0);%	vec3 tnor=(texture(tx, vuv+duv).xyz+texture(tx, vuv+0.5-duv).xyz-1).xyz;tnor.xy*=1;%	tnor.xy=vec2(vtan.x*tnor.x+vtan.y*-tnor.y,  -vtan.y*tnor.x+vtan.x*-tnor.y);%	tnor=normalize(tnor);%	vec3 ldir=normalize(lightinfo.xyz-vpos);%	vec3 cdir=normalize(campos-vpos);%	float spe=pow(max(dot(normalize(ldir+cdir), tnor), 0), 50);%	float cfresnel = 1-abs(dot(cdir, tnor));%	fcolor =mix(vcolor, skycolor, cfresnel*cfresnel)+lightcolor*spe;%}", "", "water")
		S_ShaderCreate(#S_Shader_Plasma, "#version 130 %%uniform sampler2D tx;%uniform float time;%uniform vec4 color1;%uniform vec4 color2;%%in vec2 vuv;%in vec4 vcolor;%%out vec4 fcolor;%void main()%{%vec2 duv=vec2(time*0.02, 0);%float lum=(texture(tx, vuv+duv).a+texture(tx, vuv-duv+0.5).a);%fcolor=mix(color1, color2, mod(lum*2, 1))*vcolor;%//fcolor=mix(color1, color2, (1+cos(lum*3.14*4))/2)*vcolor;%}", "", "plasma")
		S_ShaderCreate(#S_Shader_New, "#version 130 %%uniform sampler2D tx;%%// global parameters%uniform vec3 campos; // camera position%uniform vec4 ambiantcolor;%uniform vec4 lightcolor;%uniform vec4 lightinfo;  // x, y, z:position, w:range%uniform float time; // in seconds%%// keep only if you use it%in vec3 vpos; // vertex position%in vec4 vcolor; // vertex color%in vec2 vuv;  // vertex uv%in vec2 tan; // tangent (for normal mapping)%%out vec4 fcolor;%%void main()%{%vec4 tcolor=texture(tx, vuv);%fcolor=tcolor*vcolor;%}", "", "new")
	EndProcedure
	
	Procedure S_InitFont(num, name.s, height.f, style=0, brush=-1, chars.s="")
		
		Protected i, h, l, c.s, ca, im, bx, by, cx, co, cv, cl:Global nf
		If chars="":For i=32 To 128:chars+Chr(i):Next:EndIf
		
		nf=LoadFont(-1, name, height, style)
		If brush>=0:initIF(brush):bx=ImageWidth(brush):by=ImageHeight((brush)):EndIf
		IM=CreateImage(-1, 1, 1)
		StartDrawing(ImageOutput(im)):DrawingFont(FontID(nf))
		h=TextHeight(" ")+by
		l=TextWidth(chars)*1.3+Len(chars)*bx:cx=0
		StopDrawing()
		FreeImage(im)
		
		IM=CreateImage(-1, l, h, 32, #PB_Image_Transparent):StartDrawing(ImageOutput(im)):DrawingMode(#PB_2DDrawing_AllChannels):Box(0, 0, l, h, $00ffffff):StopDrawing()
		StartVectorDrawing(ImageVectorOutput(im)):VectorFont(FontID(nf))
		For i=1 To Len(chars)
			c=Mid(chars, i, 1):ca=Asc(c)
			With ScrennFont\c(ca)
				co=VectorTextWidth(c, #PB_VectorText_Visible|#PB_VectorText_Offset):If ca=126:co=0:EndIf
				cv=VectorTextWidth(c, #PB_VectorText_Visible)
				cl=VectorTextWidth(c)
				\sx=cx
				\sl=cv+bx+2
				\cl=cl+bx/2
				\co=co
				;AddPathBox(\sx, 0, \sl, h):VectorSourceColor($8800ff00):FillPath()
				MovePathCursor(cx-co+1, 0)
				If brush<0:VectorSourceColor($ffffffff):DrawVectorText(c):Else:DrawVectorTextBrush(c):EndIf
				cx+\sl+1
			EndWith
		Next
		StopVectorDrawing()
		
		ScrennFont\ns=S_CreateSprite(-1, #S_Shader_Overlay, im)
		ScrennFont\height=h
	EndProcedure
	
	Procedure S_IsSprite(num)
		If FindMapElement(SpriteInfo(), ""+num):ProcedureReturn 1:EndIf  
	EndProcedure 
	
	Procedure S_Light(x.f, y.f, z.f, dist.f, color.l, ambiantcolor.l, world=1)
		If world:screenpos(@x, @y):EndIf
		glligthx=x
		glligthy=y
		glligthz=z
		glligthdist=dist
		glligthcolor=$ff<<24 | color
		glambiantcolor=$ff<<24 | ambiantcolor
	EndProcedure
	
	Procedure S_RotateSprite(num, angle.f, mode=0)
		Spriteverif(num)
		With SpriteInfo(""+num)
			angle=Radian(angle)
			If mode:\ag+angle:Else:\ag=angle:EndIf
		EndWith
		spritecoord(num)
	EndProcedure 
	
	Procedure S_SpriteCollision(num1, X1, Y1, num2, X2, Y2)
		;TODO
		Spriteverif(num1)
		Spriteverif(num2)
	EndProcedure 
	
	Procedure S_SpriteOrigine(num, x.f, y.f, unit=#S_unit_UV) ; unit:Enumeration S_unit
		Spriteverif(num)
		With SpriteInfo(""+num)
			If unit=#S_unit_UV
				\xo=x*\Tdx
				\yo=y*\Tdy
			Else
				\xo=x
				\yo=y
			EndIf
		EndWith
		spritecoord(num)
	EndProcedure 
	
	
	Procedure S_SpriteParameter(num, parameter.s, type, v0.d, v1.f=0, v2.f=0, v3.f=0); parameter: #PB_Shader_Integer/float/vector2/vector3/vector4/color
		Protected *sh.sShaderinfo, *p.sparam
		If num=-1
			;S_SpriteParameter(-1, "screenratio", #PB_Shader_Float, glratio)
		EndIf 
		Spriteverif(num)
		With SpriteInfo(""+num)
			*p=\param(parameter)
			*p\nom=parameter
			*p\type=type
			*p\v0=v0
			*p\v1=v1
			*p\v2=v2
			*p\v3=v3
		EndWith 
	EndProcedure
	
	Procedure S_SpriteUV(num, u1.f, v1.f, u2.f, v2.f, u3.f, v3.f, u4.f, v4.f)
		Spriteverif(num)
		With SpriteInfo(""+num)
			\u1=u1:\v1=v1
			\u2=u2:\v2=v2
			\u3=u3:\v3=v3
			\u4=u4:\v4=v4
		EndWith
	EndProcedure
	
	
	
	
	
	
	
	
	
	
	
	
	
	
	
	Procedure S_TransformSprite(num, X1.f, Y1.f, X2.f, Y2.f, X3.f, Y3.f, X4.f, Y4.f)
		Spriteverif(num)
		With SpriteInfo(""+num)
			\x1=x1:\y1=y1
			\x2=x2:\y2=y2
			\x3=x3:\y3=y3
			\x4=x4:\y4=y4
			\zx=1:\zy=1
			\ag=0
		EndWith
	EndProcedure
	
	Procedure S_ZoomSprite(num, Width.f, Height.f, unit=#S_unit_UV); unit:Enumeration S_unit
		Spriteverif(num)
		With SpriteInfo(""+num)
			If unit=#S_unit_UV
				\dx=Width*\Tdx
				\dy=Height*\Tdy
			Else
				\dx=Width
				\dy=Height
			EndIf
			\zx=\dx/\tdx
			\zy=\dy/\tdy
		EndWith
		spritecoord(num)
	EndProcedure
	
	
EndModule

;====================================================================================================================================================
;====================================================================================================================================================
;====================================================================================================================================================

;-
CompilerIf #PB_Compiler_IsMainFile
	;- TEST
	
	;==================================================================================
	;  Module  >> Everything (constant, procedure, ...) beginning by 'S_' is PUBLIC           
	;=================================================================================
	
	UseModule S_Sprite
	
	ExamineDesktops()
	Define swidth=DesktopWidth(0)*0.8
	Define sheight=DesktopHeight(0)*0.8
	OpenWindow(0, 0, 0, swidth, sheight, "Lib 2D v1.0", #PB_Window_SystemMenu     |#PB_Window_ScreenCentered)
	OpenWindowedScreen(WindowID(0), 0, 0, swidth, sheight)
	S_init()
	InitKeyboard()
	InitMouse()
	;---- init screen font
	CreateImage(100, 8, 8, 32, #PB_Image_Transparent)
	StartVectorDrawing(ImageVectorOutput(100))
	VectorSourceCircularGradient(3, 3, 5)
	VectorSourceGradientColor($ffffffff, 0.0)
	VectorSourceGradientColor($ff0000ff, 0.5)
	VectorSourceGradientColor($00000000, 1.0) 
	AddPathCircle(4, 4, 4):FillPath()
	StopVectorDrawing()
	S_InitFont(0, "ink free", 30, #PB_Font_Italic, 100)
	
	Define i, sblend, sbump, sflare, sflame,  swater, scloud,  splasma,  SHwobble, swobble
	Define Event
	
	;---- load images
	UseJPEGImageDecoder()
	UsePNGImageDecoder()
	LoadImage(1, #PB_Compiler_Home+"examples/3d/Data/Textures/water.png")
	LoadImage(2, #PB_Compiler_Home+"examples/3d/Data/Textures/smoke2.png")
	LoadImage(3, #PB_Compiler_Home+"examples/3d/Data/Textures/flare.png")
	LoadImage(4, #PB_Compiler_Home+"examples/3d/Data/Textures/sky.png")
	LoadImage(5, #PB_Compiler_Home+"examples/3d/Data/Textures/nvidia/dirt_grayrocky_diffusespecular.jpg")
	LoadImage(6, #PB_Compiler_Home+"examples/3d/Data/Textures/nvidia/dirt_grayrocky_normalheight.jpg")
	LoadImage(7, #PB_Compiler_Home+"examples/3d/Data/Textures/waternormal.png")
	CreateImage(10, 512, 512, 32, #PB_Image_Transparent):StartDrawing(ImageOutput(10)):DrawingMode(#PB_2DDrawing_AlphaBlend):For i=0 To 800:Circle(Random(512-64)+32, Random(512-64)+32, 32, Random($44ffffff)):Next:StopDrawing()
	
	
	;---------------------------- init demo1
	sbump=S_CreateSprite(-1, #S_Shader_Bump, 5, 6):S_SpriteOrigine(sbump, 0.5, 0.5):S_ZoomSprite(sbump, swidth*2, sheight*2, 0):S_SpriteUV(sbump, 0, 0, 2, 0, 2, 2, 0, 2)
	sblend=S_CreateSprite(-1, #S_Shader_Blend, 1, 2):S_SpriteOrigine(sblend, 0.5, 0.5):S_ZoomSprite(sblend, 2, 2)
	sflare=S_CreateSprite(-1, #S_Shader_Overlay, 3):S_SpriteOrigine(sflare, 0.5, 0.5):S_ZoomSprite(sflare, 2, 2)
	sflame=S_CreateSprite(-1, #S_Shader_Flame, 7):S_SpriteOrigine(sflame, 0.5, 0.5):S_ZoomSprite(sflame, 1, 1.5)
	
	;----------------------------- init demo2
	swater=S_CreateSprite(-1, #S_Shader_Water, 7):S_SpriteParameter(swater, "skycolor", #PB_Shader_color, $ffffbb88):S_SpriteOrigine(swater, 0.5, 0.5):S_ZoomSprite(swater, swidth*2, swidth*2, #S_unit_Pixel)
	scloud=S_CreateSprite(-1, #S_Shader_Default, 4):S_ZoomSprite(scloud, swidth*2, swidth*2, #S_unit_Pixel):S_SpriteOrigine(scloud, 0.5, 0.5)
	
	;----------------------------- init demo3
	splasma=S_CreateSprite(-1, #S_Shader_Plasma, 7):S_SpriteParameter(splasma, "color1", #PB_Shader_color, $ffff0000):S_SpriteParameter(splasma, "color2", #PB_Shader_color, $ff00ffff):S_SpriteOrigine(splasma, 0.5, 0.5):S_ZoomSprite(splasma, sheight*2, sheight*2, #S_unit_Pixel)
	
	;---------------------------- init test shader
	SHwobble=S_ShaderCreate(-1, "#version 130 %%uniform sampler2D txt0;%uniform vec4 lightinfo;%uniform vec4 lightcolor;%uniform vec4 ambiantcolor;%uniform float time;%%in vec4 vcolor;%in vec2 vuv;%in vec3 vpos;%%out vec4 fcolor;%%void main( void ) {%	float fq=8, amp=0.04, ti=time*4;%	vec2 uv=vuv*(1+2*amp)-amp;%	uv=uv+vec2(sin(vuv.y*fq+ti)*amp, sin(vuv.x*fq+ti)*amp);%	if (uv.x<0 || uv.x>1 || uv.y<0 || uv.y>1) discard; %	vec4 tcolor=texture(txt0, uv);%	float lum=max(1-distance(lightinfo.xyz, vpos)/lightinfo.w, 0);%	fcolor =tcolor*vcolor*(ambiantcolor+lum*lightcolor);%}", "", "wobble")
	swobble=S_CreateSprite(-1, SHwobble, 10):S_SpriteOrigine(swobble, 0.5, 0.5):S_ZoomSprite(swobble, sheight, sheight, #S_unit_Pixel);:S_SpriteParameter(swobble, "amp", #PB_Shader_Float, 1)
	
	Define.f sy, a, ai, py, dy, t,   rot, zw=0.5*8, zc=0.25, example.b=0
	Define rm
	MouseLocate(swidth/2, sheight/2)
	
	Repeat
		t=ElapsedMilliseconds()/1000
		a=t*2
		sy=-t/10
		
		ClearScreen(0)
		
		S_BlendingMode(#S_BlendingMode_alphablend)
		Select example
			Case 0
				S_Camera(Sin(sy*5)*200, Sin(sy*7)*200, 1, 0)
				S_light(MouseX(), MouseY(), sheight/2, sheight*4, $ffffff, $0, 0)
				
				S_DisplaySprite(sbump, swidth/2, sheight/2)
				
				S_SpriteParameter(sblend, "blend", #PB_Shader_Float, 0.5+0.5*Cos(a)):S_DisplaySprite(sblend, swidth*0.25, sheight*0.25, $ff, $ffff00)
				S_SpriteParameter(sblend, "blend", #PB_Shader_Float, 0.5+0.5*Sin(a)):S_DisplaySprite(sblend, swidth*0.25, sheight*0.75, $ff, $ff00ff)
				
				S_BlendingMode(#S_BlendingMode_add)
				S_DisplaySprite(sflame, swidth*0.75, sheight/2, 128, $88ff)
				S_RotateSprite(sflare, 2, #PB_Relative):S_DisplaySprite(sflare, MouseX(), MouseY())
				S_BlendingMode(#S_BlendingMode_alphablend)
				
			Case 1
				rot+MouseDeltaX()*0.05
				S_Camera(0, 0, 1+Sin(sy*4)/3, rot)
				S_light(10000, -10000, 10000, 0, $ffffff, $222222*4)
				
				S_SpriteUV(swater, 0, sy, zw, sy, zw, zw+sy, 0, zw+sy):S_DisplaySprite(swater, swidth/2, sheight/2, 255, $443300)
				
				S_SpriteUV(scloud, 0, sy, zc*2, sy, zc*2, zc*2+sy, 0, zc*2+sy)
				S_DisplaySprite(scloud, swidth/2, sheight/2)
				S_SpriteUV(scloud, 0, sy, zc, sy, zc, zc+sy, 0, zc+sy)
				S_DisplaySprite(scloud, swidth/2, sheight/2)
				
			Case 2
				S_Camera(0, 0, 1, 0)
				S_DisplaySprite(splasma, swidth/2, sheight/2)
				
			Case 3
				S_Camera(0, 0, 1, 0)
				S_light(0, 0, 0, 0, 0, $ffffff, 0)
				S_DisplaySprite(sbump, swidth/2, sheight/2, $ff, $888888)
				S_DisplaySprite(swobble, swidth/2, sheight/2)
				
		EndSelect
		
		
		S_DrawText(8, 0,   "[F1] Edit shader")
		S_DrawText(8, 60,  "[Space] Change example")
		S_DrawText(8, 120, "[Esc] Quit")
		S_DrawText(8, 180, "Use mouse", 40)
		S_FlipBuffers()
		
		;   While WindowEvent():Wend
		Repeat
			Event = WindowEvent() 
			If Event = #PB_Event_CloseWindow:End:EndIf 
		Until event=0
		
		
		
		ExamineKeyboard()
		ExamineMouse()    
		If KeyboardReleased(#PB_Key_F1):S_ShaderEditor(#S_Shader_New) :EndIf
		If KeyboardReleased(#PB_Key_Space):example=(example+1)%4:EndIf
		If MouseButton(#PB_MouseButton_Right):ReleaseMouse(#True):EndIf
		
	Until KeyboardReleased(#PB_Key_Escape) Or MouseButton(#PB_MouseButton_Middle)
	
CompilerEndIf

M.
Last edited by Mesa on Thu May 23, 2024 9:14 am, edited 1 time in total.
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

@ moulder61
juste replace
If #PB_OS_Windows ...
by
if 0
or
if 1

line 144 for the color problem (I can't guarantee that it will change anything)
line 533 for y-coordinate inversion

I don't know how else to say it !

@ Mesa
ah great
I'm too lazy
change the declarations every time we change the parameters
(it would be much more practical if you could specify “public” (or whatever) when you want to share a variable or procedure)

line 949
event management is bad (at least under Windows)

Code: Select all

replace with
Repeat
	Event = WindowEvent() 
	If Event = #PB_Event_CloseWindow:End :EndIf 
Until event=0
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

@pf shadoko

OK, I managed to get it working. :)
"If 0" fixes both issues. Thanks.
I started posting on here to try to help the Linux community a bit, maybe?
I don't pretend to know much about programming, especially at your level.
Having said that, I have a few things I'm working on. I might even share them one day. ;)
I did actually do a conversion of Lady's Garden to work in Linux, just for the experience, but I'm not sure the original authors would like me sharing it?

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

@moulder61
thanks
I've redone the corrections for Linux
can you confirm if it's OK (see 1st post)

the mouse is used in the first 2 demos
(and the keyboard for commands)
if it doesn't work, that's strange, I use PB functions

i hope you'll show us your game
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

@pf shadoko

It didn't work straight away, I got a few errors:
1. Line 44: Only a literal string can be put after 'Import or ImportC'
Remove line 40:
libgl="/usr/lib64/libGL.so"
Change line 44 to:
ImportC "/usr/lib64/libGL.so"

2. image1 isn't loaded.
I changed the image paths from:
LoadImage(1,#PB_Compiler_Home+"Examples/3D/Data/Textures/water.png")
to:
LoadImage(1,#PB_Compiler_Home+"examples/3d/Data/Textures/water.png")

Seems like Linux is case sensitive. Now it works nicely on my minimal Void Linux install. :)

Regarding mouse input on the first two examples:
The light source on the first example moves very slightly if I left click and drag.
The screen rotates very slightly if I do the same on the water example.
It's not like there's enough movement for it to be particularly useful or interesting to look at. :(
Other than that, scrolling does nothing and middle clicking quits the program.

Moulder.

P.S. A few pics of one of the things I'm working on:
https://u.pcloud.link/publink/show?code ... TNpuLHDDwk
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

thanks
strange about the mouse
Do the PB examples work?
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

The examples all work, if you mean pressing space to go through the different textures?
What is the mouse supposed to do exactly?
I noticed that you put in a check when defining libgl.s, but I can't see how you can get that to work unless you include ImportC in the statements as it won't accept anything but a literal string?

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
User avatar
pf shadoko
Enthusiast
Enthusiast
Posts: 385
Joined: Thu Jul 09, 2015 9:07 am

Re: Lib Screen (Sprite) (PB 6.10)

Post by pf shadoko »

- libGL.so :
I've removed the tests, so everyone can choose their own import

- mouse :
in example 1 (case 0) the light follows the mouse
in example 2 (case 1) the screen rotates as the mouse moves horizontally
I'm talking about the PB examples (press F1 on "MouseX()" )
User avatar
moulder61
Enthusiast
Enthusiast
Posts: 188
Joined: Sun Sep 19, 2021 6:16 pm
Location: U.K.

Re: Lib Screen (Sprite) (PB 6.10)

Post by moulder61 »

pf shadoko wrote: Thu May 23, 2024 5:38 pm - libGL.so :
I've removed the tests, so everyone can choose their own import
I tried to come up with a clever way around it but failed miserably.
pf shadoko wrote: Thu May 23, 2024 5:38 pm - mouse :
in example 1 (case 0) the light follows the mouse
in example 2 (case 1) the screen rotates as the mouse moves horizontally
In both examples the mouse hardly has any effect. It works slightly better if I move the mouse very slowly.
pf shadoko wrote: Thu May 23, 2024 5:38 pm I'm talking about the PB examples (press F1 on "MouseX()" )
I thought you meant while running your program, but that didn't help. Pressing F1 in the PB IDE and going to the help screen for MouseX doesn't give me any examples.(I'm using PB 6.04 if that makes any difference?)
I find "Help" to be pretty unhelpful. Maybe it's just me coming up with things so original that nobody else has thought of them, ever? I get that a lot. :)
I've made more progress by guessing or just making stuff up. It's hard work!

Moulder.
"If it ain't broke, fix it until it is!

This message is brought to you thanks to SenselessComments.com

My PB stuff for Linux: "https://u.pcloud.link/publink/show?code ... z3MR0T3jyV
Post Reply