Avec kernadec , nous avons écrit ce programme .
voici une fonction "lasso" similaire à celle d'un logiciel de dessin
le code est très brouillon, n'hésitez pas à l'améliorer.
Code : Tout sélectionner
UseJPEG2000ImageDecoder()
UseTIFFImageDecoder()
UseTGAImageDecoder()
UseGIFImageDecoder()
UseJPEGImageDecoder()
UseJPEGImageEncoder()
UsePNGImageDecoder()
UsePNGImageEncoder()
#width = 800
#height = 600
Enumeration
#Lasso_Window_0
#Lasso_Window_1
#Lasso_Image_0
#Lasso_Image_1
#Lasso_Image_2
#Lasso_Image_3
#Lasso_Gadget_0
#Lasso_Gadget_1
#Lasso_Gadget_2
#Lasso_Gadget_3
#lasso_Menu_0
EndEnumeration
Structure copys
index.i
addr.i
px.i
py.i
lg.i
ht.i
dx.i
dy.i
EndStructure
Global NewList mescopy.copys()
Global source = 0
Global cible = 20
Global original = 40
Global img_tmps = 50
Global NewList V.point()
Macro Coo_Segment( Pa, Pb, Liste )
*Situation = @Liste
Pa = Liste : If NextElement( Liste ) = 0 : FirstElement( Liste ) : EndIf
Pb = Liste : ChangeCurrentElement( Liste, *Situation )
EndMacro
; charge une image et la convertie en 32bit
;-------------------------------------------------------------------
Procedure load_image(nom,file$)
Protected nom_p.i , temps_p.i , x.l , y.l , r.l,g.l,b.l , i.l
Protected lg.l , ht.l , depth.l , temps.i , dif.l , dif1.l
LoadImage(nom,file$)
If Not IsImage(nom) : ProcedureReturn 0 : EndIf
StartDrawing(ImageOutput(nom))
Depth=OutputDepth()
StopDrawing()
If Depth=24
CopyImage(nom,temps)
FreeImage(nom)
StartDrawing(ImageOutput(temps))
temps_p = DrawingBuffer()
lg = ImageWidth(temps)
ht = ImageHeight(temps)
dif = DrawingBufferPitch() - (lg*3)
StopDrawing()
CreateImage(nom,lg,ht,32)
StartDrawing(ImageOutput(nom))
nom_p = DrawingBuffer()
StopDrawing()
For y=0 To ht-1
For x=0 To lg-1
i = ((y*lg)+x)*3
r=PeekA(temps_p + i + 2 + dif1)
g=PeekA(temps_p + i + 1 + dif1)
b=PeekA(temps_p + i + 0 + dif1)
PokeL(nom_p + ((y*lg)+x)*4 , $ff000000 + r<<16 + g<<8 + b)
Next
dif1 = dif1 + dif
Next
FreeImage(temps) ; supprime l'image 24bits
EndIf
ProcedureReturn 1
EndProcedure
;------------------------------------------------------------------
Procedure fusionner(List mescopy.copys(),cible)
source_p = mescopy()\addr
ht1 = mescopy()\ht
lg1 = mescopy()\lg
px = mescopy()\px
py = mescopy()\py
StartDrawing(ImageOutput(cible))
cible_p = DrawingBuffer()
ht2 = ImageHeight(cible)
lg2 = ImageWidth(cible)
StopDrawing()
For y=0 To ht1-1
For x=0 To lg1-1
pos1 = source_p + ((y * lg1) + x) * 4
x2 = x + px
y2 = y + py
If x2>=0 And x2<lg2 And y2>=0 And y2<ht2
pos2 = cible_p + ((y2 * lg2) + x2) * 4
a = PeekA(pos1 + 3)
If a<>0
rgb = PeekL(pos1)
PokeL(pos2 , rgb)
EndIf
EndIf
Next
Next
EndProcedure
Procedure cn_PnPoly( px,py , List Polylist.point() )
Define pa.point, pb.point, cn.l
ForEach Polylist() : Coo_Segment( Pa, Pb, Polylist() )
If (((pa\y <= py) And (pb\y > py)) Or ((pa\y > py) And (pb\y <= py)))
vt.f = (py - pa\y) / (pb\y - pa\y);
If (px < pa\x + vt * (pb\x - pa\x)) ;
cn+1 ; ;
EndIf
EndIf
Next
ProcedureReturn (cn&1); // 0 if even (out), and 1 if odd (in)
EndProcedure
Procedure copy(source , cible , px , py)
StartDrawing(ImageOutput(source))
source_p = DrawingBuffer()
ht1 = ImageHeight(source)
lg1 = ImageWidth(source)
StopDrawing()
StartDrawing(ImageOutput(cible))
cible_p = DrawingBuffer()
ht2 = ImageHeight(cible)
lg2 = ImageWidth(cible)
StopDrawing()
StartDrawing(ImageOutput(#Lasso_Image_3))
lasso_p = DrawingBuffer()
ht3 = ImageHeight(#Lasso_Image_3)
lg3 = ImageWidth(#Lasso_Image_3)
StopDrawing()
; si le pixel est dans le 'lasso' : pixel_alpha=255 : si non : pixel_alpha=0
For y=0 To ht2-1
For x=0 To lg2-1
pos2 = ((y*lg2)+x)*4
PokeL(cible_p + pos2 , 0) ; rempli l'image de 0 ( a=0 : r=0 : g=0 : b=0)
If cn_PnPoly( px+x,py+y , v() )> 0
y1 = (y + py) * lg1
pos1 = ((y1+x+px) * 4); lit l'image source rgb
argb = PeekL(source_p + pos1)
PokeL(cible_p + pos2 , argb) ; $ff000000 = alpha
; cree le "" sur l'image source
rgb = PeekL(lasso_p + ((y*lg3)+x)*4)
PokeL(source_p + pos1,rgb & $00ffffff)
EndIf
Next
Next
EndProcedure
Procedure create_new_picture(source)
; calcul la taille de l'image selectionnée par le 'lasso'
If ListSize(v()) = 0 : ProcedureReturn : EndIf
pminx=999999
pminy=999999
pmaxx=0
pmaxy=0
ForEach v()
If pminx > v()\x : pminx = v()\x :EndIf
If pminy > v()\y : pminy = v()\y :EndIf
If pmaxx < v()\x : pmaxx = v()\x :EndIf
If pmaxy < v()\y : pmaxy = v()\y :EndIf
Next
lg = pmaxx - pminx
ht = pmaxy - pminy
; cree la nouvelle image
CreateImage(cible,lg,ht,32, #PB_Image_Transparent)
copy(source , cible ,pminx , pminy)
OpenWindow(#Lasso_Window_1, 0, 0, lg, ht, "Calque", #PB_Window_SystemMenu )
StartDrawing(ImageOutput(#Lasso_Image_1))
DrawingMode(#PB_2DDrawing_AlphaBlend)
DrawImage(ImageID(#Lasso_Image_3), 0, 0)
DrawAlphaImage(ImageID(cible),0,0)
StopDrawing()
img = CopyImage(cible,#PB_Any)
AddElement(mescopy())
StartDrawing(ImageOutput(img))
mescopy()\index = img
mescopy()\addr = DrawingBuffer()
mescopy()\ht = ImageHeight(img)
mescopy()\lg = ImageWidth(img)
mescopy()\px = ListSize(mescopy()) * 25
mescopy()\py = ListSize(mescopy()) * 25
StopDrawing()
ImageGadget(#Lasso_Gadget_1, 0, 0, WindowWidth(1), WindowHeight(1), ImageID(#Lasso_Image_1))
EndProcedure
Procedure draw_alpha(List mescopy.copys(),cible)
source_p = mescopy()\addr
ht1 = mescopy()\ht
lg1 = mescopy()\lg
px = mescopy()\px
py = mescopy()\py
StartDrawing(ImageOutput(cible))
cible_p = DrawingBuffer()
ht2 = ImageHeight(cible)
lg2 = ImageWidth(cible)
StopDrawing()
For y=0 To ht1-1
For x=0 To lg1-1
pos1 = source_p + ((y * lg1) + x) * 4
x2 = x + px
y2 = y + py
If x2>=0 And x2<lg2 And y2>=0 And y2<ht2
pos2 = cible_p + ((y2 * lg2) + x2) * 4
a = PeekA(pos1 + 3)
If a<>0
rgb = PeekL(pos1)
PokeL(pos2, rgb)
EndIf
EndIf
Next
Next
EndProcedure
OpenWindow(#Lasso_Window_0, 0, 0, #width, #height, "lasso- " + Str(TotalSeconds),#PB_Window_SystemMenu|#PB_Window_ScreenCentered)
If CreateMenu(#lasso_Menu_0, WindowID(#Lasso_Window_0))
MenuTitle("Fichiers")
MenuItem(1, "Ouvrir" +Chr(9)+"Ctrl+O")
MenuBar()
MenuItem(2, "Enregistrer sous"+Chr(9)+"Ctrl+R")
MenuBar()
MenuItem(3, "Quitter" +Chr(9)+"Ctrl+Q")
MenuTitle("Edition")
MenuItem(4, "Annuler" +Chr(9)+"Ctrl+Z")
MenuBar()
MenuItem(5, "Copier" +Chr(9)+"Ctrl+C")
MenuItem(6, "Coller" +Chr(9)+"Ctrl+V")
MenuBar()
MenuItem(7, "Couper" +Chr(9)+"Ctrl+X")
MenuTitle("Outils")
MenuItem(8, "Selection Lasso")
EndIf
CreateImage(#Lasso_Image_0, #width,#height,32)
CreateImage(#Lasso_Image_1, #width,#height,32)
CreateImage(#Lasso_Image_2, #width,#height,32)
CreateImage(#Lasso_Image_3, #width,#height,32)
CreateImage(img_tmps, #width,#height,32)
StartDrawing(ImageOutput(#Lasso_Image_3)) ; auteur netmaestro ;) je n'ai mis que la couleur à 204 comme photoshop
For i = 0 To WindowWidth(0) * 2 Step 16
For j = 0 To WindowWidth(0) * 2 Step 16
Box(j,i,8,8,RGB(204,204,204))
Box(j+8,i,8,8,#White)
Box(j,i+8,8,8,#White)
Box(j+8,i+8,8,8,RGB(204,204,204))
Next
Next
StopDrawing()
ImageGadget(#Lasso_Gadget_3, 0, 0, WindowWidth(0), WindowHeight(0), ImageID(#Lasso_Image_3))
capture = 1 ; "capture" est similaire a "opt"
opt = 0
Repeat
mx = WindowMouseX(#Lasso_Window_0)
my = WindowMouseY(#Lasso_Window_0)
Event = WaitWindowEvent()
Select event
Case #WM_LBUTTONDOWN
If capture = 1
If opt = 0
AddElement(v()) ; ajoute une coordonnee au lasso
v()\x = mx
v()\y = #height - my
EndIf
EndIf
If capture = 0
If deplace = 0 And ListSize(mescopy())>0
; selection une copy a deplacer
LastElement(mescopy())
my1 = #height - my
If mx > mescopy()\px And mx < (mescopy()\px + mescopy()\lg)
If my1 > mescopy()\py And my1 < (mescopy()\py + mescopy()\ht)
mescopy()\dx = mescopy()\px - mx
mescopy()\dy = mescopy()\py - my1
deplace = 1
EndIf
EndIf
If deplace = 0
ForEach mescopy()
If mx > mescopy()\px And mx < (mescopy()\px + mescopy()\lg)
If my1 > mescopy()\py And my1 < (mescopy()\py + mescopy()\ht)
mescopy()\dx = mescopy()\px - mx
mescopy()\dy = mescopy()\py - my1
deplace = 1
MoveElement(mescopy(),#PB_List_Last)
Break
EndIf
EndIf
Next
EndIf
Else
deplace = 0
EndIf
EndIf
Case #WM_RBUTTONDOWN
If deplace = 0 And capture = 0
Resultat = MessageRequester("fusionner", "voulez vous fusionner le calque avec 'limage" ,#PB_MessageRequester_YesNoCancel)
If Resultat = 6
fusionner(mescopy(),source)
DeleteElement(mescopy())
deplace = 0
EndIf
EndIf
Case #PB_Event_Menu
Select EventMenu() ; To see which menu has been selected
Case 1 ; charge image
file$ = OpenFileRequester("Image","","",0)
source = 10
If Not Load_Image(source,file$)
MessageRequester("load_image","erreur de chargement",#PB_MessageRequester_Ok | #PB_MessageRequester_Error)
End
EndIf
ResizeImage(source,#width,#height,#PB_Image_Smooth)
CopyImage(source,original)
SetActiveWindow(#Lasso_Window_0) ; Restore la source
StartDrawing(WindowOutput(#Lasso_Window_0))
;If IsImage(source) : DrawImage(ImageID(original),0,0) : EndIf
If IsImage(source) : DrawImage(ImageID(source),0,0) : EndIf
StopDrawing()
Case 2 ; sauve image
Case 3 ; eXit
End
Case 4 ; annuler
ClearList(v())
Case 5 ; copier
If opt = 0
opt = 1
create_new_picture(source)
*Memory = EncodeImage(cible, #PB_ImagePlugin_PNG)
SetClipboardText(Str(*Memory))
*Memory = Val(GetClipboardText())
CatchImage(#Lasso_Image_2, *Memory) ; L'image est en mémoire
SaveImage(#Lasso_Image_2, "d:\purebasic64\\Imagelassot.png",#PB_ImagePlugin_PNG,32)
EndIf
; retour activation de la fenetre principale
capture = 0
ClearList(v())
SetActiveWindow(#Lasso_Window_0) ; Restore la source
StartDrawing(WindowOutput(#Lasso_Window_0))
;If IsImage(source) : DrawImage(ImageID(original),0,0) : EndIf
If IsImage(source) : DrawImage(ImageID(source),0,0) : EndIf
StopDrawing()
;CopyImage(oroginal,source); on restore l'original
Case 6 ; coller
Case 7 ; couper
Case 8 ; lasso
ClearList(v())
opt = 0
If capture = 0 : capture = 1 : EndIf
EndSelect
EndSelect
If capture = 1
If ListSize(v()) > 0 ; "affiche" le lasso
StartDrawing(WindowOutput(#Lasso_Window_0))
DrawImage(ImageID(img_tmps),0,0)
FirstElement(v())
x1 = v()\x
y1 = v()\y
ForEach v()
x = v()\x
y = v()\y
DrawingMode(#PB_2DDrawing_XOr)
If opt = 0 : LineXY(x1,#height - y1,x,#height - y,$ffffff) : EndIf
x1=x
y1=y
Next
StopDrawing()
EndIf
EndIf
If deplace = 1
LastElement(mescopy())
mescopy()\px = mx + mescopy()\dx
mescopy()\py = (#height - my) + mescopy()\dy
EndIf
StartDrawing(ImageOutput(img_tmps))
If source <> 0
DrawImage(ImageID(source),0,0)
Else
DrawImage(ImageID(#Lasso_Image_3),0,0)
EndIf
StopDrawing()
; update affichage des copy
ForEach mescopy()
draw_alpha(mescopy(), img_tmps)
Next
StartDrawing(WindowOutput(#Lasso_Window_0))
DrawImage(ImageID(img_tmps),0,0)
StopDrawing()
; affichage le rectangle autour de l'image selectionnee
my1 = #height - my
ForEach mescopy()
If mx > mescopy()\px And mx < (mescopy()\px + mescopy()\lg)
If my1 > mescopy()\py And my1 < (mescopy()\py + mescopy()\ht)
StartDrawing(WindowOutput(#Lasso_Window_0))
DrawingMode(#PB_2DDrawing_XOr)
Line(mescopy()\px,#height - mescopy()\py,1,-mescopy()\ht)
Line(mescopy()\px,#height - mescopy()\py,mescopy()\lg,1)
Line(mescopy()\px + mescopy()\lg,#height - mescopy()\py,1,-mescopy()\ht)
Line(mescopy()\px ,#height - mescopy()\py - mescopy()\ht ,mescopy()\lg , 1)
StopDrawing()
EndIf
EndIf
Next
Until Event = #PB_Event_CloseWindow
End