Page 1 sur 3

Lib screen (Sprite)

Publié : dim. 05/mai/2024 15:03
par Guillot
[EDIT 05/17/2024] some shader corrections
[EDIT 05/18/2024] x86 corrections
[EDIT 05/23/2024] Linux corrections


salut les codeurs,

j'ai fais une petite lib pour remplacer la lib sprite
- gestion des shaders (avec éditeur intégré, modifs en temps réel)
- gestion de la lumière
- gestion de la camera (modifie la position, zoom et rotation de l'ensemble de la scène)
- possibilité de définir le point d'origine du sprite (zoom et rotation sont centrés sur ce point)
- possibilité de définir les coordonnées UV des sprites
- affichage de texte (rapide), possibilité d'utiliser un pinceau (brush)
(pas de gestion des collisions pour l'instant)

l'utilisation est un peu différente, notamment la création des sprite à partir d'image (cf demo)
les exemples d'utilisation sont en fin de programme (à partir de la ligne 725)

concernant les shaders:
le shader "new" (comobox en haut a droite de l'éditeur) contient la liste des "varying" envoyé par le vertex shader et la liste des paramètres (uniform) globaux)
pour creer un nouveau shader:
dans l'editeur choisissez un shader comme modele (combobox), cliquez sur "save clipboard" et copier le dans votre code :
SHnew=shaderCreate(-1,"#version 130 ....
pour l'utiliser:
mysprite=S_CreateSprite(-1,SHnew,image)
(remplacer le nom du shader a votre guise)

vous trouverez un peu de doc dans le code, les plus intelligents devraient pouvoir se demerder avec, pour tous les autres :P , j'attends vos questions

si ça interesse du monde, je pense faire une version plus fidele à ce que sont réellement les sprites
en PB, les sprite sont plus ou moins une image que l'on redessine à chaque frame
je pense faire quelque chose equivalent aux "entity" en 3D (plus de DisplaySprite)
ça permettra une gestion des collisions plus cohérente, possibilité de tri sur la profondeur (pour les jeux en 3d isometrique notamment)

Code : Tout sélectionner

;=======================================================
;            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 
  ; =================== Please choose your libGL.so folder ===================
  ;ImportC "/usr/lib/x86_64-linux-gnu/libGL.so"
  ;ImportC "/usr/lib/libGL.so"
  ImportC "/usr/lib64/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_Compiler_OS = #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_Compiler_OS = #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
  While WindowEvent():Wend
  ExamineKeyboard()
  ExamineMouse()    
  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()
  
  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)

Re: Lib screen (Sprite)

Publié : dim. 05/mai/2024 16:32
par Mindphazer
Salut,
j'ai une erreur

Code : Tout sélectionner

[17 :29 :57] [ERREUR] Ligne: 394
[17 :29 :57] [ERREUR] La liste chaînée ne contient aucun élément en cours.
[17 :30 :03] Le programme a été arrêté.
Sur MacOS (PB 6.10 - MacOS 14.4.1)

Re: Lib screen (Sprite)

Publié : dim. 05/mai/2024 17:16
par Guillot
Ah merde
y'a des image qui ont sans doute pas été chargées (TU DOIS PAS AVOIR sky et waternormal)
c'est depuis la 6.11

Re: Lib screen (Sprite)

Publié : dim. 05/mai/2024 18:23
par Mindphazer
Je viens d'essayer avec la 6.11 (b2)
Même résultat....

En fait, j'ai pas le dossier Nvidia dans les exemples, donc il manque ces deux images :
dirt_grayrocky_diffusespecular.jpg
dirt_grayrocky_normalheight.jpg

Re: Lib screen (Sprite)

Publié : lun. 06/mai/2024 17:24
par Mindphazer
En fait, c'est pas un problème de chargement des images, elles se chargent toutes correctement...
Mais le debugger n'est pas content :

Code : Tout sélectionner

error shader 1
ERROR: 0:1: '' :  version '130' is not supported
ERROR: 0:12: ';' : syntax error: syntax error

error shader 2
ERROR: 0:1: '' :  version '130' is not supported

error shader 3
ERROR: 0:1: '' :  version '130' is not supported

error shader 4
ERROR: 0:1: '' :  version '130' is not supported

error shader 5
ERROR: 0:1: '' :  version '130' is not supported

error shader 6
ERROR: 0:1: '' :  version '130' is not supported

error shader 7
ERROR: 0:1: '' :  version '130' is not supported

error shader 8
ERROR: 0:1: '' :  version '130' is not supported

error shader 9
ERROR: 0:1: '' :  version '130' is not supported

error shader 10
ERROR: 0:1: '' :  version '130' is not supported

Re: Lib screen (Sprite)

Publié : mar. 07/mai/2024 10:59
par Guillot
bon, on va essayer de resoudre ce probleme sur mac

dans la procedure s_init
remplace la ligne
shaderCreate(#SHoverlay,"#version 130 ...
par
shaderCreate(#SHoverlay,"#version 330 %%uniform sampler2D txt0;%%in vec4 vcolor;%in vec2 vuv;%%out vec4 fcolor;%%void main( void ) {% vec4 tcolor=texture(txt0,vuv);% fcolor =tcolor*vcolor;%}","","overlay")

ça devrai supprimer l'erreur sur le shader 2

Re: Lib screen (Sprite)

Publié : mar. 07/mai/2024 16:24
par Mindphazer
Hum, c'est pas gagné encore :
error shader 2
ERROR: 0:1: '' : version '330' is not supported
Et toujours le plantage sur
[17 :22 :37] [ERREUR] Ligne: 391
[17 :22 :37] [ERREUR] La liste chaînée ne contient aucun élément en cours.

Re: Lib screen (Sprite)

Publié : mar. 07/mai/2024 17:48
par Guillot
et tu me dis que les demos 3D shader fonctionnent (t'as bien les effet de vague sur l'eau, de relief sur la texture des objet ?)
curieux j'ai un peu regardé sur internet, il parle d'une gestion minimal d'opengl sur mac m1, sans shader notamment

Re: Lib screen (Sprite)

Publié : mar. 07/mai/2024 22:08
par Mindphazer
Bah la démo Shader Sky Water Bump fonctionne, j'ai l'impression correctement, mais il faudrait que je la lance sur PC pour vérifier que les effets sont identiques

Re: Lib screen (Sprite)

Publié : mer. 08/mai/2024 17:47
par G-Rom
Salut Guillot , j'ai cela qui traine sur mon DD :

Import OpenGL : https://pastebin.com/EeEWLV7e
Import GLFW3 : https://pastebin.com/7ibAP7N7

Pour OpenGL, c'est sous forme de module.

OpenGL::Load() est à appeler après la creation d'un contexte :
glfwWindowHint( ...
glfwCreateWindow( ...
OpenGL::Load()
et le fichier helper pour importer les fonctions de glfw3 ( le .lib est supporté maintenant par pb )
tu pourras utilisé de l'opengl "moderne" , et faire joujou avec les shaders.

Code : Tout sélectionner

; /////////////////////////////////////////////////////////////////////////////
; 
;        ██████╗██████╗ ██╗     ██████╗  █████╗ ████████╗ ██████╗ ██████╗ 
;       ██╔════╝██╔══██╗██║     ██╔══██╗██╔══██╗╚══██╔══╝██╔═══██╗██╔══██╗
;       ██║     ██████╔╝██║     ██████╔╝███████║   ██║   ██║   ██║██████╔╝
;       ██║     ██╔═══╝ ██║     ██╔══██╗██╔══██║   ██║   ██║   ██║██╔══██╗
;       ╚██████╗██║     ███████╗██████╔╝██║  ██║   ██║   ╚██████╔╝██║  ██║
;        ╚═════╝╚═╝     ╚══════╝╚═════╝ ╚═╝  ╚═╝   ╚═╝    ╚═════╝ ╚═╝  ╚═╝
; 
; 
; MIT License
; 
; Copyright (c) 2022 , CplBator
; 
; Permission is hereby granted, free of charge, To any person obtaining a copy
; of this software And associated documentation files (the "Software"), To deal
; in the Software without restriction, including without limitation the rights
; To use, copy, modify, merge, publish, distribute, sublicense, And/Or sell
; copies of the Software, And To permit persons To whom the Software is
; furnished To do so, subject To the following conditions:
; 
; The above copyright notice And this permission notice shall be included in all
; copies Or substantial portions of the Software.
; 
; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS Or
; IMPLIED, INCLUDING BUT Not LIMITED To THE WARRANTIES OF MERCHANTABILITY,
; FITNESS For A PARTICULAR PURPOSE And NONINFRINGEMENT. IN NO EVENT SHALL THE
; AUTHORS Or COPYRIGHT HOLDERS BE LIABLE For ANY CLAIM, DAMAGES Or OTHER
; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT Or OTHERWISE, ARISING FROM,
; OUT OF Or IN CONNECTION With THE SOFTWARE Or THE USE Or OTHER DEALINGS IN THE
; SOFTWARE.
;
; /////////////////////////////////////////////////////////////////////////////  

Macro void:EndMacro

Macro _QUOTE_:"
EndMacro

Macro _ :,:EndMacro

Macro IMPORT_STATIC_FUNCTION(_LIB_, _NAME_, _RET_, _PARAMS_)
  ImportC _QUOTE_#_LIB_#_QUOTE_
    _NAME_#_RET_(_PARAMS_)
  EndImport
EndMacro

Macro IMPORT_DYNAMIC_FUNCTION(_LIB_, _NAME_, _RET_, _PARAMS_)
  PrototypeC#_RET_ _NAME_(_PARAMS_)
  Global _NAME_._NAME_ = GetFunction(_LIB_,_QUOTE_#NAME#_QUOTE_)
EndMacro

Re: Lib screen (Sprite)

Publié : mer. 15/mai/2024 18:49
par Guillot
salut G-rom

ben pourquoi t'essais pas de le faire ?
j'ai un peu regardé, ça reprend exactement les fonction opengl

sinon t'as testé mon code ? ça marche chez toi ?

Re: Lib screen (Sprite)

Publié : jeu. 16/mai/2024 21:09
par G-Rom
salut G-rom
ben pourquoi t'essais pas de le faire ?
Parce que j'ai pas le temps. c'est pas l'envie qui m'en manque, j'ai même déjà un truc qui fonctionne qq part sur un de mes disque ( avec transformation matricielle , primitive de rendu , le tout en pb ). je ne peu pas lâcher le code comme ca , faut que je prenne du temps pour faire , et le temps me fait défaut.
j'ai un peu regardé, ça reprend exactement les fonction opengl
c'est le but, mais avec de l'opengl moderne , fini l'opengl des années 2000 comme cela :

Code : Tout sélectionner

 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_()   
le but est d'utilisé les VAO & VBO , voici mon code :

https://pastebin.com/XUNT5rzf

La fonction Update & Draw qui vont être interessant pour toi , ce code n'est qu'un "Tableau de vertice" sous forme de module
Math::real est une macro ".f" ou ".d" , je dois avoir Matrix4.pbi & Vector2.pbi si tu veut.
sinon t'as testé mon code ? ça marche chez toi ?
ima ligne 391

Code : Tout sélectionner

error shader 1
0(4) : error C5060: out can't be used with non-varying vpos
0(5) : error C5060: out can't be used with non-varying vcolor
0(6) : error C5060: out can't be used with non-varying vuv
0(7) : error C5060: out can't be used with non-varying tan

error shader 3
0(12) : warning C7533: global variable gl_FragColor is deprecated after version 120

Après , y a Vulkan , mais pas vraiment nécessaire en PB... ca n'apportera rien de s'en occupé.


j'ai du stoppé net mon code a cause du temps mais aussi a cause de pb lui meme ( les modules , l'abstraction , & les macro ) PB n'aime pas trop. L'idéal est de pondre un code C++ compatible PB , beaucoup plus simple a faire que de tout faire en PB, mais je me suis bien amusé a le faire.

edit:

Math.pbi
Matrix4.pbi
Vector2.pbi
Spatial2D.pbi
Texture2D.pbi


en gros , un sprite ou tout autre "Drawable" sera du genre :

Code : Tout sélectionner

  Structure sDrawable
    texture.Texture::iTexture
    shader.Shader::iShader
    spatial.Spatial2D::iSpatial2D
    vertexBuffer.VertexBuffer::iVertexBuffer
    SetTextureCallBack.SetTextureCallBack
  EndStructure
et mon module "Monitor" dessine du drawable , peu importe si c'est un sprite, du texte bitmap , une forme géométrique ect...
en espérant que mes codes puissent t'inspiré.

Re: Lib screen (Sprite)

Publié : ven. 17/mai/2024 10:08
par Guillot
tiens j'ai modifié mon code
tu peut retester et me dire si les shaders passent mieux
mon problème c'est que je suis sur un chipset intel, le pilote est trop permissif (je peux faire plein de boulettes, ça passe tjrs)

sinon pour ce qui est du vbo/vao ça devrait pas etre sorcier a passer les données par un buffer (y'a juste quelques lignes à changer)

pour ce qui est de gflw3 faudra voir avec fred pour l'integrer dans une fenetre PB
j'ai regarder sur le site, y'a un erxemple, la creation des shader est similaire a opengl, donc l'adaptation devrait etre vite vu
enfin, à priori !

ça pourrait être intéressant si le multi ecran est mieux géré, ainsi que les manettes, parce que là aussi PB est completement largué, (pas de gestion des triggers indépendant, manette apparaissant 2 fois dans la liste des joysticks connectés)

Re: Lib screen (Sprite)

Publié : ven. 17/mai/2024 17:42
par G-Rom
...ça pourrait être intéressant si le multi ecran est mieux géré...
C'est pour cela que j'ai intégré GLFW , je fabriquais des bornes d'arcade , c'est utile ( si tu utilise un marquee ( l'écran bannière en haut ) ) , pareil pour les joysticks , mieux géré , y a des callbacks en cas de déco / reco ( écran , joystick )
pour ce qui est de gflw3 faudra voir avec fred pour l'integrer dans une fenetre PB
https://discourse.glfw.org/t/attach-a-g ... area/882/5

Pour faire de l'embeding dans un widget existant , faut si connaitre dans les différentes API système , je ne suis pas calé pour cela , mais avec un peu de recherche , ca doit être jouable.
sinon pour ce qui est du vbo/vao ça devrait pas etre sorcier a passer les données par un buffer (y'a juste quelques lignes à changer)
Mon module VertexBuffer est fait pour cela. ( voir mon topic plus haut )

Si tu veut faire une lib dédié à PB pour la 2D , faut que tu partes sur du c++ / c , le C pour l'export vers PB , c'est plus facile de faire de l'abstraction en c++ qu'en PB, pb n'est pas prévu pour.

Tu vas me demandé pourquoi faire de l'abstraction :

En graphisme , tout est une question de vertex , d'uv , de couleur , etc... que se soit un sprite , du texte , des formes géométrique , etc...
le point commun de tout cela , le vertex buffer , d'où l'abstraction.

Quel est ton objectif final ? tu parles dans ton premier topic , de faire du z-ordering ( ta citation sur l'exemple isométrique ) , on sort du cadre d'un simple affichage de sprite. tu parts sur un petit moteur de rendu , en soit , c'est pas sorcier, mais y a du taf a fournir.

J'ai testé ton code, Erreur s_sprite "Image1 isnt loaded" et sa boucle dans le vide.

Re: Lib screen (Sprite)

Publié : ven. 17/mai/2024 18:15
par Guillot
comme je t'ai dis plusieurs fois je connais pas le c (et j'aime pas le c)
de plus Fred est sensé ajouter la possibilité de faire des lib depuis PB (il m'avais promis ça pour dans 3/4 mois, y'a deja 8 mois !)
mon objectif est juste d'améliorer la lib sprite

concernant le zbuffer c'est pour pouvoir faire de la 3d isometrique entre autre, genre des personnages qui ce baladent devant ou derriere des objets par exemple, en l'état c'est compliquer de gerer ça, on doit afficher le sprite au milieu du code affichant le décor


mon code nécéssite PB 6.10 (j'utilise 2 textures qui sont incluses depuis cette version)