Un simili autocad trés léger

Vous débutez et vous avez besoin d'aide ? N'hésitez pas à poser vos questions
Torp
Messages : 360
Inscription : lun. 22/nov./2004 13:05

Un simili autocad trés léger

Message par Torp »

Salut,

Je désirerais faire pour mon boulot un petite application de calculs de plomberie (bah oui :)), mais je voudrais pour cela pouvoir faire un mode saisie graphique style « Autocad » (en très light bien sur et seulement en 2D). A savoir : une zone graphique où l’on dessiner des lignes, des cercles,… pouvoir les déplacer, les effacer, les tourner etc… jusque la rien de bien compliqué, je pense pouvoir y arriver (hum hum…), mais là ou j’ai vraiment du mal c’est pour implanter un zoom (pas de perspective), un pan (défilements sur la zone de travail).

Voili voilou, si quelqu’un c’est déjà penché sur la question et a un bout de code, c’est volontiers

Merci
A+
Patrick88
Messages : 1564
Inscription : mer. 21/janv./2004 18:24

Message par Patrick88 »

en purebasic 3.9x , il n'y a pas de zoom ni de pan

Code : Tout sélectionner

;{ Nom de l'application = PureCAD - patrick.claude@free.fr
; description = Petit logiciel de Dessin vectoriel
; date création = 6 / 12 / 04 (minicad)

; date modification = 10 / 12 / 04 - r10.2012-16

;   stockage des préférences dans un fichier "PureCAD.ini" dans le dossier de l'application
;   suppression de la table des sommets
;                 
; date modification = 30 / 12 / 04 - r10.3012-14

;   traitement selection entité par un case #ENT_SEL et non plus par défaut
;   correction des problèmes de décalage de table lors des suppressions et ajouts 
;   correction des problèmes de selection de lignes = passage des variables en nombre réels
;   correction des problèmes de selection des lignes horizontales et verticales

;   dessin des cercles 
;     implémenté      = regen , enregistrement cvs
;     pas implémentée = effacement , enregistrement scr , selection , calcul
;}
;-

;{ déclaration constantes
;- CONSTANTES -> EVENEMENTS WINDOWS
#MOUSE_MOVE = 512
#TERMINER_APPLICATION = 2
#TOUCHE_ECHAP_APPUYEE = 9999

;- constantes type fichier
#CVS_FILE = 0
#SCR_FILE = 1
#DXF_FILE = 2
#JPG_FILE = 3
#ALL_FILE = 4

;- constantes entitées
Enumeration 10 Step 10
  #ENT_SEL
  #ENT_DEL
  #ENT_LINE
  #ENT_CIRCLE
EndEnumeration

;- CONSTANTES -> MENU
Enumeration
  #MNU_MAIN
  ; menu fichier
  #MNU_MAIN_OUVRIR
  #MNU_MAIN_ENREGISTRER
  #MNU_MAIN_ENREGISTRER_SOUS
  #MNU_MAIN_QUIT 
  ; menu dessiner 
  #MNU_MAIN_LIGNE
  #MNU_MAIN_CERCLE
  ; menu modifier
  #MNU_MAIN_PROPRIETE
  #MNU_MAIN_SELECTIONNER
  #MNU_MAIN_EFFACER
EndEnumeration
;- CONSTANTES -> FENETRES ET GADGETS
Enumeration
  #WIN_MAIN
    #GDT_STB_MAIN
    #IMAGE_ECRAN
  
  #WIN_PROP
    #GDT_LST_PROP
EndEnumeration
;}
;{ déclaration structures
Structure STRU_INFO
  WIN_XMIN.w
  WIN_YMIN.w
  WIN_WIDTH.w
  WIN_HEIGHT.w
  WIN_OPTION.l
  WIN_TITLE$
  DRW_GAPX.w : DRW_GAPY.w : DRW_X.w : DRW_Y.w : DRW_WIDTH.w : DRW_HEIGHT.w
  PROP_SHOW.b:PROP_X.w:PROP_Y.w:PROP_WIDTH.w:PROP_HEIGHT.w
  
  COUL_FOND.l
  COUL_CURSEUR.l
  HWND_WIN_MAIN.l
  
  SELECTION.b
  POIGNEE.b
  
  fichier_dessin.s
  type_fichier.b
  
  DEFAULT_FILE$
  PATTERN$
  PATTERN_POSITION.b
EndStructure
Structure STRU_ENT_LINE
  No.l : maintien.s
  X1.f : y1.f : x2.f : y2.f : long.f
  tan_angle.f : ang_rad.f : ang_deg.f : dist_ord.f
  
  coul.l
EndStructure
Structure STRU_ENT_CIRCLE
  No.l : maintien.s
  X1.f : y1.f : Rayon.f : long.f
  tan_angle.f : ang_rad.f : ang_deg.f : dist_ord.f
  flag_remplissage.b : Coul_Remplissage.l
  coul.l
EndStructure
;}
;{ déclaration variables
Global quit.b ,version.s
Global INFO.STRU_INFO
Global sommet_courant.l, sommet_selection.l
Global num_entite.l, entite_selection.s, compteur_entite.l

Dim Sommet.w(3) ; contient le dernier Sommet selectionné + celui en cours

NewList ENT_LINE.STRU_ENT_LINE()
NewList ENT_CIRCLE.STRU_ENT_CIRCLE()

;}
;{ déclaration procedures
Procedure FichierPreference()
  version = "r10."+RSet(Str(Day(Date())),2,"0")+RSet(Str(Month(Date())),2,"0")+RSet(Str(Hour(Date())),2,"0")
  If OpenPreferences("PureCAD.ini") <> 0
    PreferenceGroup("WINDOW")
    INFO\WIN_XMIN = ReadPreferenceLong("XMIN",0)
    INFO\WIN_YMIN = ReadPreferenceLong("YMIN",0)
    INFO\WIN_WIDTH = ReadPreferenceLong("WIDTH",400)
    INFO\WIN_HEIGHT = ReadPreferenceLong("HEIGHT",400)
    INFO\WIN_OPTION = ReadPreferenceLong("OPTION",#PB_Window_ScreenCentered | #PB_Window_SystemMenu)
    INFO\WIN_TITLE$ = ReadPreferenceString("TITLE","PureCAD "+version)
    
    PreferenceGroup("DRAWING")
    INFO\DRW_X = ReadPreferenceLong("X_MIN",0) 
    INFO\DRW_Y = ReadPreferenceLong("Y_MIN",0)
    INFO\DRW_WIDTH = ReadPreferenceLong("WIDTH",INFO\WIN_WIDTH)
    INFO\DRW_HEIGHT = ReadPreferenceLong("HEIGHT",INFO\WIN_HEIGHT-40)
    
    INFO\COUL_FOND = ReadPreferenceLong("COUL_FOND",RGB(255,255,255))
    INFO\COUL_CURSEUR = ReadPreferenceLong("COUL_CURSEUR",RGB(0,0,0))
    
    PreferenceGroup("INPUT_OUTPUT")
    INFO\DEFAULT_FILE$ = ReadPreferenceString("DEFAULT_FILE","sans_nom.cvs")
    INFO\PATTERN$ = "ASCII délimité (*.cvs)|*.cvs|"
    INFO\PATTERN$ + "Script (*.scr)|*.scr|" 
    INFO\PATTERN$ + "DXF (*.dxf)|*.dxf|"
    INFO\PATTERN$ + "Jpeg (*.jpg)|*.jpg|" 
    INFO\PATTERN$ + "All files (*.*)|*.*"
    INFO\PATTERN$ = ReadPreferenceString("PATTERN",INFO\PATTERN$)
    INFO\PATTERN_POSITION = ReadPreferenceLong("PATTERN_POSITION",0)
    
    PreferenceGroup("PROPERTIES")
    INFO\PROP_SHOW = ReadPreferenceLong("PROP_SHOW",0)
    INFO\PROP_X = ReadPreferenceLong("X_MIN",INFO\WIN_XMIN)
    INFO\PROP_Y = ReadPreferenceLong("Y_MIN",INFO\WIN_YMIN+25)
    INFO\PROP_WIDTH = ReadPreferenceLong("WIDTH",150)
    INFO\PROP_HEIGHT = ReadPreferenceLong("HEIGHT",INFO\WIN_HEIGHT)
    
    PreferenceGroup("ACCROCH_OBJ")
    INFO\SELECTION = ReadPreferenceLong("SELECTION",5)
    INFO\POIGNEE = ReadPreferenceLong("POIGNEE",10)
    
    ClosePreferences()
  Else
    CreatePreferences("PureCAD.ini")
    PreferenceGroup("WINDOW")
    INFO\WIN_XMIN = 0
    INFO\WIN_YMIN = 0
    INFO\WIN_WIDTH = 400
    INFO\WIN_HEIGHT = 400
    INFO\WIN_OPTION = #PB_Window_ScreenCentered | #PB_Window_SystemMenu
    INFO\WIN_TITLE$ = "PureCAD "+version
    WritePreferenceLong("XMIN",INFO\WIN_XMIN)
    WritePreferenceLong("YMIN",INFO\WIN_YMIN)
    WritePreferenceLong("WIDTH",INFO\WIN_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\WIN_HEIGHT)
    WritePreferenceLong("OPTION",INFO\WIN_OPTION)
    WritePreferenceString("TITLE",INFO\WIN_TITLE$)
    
    PreferenceGroup("DRAWING")
    INFO\DRW_X = 0 : INFO\DRW_Y = 0
    INFO\DRW_WIDTH = INFO\WIN_WIDTH
    INFO\DRW_HEIGHT = INFO\WIN_HEIGHT-40
    WritePreferenceLong("X_MIN",INFO\DRW_X)
    WritePreferenceLong("Y_MIN",INFO\DRW_Y)
    WritePreferenceLong("WIDTH",INFO\DRW_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\DRW_HEIGHT)
    
    INFO\COUL_FOND = RGB(255,255,255)
    INFO\COUL_CURSEUR = RGB(0,0,0)
    WritePreferenceLong("COUL_FOND",INFO\COUL_FOND)
    WritePreferenceLong("COUL_CURSEUR",INFO\COUL_CURSEUR)
    
    PreferenceGroup("INPUT_OUTPUT")
    INFO\DEFAULT_FILE$ = "sans_nom.cvs"              ; initial path + file 
    INFO\PATTERN$ = "ASCII délimité (*.cvs)|*.cvs|"  ; set first pattern  (index = 0) 
    INFO\PATTERN$ + "Script (*.scr)|*.scr|"          ; set second pattern (index = 1) 
    INFO\PATTERN$ + "DXF (*.dxf)|*.dxf|"             ; set third pattern  (index = 2) 
    INFO\PATTERN$ + "Jpeg (*.jpg)|*.jpg|"            ; set fourth pattern (index = 3) 
    INFO\PATTERN$ + "All files (*.*)|*.*"            ; set fifth pattern  (index = 4) 
    INFO\PATTERN_POSITION = 0  
    WritePreferenceString("DEFAULT_FILE",INFO\DEFAULT_FILE$)
    WritePreferenceString("PATTERN",INFO\PATTERN$)
    WritePreferenceLong("PATTERN_POSITION", INFO\PATTERN_POSITION)
    
    PreferenceGroup("PROPERTIES")
    INFO\PROP_SHOW = 0
    INFO\PROP_X = INFO\WIN_XMIN
    INFO\PROP_Y = INFO\WIN_YMIN+25
    INFO\PROP_WIDTH = 150
    INFO\PROP_HEIGHT = INFO\WIN_HEIGHT
    WritePreferenceLong("PROP_SHOW",INFO\PROP_SHOW)
    WritePreferenceLong("X_MIN",INFO\PROP_X)
    WritePreferenceLong("Y_MIN",INFO\PROP_Y)
    WritePreferenceLong("WIDTH",INFO\PROP_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\PROP_HEIGHT)
    
    PreferenceGroup("ACCROCH_OBJ")
    INFO\SELECTION = 5
    INFO\POIGNEE = 10
    WritePreferenceLong("SELECTION",INFO\SELECTION)
    WritePreferenceLong("POIGNEE",INFO\POIGNEE)
    
    ClosePreferences()
  EndIf
EndProcedure
  
Procedure Initialisation()
  FichierPreference()

  quit = 0
  sommet_courant = -1 
  num_entite =0 : compteur_entite = 0
EndProcedure

;{ gestion des fenêtres
Procedure WindowCallback(WindowID, Message, lParam, wParam)
  If Message = #WM_PAINT
    StartDrawing(WindowOutput())
    DrawImage(UseImage(#IMAGE_ECRAN), 0, 0)
    StopDrawing()
  EndIf
  
  ProcedureReturn #PB_ProcessPureBasicEvents
EndProcedure
Procedure FondEcran()
  If IsImage(#IMAGE_ECRAN)<>0
    FreeImage(#IMAGE_ECRAN)
  EndIf
  If CreateImage(#IMAGE_ECRAN, INFO\DRW_WIDTH, INFO\DRW_HEIGHT)
    StartDrawing(ImageOutput())
      Box(0,0,INFO\DRW_WIDTH,INFO\DRW_HEIGHT,INFO\COUL_FOND)
      DrawingMode(4)
      Box(0,0,INFO\DRW_WIDTH,INFO\DRW_HEIGHT,RGB(0,0,0))
      DrawingMode(0)
      ForEach ENT_LINE()
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1,ENT_LINE()\x2,ENT_LINE()\y2,ENT_LINE()\coul)
      Next
      DrawingMode(4)
      ForEach ENT_CIRCLE()
        Circle(ENT_CIRCLE()\X1,ENT_CIRCLE()\y1,ENT_CIRCLE()\Rayon,ENT_CIRCLE()\coul)
      Next
    StopDrawing() 
  EndIf

EndProcedure
Procedure FlipBuffer()
  StartDrawing(WindowOutput())
  DrawImage(UseImage(#IMAGE_ECRAN), INFO\DRW_X, INFO\DRW_Y)
  StopDrawing()
EndProcedure
Procedure PopupWin_Prop()
 
  INFO\PROP_X = INFO\WIN_XMIN:INFO\PROP_Y = INFO\WIN_YMIN+25:INFO\PROP_WIDTH = 150:INFO\PROP_HEIGHT = INFO\WIN_HEIGHT
   
  If OpenWindow(#WIN_PROP,INFO\PROP_X,INFO\PROP_Y,INFO\PROP_WIDTH,INFO\PROP_HEIGHT/1.5,#PB_Window_SystemMenu|#PB_Window_SizeGadget,"Propriétés...")
    If CreateGadgetList(WindowID(#WIN_PROP))
      ListIconGadget(#GDT_LST_PROP,0,0,INFO\PROP_WIDTH,INFO\PROP_HEIGHT,"Libéllé",75,#PB_ListIcon_GridLines )
      AddGadgetColumn(#GDT_LST_PROP,1,"Valeur",70)
    EndIf
  EndIf
  
  UseWindow(#WIN_MAIN)
EndProcedure
Procedure refreshWin_prop(type_entite.b,no_ent.w)
  
    Select type_entite
      Case #ENT_LINE
        SelectElement(ENT_LINE(),no_ent)
        If INFO\PROP_SHOW = 1
          ClearGadgetItemList(#GDT_LST_PROP)
          AddGadgetItem(#GDT_LST_PROP,-1,"ID Entité"+Chr(10)+Str(ENT_LINE()\No))
          AddGadgetItem(#GDT_LST_PROP,-1,"Entité"+Chr(10)+"LIGNE")
          AddGadgetItem(#GDT_LST_PROP,-1,"Départ X"+Chr(10)+Str(ENT_LINE()\X1))
          AddGadgetItem(#GDT_LST_PROP,-1,"Départ Y"+Chr(10)+Str(ENT_LINE()\y1))
          AddGadgetItem(#GDT_LST_PROP,-1,"Extrémité X"+Chr(10)+Str(ENT_LINE()\x2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Extrémité Y"+Chr(10)+Str(ENT_LINE()\y2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Longueur"+Chr(10)+StrF(ENT_LINE()\long,2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Angle degré"+Chr(10)+StrF(ENT_LINE()\ang_deg))
          AddGadgetItem(#GDT_LST_PROP,-1,"Angle radian"+Chr(10)+StrF(ENT_LINE()\ang_rad))
          AddGadgetItem(#GDT_LST_PROP,-1,"tangente angle"+Chr(10)+StrF(ENT_LINE()\tan_angle))
          AddGadgetItem(#GDT_LST_PROP,-1,"dist. a ordonné"+Chr(10)+StrF(ENT_LINE()\dist_ord))
        EndIf
        StartDrawing(WindowOutput())
        DrawingMode(4)
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1-1,ENT_LINE()\x2,ENT_LINE()\y2-1,RGB(0,255,0))
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1,ENT_LINE()\x2,ENT_LINE()\y2,RGB(0,255,0))
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1+1,ENT_LINE()\x2,ENT_LINE()\y2+1,RGB(0,255,0))
        Box(ENT_LINE()\X1-INFO\POIGNEE/2,ENT_LINE()\y1-INFO\POIGNEE/2,INFO\POIGNEE,INFO\POIGNEE,RGB(0,0,255))
        Box(ENT_LINE()\x2-INFO\POIGNEE/2,ENT_LINE()\y2-INFO\POIGNEE/2,INFO\POIGNEE,INFO\POIGNEE,RGB(0,0,255))
        DrawingMode(0)
        StopDrawing()

    EndSelect
EndProcedure
;}
;{ calculs divers

Procedure.l Distance(x.l,y.l) ;; desactivé
  ; Sommet.l = -1
  ; ForEach Sommet()
    ; Distance.l = Sqr(Pow(x-Sommet()\x,2)+Pow(y-Sommet()\y,2))
    ; ; INFO\SELECTION * 2 pour une sélection plus aisée d'un sommet
    ; If Distance <= INFO\SELECTION * 2
      ; Sommet = Sommet()\No
      ; Break
    ; EndIf 
  ; Next
  ; 
  ; ProcedureReturn Sommet
EndProcedure
Procedure calcul(type_entite.b,no_ent.w)
  Select type_entite
    Case #ENT_LINE
      SelectElement(ENT_LINE(),no_ent)
      ; calcul de la longueur hypothénuse = racine carré de (x1-x2)²+(y1-y2)²
      cx1 = ENT_LINE()\X1 : cy1 = ENT_LINE()\y1 : cx2 = ENT_LINE()\x2 : cy2 = ENT_LINE()\y2
      ; If cx1>cx2 : tmp=cx1 : cx1 = cx2 : cx2 = cx1 : EndIf
      ; If cy1>cy2 : tmp=cy1 : cy1 = cy2 : cy2 = cy1 : EndIf
      ENT_LINE()\long = Sqr(Pow((cx2-cx1),2)+Pow((cy2-cy1),2))
      If cx1=cx2 ; si la droite est parfaitement verticale
        ENT_LINE()\tan_angle = 9999
        ENT_LINE()\ang_rad = 1.5707963
        ENT_LINE()\ang_deg = 90
        ENT_LINE()\dist_ord = cx1
      Else
        If cy1=cy2 ; la droite est parfaitement horizontale
          ENT_LINE()\tan_angle = 0
          ENT_LINE()\ang_rad = 0
          ENT_LINE()\ang_deg = 0
          If cx1 < cx2 
            ENT_LINE()\dist_ord = cx1
          Else
            ENT_LINE()\dist_ord = cx2
          EndIf
        Else
          ENT_LINE()\tan_angle = (cy2-cy1)/(cx2-cx1)
          ENT_LINE()\ang_rad = ATan(ENT_LINE()\tan_angle)
          ENT_LINE()\ang_deg = ENT_LINE()\ang_rad * 57.2957795 ; = 180/PI
          ENT_LINE()\dist_ord = cy1-ENT_LINE()\tan_angle*cx1 ; = b de y = ax+b
        EndIf
      EndIf
  EndSelect 
  LastElement(ENT_LINE())
EndProcedure
Procedure Entite_supprime(type_entite.b,no_ent.w)
  Select type_entite
    Case #ENT_LINE
      SelectElement(ENT_LINE(),no_ent)
      DeleteElement(ENT_LINE(),1)
      ; mettre à jour le numéro d'entité  !!! différent du compteur d'entité = <compteur_entite>
  EndSelect
  
  
  StatusBarText(#GDT_STB_MAIN, 2, "Regen..."):num_entite=-1
  ;; pour chaque type d'entité faire :
  ForEach ENT_LINE()
    num_entite+1
    ENT_LINE()\No = num_entite ; met à jour le numéro d'entité
    ENT_LINE()\maintien = RSet(Str(#ENT_LINE),4,"0")+RSet(Str(num_entite),8,"0") ; met à jour le maintien
  Next
  compteur_entite = num_entite+1
  
  StatusBarText(#GDT_STB_MAIN, 2, "")
  FondEcran()
  FlipBuffer()
EndProcedure
Procedure SelectionEntite()
  entite_selection = "-1"
  point_x = WindowMouseX() : point_y = WindowMouseY()
  
  ; OpenWindow(100,0,0,300,300,0,"")
  ; If CreateGadgetList(WindowID(100))
    ; ListViewGadget(101,0,0,300,300)
  ; EndIf
  ; If CountGadgetItems(101)>0
    ; ClearGadgetItemList(101)
  ; EndIf
  
  ForEach ENT_LINE()
    ; teste si le point est sur la ligne ou proche
    ; 1) calcul de la droite perpendiculaire  à S1 qui passe par Px Py		
    
    ;; il s'agit d'une droite verticale
    If ENT_LINE()\tan_angle = 9999
      tan_angle.f = 0
      dist_ord.f = point_x
      ; 2) intersection de ENT_LINE() avec 1)				
      point_x1.f = ENT_LINE()\X1
      point_y1.f = point_y
    Else  
      ;; il s'agit d'une droite horizontale
      If ENT_LINE()\tan_angle = 0
        tan_angle.f = 9999
        dist_ord.f = point_x
        ; 2) intersection de ENT_LINE() avec 1)				
        point_x1.f = point_x
        point_y1.f = ENT_LINE()\y1
      Else
        ;; sinon il s'agit d'une droite oblique quelconque
        tan_angle.f	= -1/ENT_LINE()\tan_angle
        dist_ord.f	= point_y - tan_angle * point_x
        ; 2) intersection de ENT_LINE() avec 1)				
        point_x1.f	= ( dist_ord - ENT_LINE()\dist_ord ) / ( ENT_LINE()\tan_angle - tan_angle )
        point_y1.f	= ENT_LINE()\tan_angle * point_x1 + ENT_LINE()\dist_ord
      EndIf
    EndIf
    
    ; 3) calcul de la Distance de point_x,point_y à point_x1,point_y1
    long_per.f	= Sqr(Pow((point_x-point_x1),2)+Pow((point_y-point_y1),2))

    If long_per <= INFO\SELECTION
      ; 4) calcul de la Distance de ENT_LINE()\X1,y1 à ppx,ppy				
      long_1.f	= Sqr(Pow((ENT_LINE()\X1-point_x1),2)+Pow((ENT_LINE()\y1-point_y1),2))
      
      ; 5) calcul de la Distance de ENT_LINE()\x2,y2 à ppx,ppy  				
      long_2.f	= Sqr(Pow((ENT_LINE()\x2-point_x1),2)+Pow((ENT_LINE()\y2-point_y1),2))
      
      long_result.f	= long_1 + long_2
      ; AddGadgetItem(101,-1,"point_x "+StrF(point_x))
      ; AddGadgetItem(101,-1,"point_y"+StrF(point_y))
      ; AddGadgetItem(101,-1,"lg du segment "+StrF(long_per)+" long selection"+Str(INFO\SELECTION))
      ; AddGadgetItem(101,-1,"tan_angle "+StrF(tan_angle))
      ; AddGadgetItem(101,-1,"dist_ord "+StrF(dist_ord))
      ; AddGadgetItem(101,-1,"point_x1 "+StrF(point_x1))
      ; AddGadgetItem(101,-1,"point_y1"+StrF(point_y1))
      ; AddGadgetItem(101,-1,"long1 "+StrF(long_1))
      ; AddGadgetItem(101,-1,"long2 "+StrF(long_2))
      ; AddGadgetItem(101,-1,"long_result "+StrF(long_result))
      ; AddGadgetItem(101,-1,"ENT_LINE()\long"+StrF(ENT_LINE()\long))
      ; AddGadgetItem(101,-1,"long_result < ENT_LINE()\long ")

      If Int(long_result) <= ENT_LINE()\long + INFO\SELECTION
        entite_selection = ENT_LINE()\maintien 
        UseWindow(#WIN_MAIN)
        Break
      EndIf  
    EndIf
  Next
  UseWindow(#WIN_MAIN)
EndProcedure
;}
;{ opération sur les fichiers
Procedure Fichier_sauvegarder(type.b)
  ; INFO\type_fichier contient le numéro du filtre ou patern choisi
  Select type
    Case #CVS_FILE
      If CreateFile(0,INFO\fichier_dessin)
        ForEach ENT_LINE()
          chaine.s = "LINE;"+Str(ENT_LINE()\No)+";"
          chaine = chaine + Str(ENT_LINE()\X1)+";"+Str(ENT_LINE()\y1)+";"
          chaine = chaine + Str(ENT_LINE()\x2)+";"+Str(ENT_LINE()\y2)+";"
          chaine = chaine + Str(ENT_LINE()\long)+";"
          chaine = chaine + StrF(ENT_LINE()\tan_angle,6)+";"
          chaine = chaine + StrF(ENT_LINE()\ang_deg,6)+";"
          chaine = chaine + StrF(ENT_LINE()\ang_rad,6)+";"
          chaine = chaine + StrF(ENT_LINE()\dist_ord,6)
          WriteStringN(chaine)
        Next
        ForEach ENT_CIRCLE()
          chaine.s = "CIRCLE;"+Str(ENT_CIRCLE()\No)+";"
          chaine = chaine + Str(ENT_CIRCLE()\X1)+";"+Str(ENT_CIRCLE()\y1)+";"
          chaine = chaine + Str(ENT_CIRCLE()\Rayon) ;+";"
          ; chaine = chaine + Str(ENT_LINE()\long)+";"
          ; chaine = chaine + StrF(ENT_LINE()\tan_angle,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\ang_deg,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\ang_rad,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\dist_ord,6)
          WriteStringN(chaine)
        Next
        
        ; WriteStringN("")
        ; ForEach Sommet()
          ; chaine.s = "SOMMET;"+Str(Sommet()\No)+";"+Str(Sommet()\x)+";"+Str(Sommet()\y)
          ; WriteStringN(chaine)
        ; Next
        CloseFile(0)
      EndIf
    Case #SCR_FILE
      If CreateFile(0,INFO\fichier_dessin)
        ForEach ENT_LINE()
          chaine.s = "LIGNE" : WriteStringN(chaine)
          chaine = Str(ENT_LINE()\X1)+","+Str(ENT_LINE()\y1) : WriteStringN(chaine)
          chaine = Str(ENT_LINE()\x2)+","+Str(ENT_LINE()\y2) : WriteStringN(chaine)
          WriteStringN("")
        Next
        
        CloseFile(0)
      EndIf
  EndSelect
  
EndProcedure
;}
;{ dessin des entités
Procedure DessineLigne()
  LastElement(ENT_LINE());; replace le pointeur à la fin de la liste
  
  AddElement(ENT_LINE())
  num_entite = compteur_entite
  ENT_LINE()\No = num_entite
  ENT_LINE()\maintien = RSet(Str(#ENT_LINE),4,"0")+RSet(Str(num_entite),8,"0")
  If sommet_selection = -1
    ; aucun sommet n'est selectionné, on commence une nouvelle ligne
    Sommet(0) = WindowMouseX() : Sommet(1) = WindowMouseY() 
    ; premier point de la ligne
    ENT_LINE()\X1 = Sommet(0) : ENT_LINE()\y1 = Sommet(1) 
    sommet_courant = 0
  Else
    ; au contraire, si un Sommet est selectionné
    ENT_LINE()\X1 = Sommet(2) : ENT_LINE()\y1 = Sommet(2)
    sommet_courant = 2
  EndIf
  
  StatusBarText(#GDT_STB_MAIN, 2, "Ligne, 2ème point...")
  Repeat
    event = WaitWindowEvent()
    If event = #WM_MOUSEMOVE
      FlipBuffer()
      StartDrawing(WindowOutput())
      LineXY(ENT_LINE()\X1,ENT_LINE()\y1,WindowMouseX(),WindowMouseY(),RGB(255,0,0))
      StopDrawing()
    EndIf
  Until event=#WM_LBUTTONUP
  Sommet(2) = WindowMouseX() : Sommet(3) = WindowMouseY()
  ENT_LINE()\x2 = Sommet(2) :ENT_LINE()\y2 = Sommet(3)
  calcul(#ENT_LINE,ENT_LINE()\No)
  refreshWin_prop(#ENT_LINE,ENT_LINE()\No)
  compteur_entite +1
  StatusBarText(#GDT_STB_MAIN, 2, "")
EndProcedure
Procedure DessineCercle()
  LastElement(ENT_CIRCLE());; replace le pointeur à la fin de la liste
  
  AddElement(ENT_CIRCLE())
  num_entite = compteur_entite
  ENT_CIRCLE()\No = num_entite
  ENT_CIRCLE()\maintien = RSet(Str(#ENT_CIRCLE),4,"0")+RSet(Str(num_entite),8,"0")
  If sommet_selection = -1
    ; aucun sommet n'est selectionné, on commence une nouvelle ligne
    Sommet(0) = WindowMouseX() : Sommet(1) = WindowMouseY() 
    ; premier point de la ligne
    ENT_CIRCLE()\X1 = Sommet(0) : ENT_CIRCLE()\y1 = Sommet(1) 
    sommet_courant = 0
  Else
    ; au contraire, si un Sommet est selectionné
    ENT_CIRCLE()\X1 = Sommet(2) : ENT_CIRCLE()\y1 = Sommet(2)
    sommet_courant = 2
  EndIf
  
  StatusBarText(#GDT_STB_MAIN, 2, "Cercle, Rayon...")
  Repeat
    event = WaitWindowEvent()
    If event = #WM_MOUSEMOVE
      FlipBuffer()
      StartDrawing(WindowOutput())
      DrawingMode(4)
      Rayon = ENT_CIRCLE()\X1-WindowMouseX()
      Circle(ENT_CIRCLE()\X1,ENT_CIRCLE()\y1,Rayon,RGB(255,0,0))
      StopDrawing()
    EndIf
  Until event=#WM_LBUTTONUP
  Sommet(2) = WindowMouseX() : Sommet(3) = WindowMouseY()
  ENT_CIRCLE()\Rayon = ENT_CIRCLE()\X1-Sommet(2) 
  calcul(#ENT_CIRCLE,ENT_CIRCLE()\No)
  refreshWin_prop(#ENT_CIRCLE,ENT_CIRCLE()\No)
  compteur_entite +1
  StatusBarText(#GDT_STB_MAIN, 2, "")
EndProcedure
;}

;}
;{ programme principal
Initialisation()

If OpenWindow(#WIN_MAIN, INFO\WIN_XMIN, INFO\WIN_YMIN, INFO\WIN_WIDTH, INFO\WIN_HEIGHT, INFO\WIN_OPTION, INFO\WIN_TITLE$)
  INFO\WIN_XMIN = WindowX()
  INFO\WIN_YMIN = WindowY()
  ;{ définitions menu
  If CreateMenu(#MNU_MAIN,WindowID(#WIN_MAIN))
    MenuTitle("Fichier")
    MenuItem(#MNU_MAIN_OUVRIR,"Ouvrir...")
    MenuBar()
    MenuItem(#MNU_MAIN_ENREGISTRER_SOUS,"Enregistrer sous...")
    MenuBar()
    MenuItem(#MNU_MAIN_QUIT,"Quitter"+Chr(9)+"ALT+F4")
    ;MenuTitle("Edition")
    ;MenuTitle("Vue")
    ;MenuTitle("Insérer")
    ;MenuTitle("Format")
    ;MenuTitle("Outils")
    MenuTitle("Dessin")
    MenuItem(#MNU_MAIN_LIGNE,"Ligne")
    MenuItem(#MNU_MAIN_CERCLE,"Cercle")
    ;MenuTitle("Cotation")
    MenuTitle("Modifier")
    MenuItem(#MNU_MAIN_PROPRIETE,"Propriétés")
    MenuBar()
    MenuItem(#MNU_MAIN_SELECTIONNER,"Selectionner")
    MenuItem(#MNU_MAIN_EFFACER,"Effacer")
    
  EndIf
  ;}
  ;{ définitions gadgets
  ; If CreateGadgetList(WindowID(#WIN_MAIN))
    ; 
  ; EndIf
  If CreateStatusBar(#GDT_STB_MAIN,WindowID(#WIN_MAIN))
    AddStatusBarField(50)
    AddStatusBarField(50)
    AddStatusBarField(200)
  EndIf
  ;}
  
  INFO\HWND_WIN_MAIN = WindowID(#WIN_MAIN)
  AddKeyboardShortcut(#WIN_MAIN, #PB_Shortcut_Escape, #TOUCHE_ECHAP_APPUYEE) ; qui generera un evenement de valeur 15. 
  
  FondEcran()
  
  SetWindowCallback(@WindowCallback())
  quit.b = 0
  Repeat
    event = WaitWindowEvent()
    
    ;FlipBuffer()
    mx = WindowMouseX() : my = WindowMouseY()
    
    StatusBarText(#GDT_STB_MAIN, 0, "X:"+Str(mx)) 
    StatusBarText(#GDT_STB_MAIN, 1, "Y:"+Str(my)) 
    
    Select event
      ;{ traitement evénement gadgets
      Case #PB_Event_Gadget
        Select EventGadgetID()
          
        EndSelect ;}
        ;{ traitement évenement menu + pop-up menu
      Case #PB_Event_Menu
        Select EventMenuID() 
          Case #TOUCHE_ECHAP_APPUYEE
            DRAW_ENT = -1
            
          ;{ traitement menu fichier
          Case #MNU_MAIN_OUVRIR
            
          Case #MNU_MAIN_ENREGISTRER_SOUS
            
            INFO\fichier_dessin = SaveFileRequester("Enregistrer le dessin sous ...",INFO\DEFAULT_FILE$,INFO\PATTERN$,INFO\PATTERN_POSITION)
            INFO\type_fichier = SelectedFilePattern()
            
            Select INFO\type_fichier
              Case #CVS_FILE ;= 0
                If UCase(Right(INFO\fichier_dessin,4))<>".CVS"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".CVS"
                EndIf
                Fichier_sauvegarder(#CVS_FILE)
                
              Case #SCR_FILE ;= 1
                If UCase(Right(INFO\fichier_dessin,4))<>".SCR"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".SCR"
                EndIf
                Fichier_sauvegarder(#SCR_FILE)
                
              Case #DXF_FILE ;= 2
                If UCase(Right(INFO\fichier_dessin,4))<>".DXF"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".DXF"
                EndIf
                Fichier_sauvegarder(#DXF_FILE)
                
              Case #JPG_FILE ;= 3
                If UCase(Right(INFO\fichier_dessin,4))<>".JPG"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".JPG"
                EndIf
                Fichier_sauvegarder(#JPG_FILE)
                
              Case #ALL_FILE ;= 4
                
            EndSelect
            StatusBarText(#GDT_STB_MAIN, 2, "...."+Right(INFO\fichier_dessin,30)) 
            
            
          Case #MNU_MAIN_QUIT
            quit = #TERMINER_APPLICATION
          ;}
          ;{ traitement menu dessin  
          Case #MNU_MAIN_LIGNE
            DRAW_ENT = #ENT_LINE
            StatusBarText(#GDT_STB_MAIN, 2, "Ligne, 1er point...")
          Case #MNU_MAIN_CERCLE
            DRAW_ENT = #ENT_CIRCLE
            StatusBarText(#GDT_STB_MAIN, 2, "Cercle, Centre...")
            ;}
          ;{ traitement menu modifier
          Case #MNU_MAIN_PROPRIETE
            If GetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE)=0
              SetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE,1)
              PopupWin_Prop() 
              INFO\PROP_SHOW=1
            Else
              SetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE,0)
              CloseWindow(#WIN_PROP)
              INFO\PROP_SHOW=0
            EndIf
            
          Case #MNU_MAIN_SELECTIONNER
            DRAW_ENT = #ENT_SEL
            StatusBarText(#GDT_STB_MAIN, 2, "Selectionner une entitée...")
            
          Case #MNU_MAIN_EFFACER
            DRAW_ENT = #ENT_DEL
            StatusBarText(#GDT_STB_MAIN, 2, "Supprimer une entitée...")
            ;}
            
        EndSelect ;}
        ;{ traitement autres évenements
      Case #PB_Event_CloseWindow
        quit = #TERMINER_APPLICATION
      
      Case #WM_CHAR
        Debug wParam
        Debug lParam
        
      Case #MOUSE_MOVE
        sommet_selection = -1

      Case #WM_LBUTTONUP
        Select DRAW_ENT
          ;{ dessiner 
          Case #ENT_LINE
            DessineLigne()
            FondEcran()
            
          Case #ENT_CIRCLE
            DessineCercle()
            FondEcran()
         ;}
          ;{ supprimer une entitée
          Case #ENT_DEL
            ; si on clique sur une entité, affiche ses caractéristique dans la fenêtre propriété
            FlipBuffer()
            StatusBarText(#GDT_STB_MAIN, 2, "Cliquer sur l'entité à supprimer...")
            SelectionEntite()  ; + met a jour entite_selection = renvoie n° entite
            If Left(entite_selection,1)<>"R"
              code_entite = Val(Left(entite_selection,4))
              num_entite = Val(Right(entite_selection,8))
              Entite_supprime(code_entite,num_entite)
            EndIf
          ;}
          ;{ selectionner une entitée
          Case #ENT_SEL
            ; si on clique sur une entité, affiche ses caractéristique dans la fenêtre propriété
            ;sommet_selection = -1 : entite_selection = ""
            FlipBuffer()
            SelectionEntite()  ; + met a jour entite_selection = renvoie n° entite
            If Left(entite_selection,1)<>"R"
              code_entite = Val(Left(entite_selection,4))
              num_entite = Val(Right(entite_selection,8))
              refreshWin_prop(code_entite,num_entite)
            EndIf
            ;}
            
        EndSelect
        ;}
    EndSelect
  Until quit>0
EndIf

DeleteFile("PureCAD.ini")
FichierPreference()

End
;}
[/img]
bernard13
Messages : 1221
Inscription : mer. 05/janv./2005 21:30

Message par bernard13 »

SALUT TORP

tu bosse dans quel secteur?
Torp
Messages : 360
Inscription : lun. 22/nov./2004 13:05

Message par Torp »

Patrick88 a écrit :en purebasic 3.9x , il n'y a pas de zoom ni de pan
Tant pis c'est déjà un bon début :wink:

A+
Torp
Messages : 360
Inscription : lun. 22/nov./2004 13:05

Message par Torp »

bernard13 a écrit :tu bosse dans quel secteur?
Bureau d'études Clim.
Avatar de l’utilisateur
Progi1984
Messages : 2659
Inscription : mar. 14/déc./2004 13:56
Localisation : France > Rennes
Contact :

Message par Progi1984 »

Code V4

Code : Tout sélectionner

;{ Nom de l'application = PureCAD - patrick.claude@free.fr
; description = Petit logiciel de Dessin vectoriel
; date création = 6 / 12 / 04 (minicad)

; date modification = 10 / 12 / 04 - r10.2012-16

;   stockage des préférences dans un fichier "PureCAD.ini" dans le dossier de l'application
;   suppression de la table des sommets
;                 
; date modification = 30 / 12 / 04 - r10.3012-14

;   traitement selection entité par un case #ENT_SEL et non plus par défaut
;   correction des problèmes de décalage de table lors des suppressions et ajouts
;   correction des problèmes de selection de lignes = passage des variables en nombre réels
;   correction des problèmes de selection des lignes horizontales et verticales

;   dessin des cercles
;     implémenté      = regen , enregistrement cvs
;     pas implémentée = effacement , enregistrement scr , selection , calcul
;}
;-

;{ déclaration constantes
;- CONSTANTES -> EVENEMENTS WINDOWS
#MOUSE_MOVE = 512
#TERMINER_APPLICATION = 2
#TOUCHE_ECHAP_APPUYEE = 9999

;- constantes type fichier
#CVS_FILE = 0
#SCR_FILE = 1
#DXF_FILE = 2
#JPG_FILE = 3
#ALL_FILE = 4

;- constantes entitées
Enumeration 10 Step 10
  #ENT_SEL
  #ENT_DEL
  #ENT_LINE
  #ENT_CIRCLE
EndEnumeration

;- CONSTANTES -> MENU
Enumeration
  #MNU_MAIN
  ; menu fichier
  #MNU_MAIN_OUVRIR
  #MNU_MAIN_ENREGISTRER
  #MNU_MAIN_ENREGISTRER_SOUS
  #MNU_MAIN_QUIT
  ; menu dessiner
  #MNU_MAIN_LIGNE
  #MNU_MAIN_CERCLE
  ; menu modifier
  #MNU_MAIN_PROPRIETE
  #MNU_MAIN_SELECTIONNER
  #MNU_MAIN_EFFACER
EndEnumeration
;- CONSTANTES -> FENETRES ET GADGETS
Enumeration
  #WIN_MAIN
    #GDT_STB_MAIN
    #IMAGE_ECRAN
 
  #WIN_PROP
    #GDT_LST_PROP
EndEnumeration
;}
;{ déclaration structures
Structure STRU_INFO
  WIN_XMIN.w
  WIN_YMIN.w
  WIN_WIDTH.w
  WIN_HEIGHT.w
  WIN_OPTION.l
  WIN_TITLE$
  DRW_GAPX.w : DRW_GAPY.w : DRW_X.w : DRW_Y.w : DRW_WIDTH.w : DRW_HEIGHT.w
  PROP_SHOW.b:PROP_X.w:PROP_Y.w:PROP_WIDTH.w:PROP_HEIGHT.w
 
  COUL_FOND.l
  COUL_CURSEUR.l
  HWND_WIN_MAIN.l
 
  SELECTION.b
  POIGNEE.b
 
  fichier_dessin.s
  type_fichier.b
 
  DEFAULT_FILE$
  PATTERN$
  PATTERN_POSITION.b
EndStructure
Structure STRU_ENT_LINE
  No.l : maintien.s
  X1.f : y1.f : x2.f : y2.f : long.f
  tan_angle.f : ang_rad.f : ang_deg.f : dist_ord.f
 
  coul.l
EndStructure
Structure STRU_ENT_CIRCLE
  No.l : maintien.s
  X1.f : y1.f : Rayon.f : long.f
  tan_angle.f : ang_rad.f : ang_deg.f : dist_ord.f
  flag_remplissage.b : Coul_Remplissage.l
  coul.l
EndStructure
;}
;{ déclaration variables
Global quit.b ,version.s
Global INFO.STRU_INFO
Global sommet_courant.l, sommet_selection.l
Global num_entite.l, entite_selection.s, compteur_entite.l

Global Dim Sommet.w(3) ; contient le dernier Sommet selectionné + celui en cours

Global NewList ENT_LINE.STRU_ENT_LINE()
Global NewList ENT_CIRCLE.STRU_ENT_CIRCLE()

;}
;{ déclaration procedures
Procedure FichierPreference()
  version = "r10."+RSet(Str(Day(Date())),2,"0")+RSet(Str(Month(Date())),2,"0")+RSet(Str(Hour(Date())),2,"0")
  If OpenPreferences("PureCAD.ini") <> 0
    PreferenceGroup("WINDOW")
    INFO\WIN_XMIN = ReadPreferenceLong("XMIN",0)
    INFO\WIN_YMIN = ReadPreferenceLong("YMIN",0)
    INFO\WIN_WIDTH = ReadPreferenceLong("WIDTH",400)
    INFO\WIN_HEIGHT = ReadPreferenceLong("HEIGHT",400)
    INFO\WIN_OPTION = ReadPreferenceLong("OPTION",#PB_Window_ScreenCentered | #PB_Window_SystemMenu)
    INFO\WIN_TITLE$ = ReadPreferenceString("TITLE","PureCAD "+version)
   
    PreferenceGroup("DRAWING")
    INFO\DRW_X = ReadPreferenceLong("X_MIN",0)
    INFO\DRW_Y = ReadPreferenceLong("Y_MIN",0)
    INFO\DRW_WIDTH = ReadPreferenceLong("WIDTH",INFO\WIN_WIDTH)
    INFO\DRW_HEIGHT = ReadPreferenceLong("HEIGHT",INFO\WIN_HEIGHT-40)
   
    INFO\COUL_FOND = ReadPreferenceLong("COUL_FOND",RGB(255,255,255))
    INFO\COUL_CURSEUR = ReadPreferenceLong("COUL_CURSEUR",RGB(0,0,0))
   
    PreferenceGroup("INPUT_OUTPUT")
    INFO\DEFAULT_FILE$ = ReadPreferenceString("DEFAULT_FILE","sans_nom.cvs")
    INFO\PATTERN$ = "ASCII délimité (*.cvs)|*.cvs|"
    INFO\PATTERN$ + "Script (*.scr)|*.scr|"
    INFO\PATTERN$ + "DXF (*.dxf)|*.dxf|"
    INFO\PATTERN$ + "Jpeg (*.jpg)|*.jpg|"
    INFO\PATTERN$ + "All files (*.*)|*.*"
    INFO\PATTERN$ = ReadPreferenceString("PATTERN",INFO\PATTERN$)
    INFO\PATTERN_POSITION = ReadPreferenceLong("PATTERN_POSITION",0)
   
    PreferenceGroup("PROPERTIES")
    INFO\PROP_SHOW = ReadPreferenceLong("PROP_SHOW",0)
    INFO\PROP_X = ReadPreferenceLong("X_MIN",INFO\WIN_XMIN)
    INFO\PROP_Y = ReadPreferenceLong("Y_MIN",INFO\WIN_YMIN+25)
    INFO\PROP_WIDTH = ReadPreferenceLong("WIDTH",150)
    INFO\PROP_HEIGHT = ReadPreferenceLong("HEIGHT",INFO\WIN_HEIGHT)
   
    PreferenceGroup("ACCROCH_OBJ")
    INFO\SELECTION = ReadPreferenceLong("SELECTION",5)
    INFO\POIGNEE = ReadPreferenceLong("POIGNEE",10)
   
    ClosePreferences()
  Else
    CreatePreferences("PureCAD.ini")
    PreferenceGroup("WINDOW")
    INFO\WIN_XMIN = 0
    INFO\WIN_YMIN = 0
    INFO\WIN_WIDTH = 400
    INFO\WIN_HEIGHT = 400
    INFO\WIN_OPTION = #PB_Window_ScreenCentered | #PB_Window_SystemMenu
    INFO\WIN_TITLE$ = "PureCAD "+version
    WritePreferenceLong("XMIN",INFO\WIN_XMIN)
    WritePreferenceLong("YMIN",INFO\WIN_YMIN)
    WritePreferenceLong("WIDTH",INFO\WIN_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\WIN_HEIGHT)
    WritePreferenceLong("OPTION",INFO\WIN_OPTION)
    WritePreferenceString("TITLE",INFO\WIN_TITLE$)
   
    PreferenceGroup("DRAWING")
    INFO\DRW_X = 0 : INFO\DRW_Y = 0
    INFO\DRW_WIDTH = INFO\WIN_WIDTH
    INFO\DRW_HEIGHT = INFO\WIN_HEIGHT-40
    WritePreferenceLong("X_MIN",INFO\DRW_X)
    WritePreferenceLong("Y_MIN",INFO\DRW_Y)
    WritePreferenceLong("WIDTH",INFO\DRW_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\DRW_HEIGHT)
   
    INFO\COUL_FOND = RGB(255,255,255)
    INFO\COUL_CURSEUR = RGB(0,0,0)
    WritePreferenceLong("COUL_FOND",INFO\COUL_FOND)
    WritePreferenceLong("COUL_CURSEUR",INFO\COUL_CURSEUR)
   
    PreferenceGroup("INPUT_OUTPUT")
    INFO\DEFAULT_FILE$ = "sans_nom.cvs"              ; initial path + file
    INFO\PATTERN$ = "ASCII délimité (*.cvs)|*.cvs|"  ; set first pattern  (index = 0)
    INFO\PATTERN$ + "Script (*.scr)|*.scr|"          ; set second pattern (index = 1)
    INFO\PATTERN$ + "DXF (*.dxf)|*.dxf|"             ; set third pattern  (index = 2)
    INFO\PATTERN$ + "Jpeg (*.jpg)|*.jpg|"            ; set fourth pattern (index = 3)
    INFO\PATTERN$ + "All files (*.*)|*.*"            ; set fifth pattern  (index = 4)
    INFO\PATTERN_POSITION = 0 
    WritePreferenceString("DEFAULT_FILE",INFO\DEFAULT_FILE$)
    WritePreferenceString("PATTERN",INFO\PATTERN$)
    WritePreferenceLong("PATTERN_POSITION", INFO\PATTERN_POSITION)
   
    PreferenceGroup("PROPERTIES")
    INFO\PROP_SHOW = 0
    INFO\PROP_X = INFO\WIN_XMIN
    INFO\PROP_Y = INFO\WIN_YMIN+25
    INFO\PROP_WIDTH = 150
    INFO\PROP_HEIGHT = INFO\WIN_HEIGHT
    WritePreferenceLong("PROP_SHOW",INFO\PROP_SHOW)
    WritePreferenceLong("X_MIN",INFO\PROP_X)
    WritePreferenceLong("Y_MIN",INFO\PROP_Y)
    WritePreferenceLong("WIDTH",INFO\PROP_WIDTH)
    WritePreferenceLong("HEIGHT",INFO\PROP_HEIGHT)
   
    PreferenceGroup("ACCROCH_OBJ")
    INFO\SELECTION = 5
    INFO\POIGNEE = 10
    WritePreferenceLong("SELECTION",INFO\SELECTION)
    WritePreferenceLong("POIGNEE",INFO\POIGNEE)
   
    ClosePreferences()
  EndIf
EndProcedure
 
Procedure Initialisation()
  FichierPreference()

  quit = 0
  sommet_courant = -1
  num_entite =0 : compteur_entite = 0
EndProcedure

;{ gestion des fenêtres
Procedure WindowCallback(WindowID, Message, lParam, wParam)
  If Message = #WM_PAINT
    StartDrawing(WindowOutput(#WIN_MAIN))
    DrawImage(ImageID(#IMAGE_ECRAN), 0, 0)
    StopDrawing()
  EndIf
 
  ProcedureReturn #PB_ProcessPureBasicEvents
EndProcedure
Procedure FondEcran()
  If IsImage(#IMAGE_ECRAN)<>0
    FreeImage(#IMAGE_ECRAN)
  EndIf
  If CreateImage(#IMAGE_ECRAN, INFO\DRW_WIDTH, INFO\DRW_HEIGHT)
    StartDrawing(ImageOutput(#IMAGE_ECRAN))
      Box(0,0,INFO\DRW_WIDTH,INFO\DRW_HEIGHT,INFO\COUL_FOND)
      DrawingMode(4)
      Box(0,0,INFO\DRW_WIDTH,INFO\DRW_HEIGHT,RGB(0,0,0))
      DrawingMode(0)
      ForEach ENT_LINE()
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1,ENT_LINE()\x2,ENT_LINE()\y2,ENT_LINE()\coul)
      Next
      DrawingMode(4)
      ForEach ENT_CIRCLE()
        Circle(ENT_CIRCLE()\X1,ENT_CIRCLE()\y1,ENT_CIRCLE()\Rayon,ENT_CIRCLE()\coul)
      Next
    StopDrawing()
  EndIf

EndProcedure
Procedure FlipBuffer()
  StartDrawing(WindowOutput(#WIN_MAIN))
  DrawImage(ImageID(#IMAGE_ECRAN), INFO\DRW_X, INFO\DRW_Y)
  StopDrawing()
EndProcedure
Procedure PopupWin_Prop()
 
  INFO\PROP_X = INFO\WIN_XMIN:INFO\PROP_Y = INFO\WIN_YMIN+25:INFO\PROP_WIDTH = 150:INFO\PROP_HEIGHT = INFO\WIN_HEIGHT
   
  If OpenWindow(#WIN_PROP,INFO\PROP_X,INFO\PROP_Y,INFO\PROP_WIDTH,INFO\PROP_HEIGHT/1.5,"Propriétés...",#PB_Window_SystemMenu|#PB_Window_SizeGadget)
    If CreateGadgetList(WindowID(#WIN_PROP))
      ListIconGadget(#GDT_LST_PROP,0,0,INFO\PROP_WIDTH,INFO\PROP_HEIGHT,"Libéllé",75,#PB_ListIcon_GridLines )
      AddGadgetColumn(#GDT_LST_PROP,1,"Valeur",70)
    EndIf
  EndIf
 
  SetActiveWindow(#WIN_MAIN)
EndProcedure
Procedure refreshWin_prop(type_entite.b,no_ent.w)
 
    Select type_entite
      Case #ENT_LINE
        SelectElement(ENT_LINE(),no_ent)
        If INFO\PROP_SHOW = 1
          ClearGadgetItemList(#GDT_LST_PROP)
          AddGadgetItem(#GDT_LST_PROP,-1,"ID Entité"+Chr(10)+Str(ENT_LINE()\No))
          AddGadgetItem(#GDT_LST_PROP,-1,"Entité"+Chr(10)+"LIGNE")
          AddGadgetItem(#GDT_LST_PROP,-1,"Départ X"+Chr(10)+Str(ENT_LINE()\X1))
          AddGadgetItem(#GDT_LST_PROP,-1,"Départ Y"+Chr(10)+Str(ENT_LINE()\y1))
          AddGadgetItem(#GDT_LST_PROP,-1,"Extrémité X"+Chr(10)+Str(ENT_LINE()\x2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Extrémité Y"+Chr(10)+Str(ENT_LINE()\y2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Longueur"+Chr(10)+StrF(ENT_LINE()\long,2))
          AddGadgetItem(#GDT_LST_PROP,-1,"Angle degré"+Chr(10)+StrF(ENT_LINE()\ang_deg))
          AddGadgetItem(#GDT_LST_PROP,-1,"Angle radian"+Chr(10)+StrF(ENT_LINE()\ang_rad))
          AddGadgetItem(#GDT_LST_PROP,-1,"tangente angle"+Chr(10)+StrF(ENT_LINE()\tan_angle))
          AddGadgetItem(#GDT_LST_PROP,-1,"dist. a ordonné"+Chr(10)+StrF(ENT_LINE()\dist_ord))
        EndIf
        StartDrawing(WindowOutput(#WIN_MAIN))
        DrawingMode(4)
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1-1,ENT_LINE()\x2,ENT_LINE()\y2-1,RGB(0,255,0))
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1,ENT_LINE()\x2,ENT_LINE()\y2,RGB(0,255,0))
        LineXY(ENT_LINE()\X1,ENT_LINE()\y1+1,ENT_LINE()\x2,ENT_LINE()\y2+1,RGB(0,255,0))
        Box(ENT_LINE()\X1-INFO\POIGNEE/2,ENT_LINE()\y1-INFO\POIGNEE/2,INFO\POIGNEE,INFO\POIGNEE,RGB(0,0,255))
        Box(ENT_LINE()\x2-INFO\POIGNEE/2,ENT_LINE()\y2-INFO\POIGNEE/2,INFO\POIGNEE,INFO\POIGNEE,RGB(0,0,255))
        DrawingMode(0)
        StopDrawing()

    EndSelect
EndProcedure
;}
;{ calculs divers

Procedure.l Distance(x.l,y.l) ;; desactivé
  ; Sommet.l = -1
  ; ForEach Sommet()
    ; Distance.l = Sqr(Pow(x-Sommet()\x,2)+Pow(y-Sommet()\y,2))
    ; ; INFO\SELECTION * 2 pour une sélection plus aisée d'un sommet
    ; If Distance <= INFO\SELECTION * 2
      ; Sommet = Sommet()\No
      ; Break
    ; EndIf
  ; Next
  ;
  ; ProcedureReturn Sommet
EndProcedure
Procedure calcul(type_entite.b,no_ent.w)
  Select type_entite
    Case #ENT_LINE
      SelectElement(ENT_LINE(),no_ent)
      ; calcul de la longueur hypothénuse = racine carré de (x1-x2)²+(y1-y2)²
      cx1 = ENT_LINE()\X1 : cy1 = ENT_LINE()\y1 : cx2 = ENT_LINE()\x2 : cy2 = ENT_LINE()\y2
      ; If cx1>cx2 : tmp=cx1 : cx1 = cx2 : cx2 = cx1 : EndIf
      ; If cy1>cy2 : tmp=cy1 : cy1 = cy2 : cy2 = cy1 : EndIf
      ENT_LINE()\long = Sqr(Pow((cx2-cx1),2)+Pow((cy2-cy1),2))
      If cx1=cx2 ; si la droite est parfaitement verticale
        ENT_LINE()\tan_angle = 9999
        ENT_LINE()\ang_rad = 1.5707963
        ENT_LINE()\ang_deg = 90
        ENT_LINE()\dist_ord = cx1
      Else
        If cy1=cy2 ; la droite est parfaitement horizontale
          ENT_LINE()\tan_angle = 0
          ENT_LINE()\ang_rad = 0
          ENT_LINE()\ang_deg = 0
          If cx1 < cx2
            ENT_LINE()\dist_ord = cx1
          Else
            ENT_LINE()\dist_ord = cx2
          EndIf
        Else
          ENT_LINE()\tan_angle = (cy2-cy1)/(cx2-cx1)
          ENT_LINE()\ang_rad = ATan(ENT_LINE()\tan_angle)
          ENT_LINE()\ang_deg = ENT_LINE()\ang_rad * 57.2957795 ; = 180/PI
          ENT_LINE()\dist_ord = cy1-ENT_LINE()\tan_angle*cx1 ; = b de y = ax+b
        EndIf
      EndIf
  EndSelect
  LastElement(ENT_LINE())
EndProcedure
Procedure Entite_supprime(type_entite.b,no_ent.w)
  Select type_entite
    Case #ENT_LINE
      SelectElement(ENT_LINE(),no_ent)
      DeleteElement(ENT_LINE(),1)
      ; mettre à jour le numéro d'entité  !!! différent du compteur d'entité = <compteur_entite>
  EndSelect
 
 
  StatusBarText(#GDT_STB_MAIN, 2, "Regen..."):num_entite=-1
  ;; pour chaque type d'entité faire :
  ForEach ENT_LINE()
    num_entite+1
    ENT_LINE()\No = num_entite ; met à jour le numéro d'entité
    ENT_LINE()\maintien = RSet(Str(#ENT_LINE),4,"0")+RSet(Str(num_entite),8,"0") ; met à jour le maintien
  Next
  compteur_entite = num_entite+1
 
  StatusBarText(#GDT_STB_MAIN, 2, "")
  FondEcran()
  FlipBuffer()
EndProcedure
Procedure SelectionEntite()
  entite_selection = "-1"
  point_x = WindowMouseX(#WIN_MAIN) : point_y = WindowMouseY(#WIN_MAIN)
 
  ; OpenWindow(100,0,0,300,300,0,"")
  ; If CreateGadgetList(WindowID(100))
    ; ListViewGadget(101,0,0,300,300)
  ; EndIf
  ; If CountGadgetItems(101)>0
    ; ClearGadgetItemList(101)
  ; EndIf
 
  ForEach ENT_LINE()
    ; teste si le point est sur la ligne ou proche
    ; 1) calcul de la droite perpendiculaire  à S1 qui passe par Px Py      
   
    ;; il s'agit d'une droite verticale
    If ENT_LINE()\tan_angle = 9999
      tan_angle.f = 0
      dist_ord.f = point_x
      ; 2) intersection de ENT_LINE() avec 1)            
      point_x1.f = ENT_LINE()\X1
      point_y1.f = point_y
    Else 
      ;; il s'agit d'une droite horizontale
      If ENT_LINE()\tan_angle = 0
        tan_angle.f = 9999
        dist_ord.f = point_x
        ; 2) intersection de ENT_LINE() avec 1)            
        point_x1.f = point_x
        point_y1.f = ENT_LINE()\y1
      Else
        ;; sinon il s'agit d'une droite oblique quelconque
        tan_angle.f   = -1/ENT_LINE()\tan_angle
        dist_ord.f   = point_y - tan_angle * point_x
        ; 2) intersection de ENT_LINE() avec 1)            
        point_x1.f   = ( dist_ord - ENT_LINE()\dist_ord ) / ( ENT_LINE()\tan_angle - tan_angle )
        point_y1.f   = ENT_LINE()\tan_angle * point_x1 + ENT_LINE()\dist_ord
      EndIf
    EndIf
   
    ; 3) calcul de la Distance de point_x,point_y à point_x1,point_y1
    long_per.f   = Sqr(Pow((point_x-point_x1),2)+Pow((point_y-point_y1),2))

    If long_per <= INFO\SELECTION
      ; 4) calcul de la Distance de ENT_LINE()\X1,y1 à ppx,ppy            
      long_1.f   = Sqr(Pow((ENT_LINE()\X1-point_x1),2)+Pow((ENT_LINE()\y1-point_y1),2))
     
      ; 5) calcul de la Distance de ENT_LINE()\x2,y2 à ppx,ppy              
      long_2.f   = Sqr(Pow((ENT_LINE()\x2-point_x1),2)+Pow((ENT_LINE()\y2-point_y1),2))
     
      long_result.f   = long_1 + long_2
      ; AddGadgetItem(101,-1,"point_x "+StrF(point_x))
      ; AddGadgetItem(101,-1,"point_y"+StrF(point_y))
      ; AddGadgetItem(101,-1,"lg du segment "+StrF(long_per)+" long selection"+Str(INFO\SELECTION))
      ; AddGadgetItem(101,-1,"tan_angle "+StrF(tan_angle))
      ; AddGadgetItem(101,-1,"dist_ord "+StrF(dist_ord))
      ; AddGadgetItem(101,-1,"point_x1 "+StrF(point_x1))
      ; AddGadgetItem(101,-1,"point_y1"+StrF(point_y1))
      ; AddGadgetItem(101,-1,"long1 "+StrF(long_1))
      ; AddGadgetItem(101,-1,"long2 "+StrF(long_2))
      ; AddGadgetItem(101,-1,"long_result "+StrF(long_result))
      ; AddGadgetItem(101,-1,"ENT_LINE()\long"+StrF(ENT_LINE()\long))
      ; AddGadgetItem(101,-1,"long_result < ENT_LINE()\long ")

      If Int(long_result) <= ENT_LINE()\long + INFO\SELECTION
        entite_selection = ENT_LINE()\maintien
        SetActiveWindow(#WIN_MAIN)
        Break
      EndIf 
    EndIf
  Next
  SetActiveWindow(#WIN_MAIN)
EndProcedure
;}
;{ opération sur les fichiers
Procedure Fichier_sauvegarder(type.b)
  ; INFO\type_fichier contient le numéro du filtre ou patern choisi
  Select type
    Case #CVS_FILE
      If CreateFile(0,INFO\fichier_dessin)
        ForEach ENT_LINE()
          chaine.s = "LINE;"+Str(ENT_LINE()\No)+";"
          chaine = chaine + Str(ENT_LINE()\X1)+";"+Str(ENT_LINE()\y1)+";"
          chaine = chaine + Str(ENT_LINE()\x2)+";"+Str(ENT_LINE()\y2)+";"
          chaine = chaine + Str(ENT_LINE()\long)+";"
          chaine = chaine + StrF(ENT_LINE()\tan_angle,6)+";"
          chaine = chaine + StrF(ENT_LINE()\ang_deg,6)+";"
          chaine = chaine + StrF(ENT_LINE()\ang_rad,6)+";"
          chaine = chaine + StrF(ENT_LINE()\dist_ord,6)
          WriteStringN(0,chaine)
        Next
        ForEach ENT_CIRCLE()
          chaine.s = "CIRCLE;"+Str(ENT_CIRCLE()\No)+";"
          chaine = chaine + Str(ENT_CIRCLE()\X1)+";"+Str(ENT_CIRCLE()\y1)+";"
          chaine = chaine + Str(ENT_CIRCLE()\Rayon) ;+";"
          ; chaine = chaine + Str(ENT_LINE()\long)+";"
          ; chaine = chaine + StrF(ENT_LINE()\tan_angle,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\ang_deg,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\ang_rad,6)+";"
          ; chaine = chaine + StrF(ENT_LINE()\dist_ord,6)
          WriteStringN(0,chaine)
        Next
       
        ; WriteStringN("")
        ; ForEach Sommet()
          ; chaine.s = "SOMMET;"+Str(Sommet()\No)+";"+Str(Sommet()\x)+";"+Str(Sommet()\y)
          ; WriteStringN(chaine)
        ; Next
        CloseFile(0)
      EndIf
    Case #SCR_FILE
      If CreateFile(0,INFO\fichier_dessin)
        ForEach ENT_LINE()
          chaine.s = "LIGNE" : WriteStringN(0,chaine)
          chaine = Str(ENT_LINE()\X1)+","+Str(ENT_LINE()\y1) : WriteStringN(0,chaine)
          chaine = Str(ENT_LINE()\x2)+","+Str(ENT_LINE()\y2) : WriteStringN(0,chaine)
          WriteStringN(0,"")
        Next
       
        CloseFile(0)
      EndIf
  EndSelect
 
EndProcedure
;}
;{ dessin des entités
Procedure DessineLigne()
  LastElement(ENT_LINE());; replace le pointeur à la fin de la liste
 
  AddElement(ENT_LINE())
  num_entite = compteur_entite
  ENT_LINE()\No = num_entite
  ENT_LINE()\maintien = RSet(Str(#ENT_LINE),4,"0")+RSet(Str(num_entite),8,"0")
  If sommet_selection = -1
    ; aucun sommet n'est selectionné, on commence une nouvelle ligne
    Sommet(0) = WindowMouseX(#WIN_MAIN) : Sommet(1) = WindowMouseY(#WIN_MAIN)
    ; premier point de la ligne
    ENT_LINE()\X1 = Sommet(0) : ENT_LINE()\y1 = Sommet(1)
    sommet_courant = 0
  Else
    ; au contraire, si un Sommet est selectionné
    ENT_LINE()\X1 = Sommet(2) : ENT_LINE()\y1 = Sommet(2)
    sommet_courant = 2
  EndIf
 
  StatusBarText(#GDT_STB_MAIN, 2, "Ligne, 2ème point...")
  Repeat
    event = WaitWindowEvent()
    If event = #WM_MOUSEMOVE
      FlipBuffer()
      StartDrawing(WindowOutput(#WIN_MAIN))
      LineXY(ENT_LINE()\X1,ENT_LINE()\y1,WindowMouseX(#WIN_MAIN),WindowMouseY(#WIN_MAIN),RGB(255,0,0))
      StopDrawing()
    EndIf
  Until event=#WM_LBUTTONUP
  Sommet(2) = WindowMouseX(#WIN_MAIN) : Sommet(3) = WindowMouseY(#WIN_MAIN)
  ENT_LINE()\x2 = Sommet(2) :ENT_LINE()\y2 = Sommet(3)
  calcul(#ENT_LINE,ENT_LINE()\No)
  refreshWin_prop(#ENT_LINE,ENT_LINE()\No)
  compteur_entite +1
  StatusBarText(#GDT_STB_MAIN, 2, "")
EndProcedure
Procedure DessineCercle()
  LastElement(ENT_CIRCLE());; replace le pointeur à la fin de la liste
 
  AddElement(ENT_CIRCLE())
  num_entite = compteur_entite
  ENT_CIRCLE()\No = num_entite
  ENT_CIRCLE()\maintien = RSet(Str(#ENT_CIRCLE),4,"0")+RSet(Str(num_entite),8,"0")
  If sommet_selection = -1
    ; aucun sommet n'est selectionné, on commence une nouvelle ligne
    Sommet(0) = WindowMouseX(#WIN_MAIN) : Sommet(1) = WindowMouseY(#WIN_MAIN)
    ; premier point de la ligne
    ENT_CIRCLE()\X1 = Sommet(0) : ENT_CIRCLE()\y1 = Sommet(1)
    sommet_courant = 0
  Else
    ; au contraire, si un Sommet est selectionné
    ENT_CIRCLE()\X1 = Sommet(2) : ENT_CIRCLE()\y1 = Sommet(2)
    sommet_courant = 2
  EndIf
 
  StatusBarText(#GDT_STB_MAIN, 2, "Cercle, Rayon...")
  Repeat
    event = WaitWindowEvent()
    If event = #WM_MOUSEMOVE
      FlipBuffer()
      StartDrawing(WindowOutput(#WIN_MAIN))
      DrawingMode(4)
      Rayon = ENT_CIRCLE()\X1-WindowMouseX(#WIN_MAIN)
      Circle(ENT_CIRCLE()\X1,ENT_CIRCLE()\y1,Rayon,RGB(255,0,0))
      StopDrawing()
    EndIf
  Until event=#WM_LBUTTONUP
  Sommet(2) = WindowMouseX(#WIN_MAIN) : Sommet(3) = WindowMouseY(#WIN_MAIN)
  ENT_CIRCLE()\Rayon = ENT_CIRCLE()\X1-Sommet(2)
  calcul(#ENT_CIRCLE,ENT_CIRCLE()\No)
  refreshWin_prop(#ENT_CIRCLE,ENT_CIRCLE()\No)
  compteur_entite +1
  StatusBarText(#GDT_STB_MAIN, 2, "")
EndProcedure
;}

;}
;{ programme principal
Initialisation()

If OpenWindow(#WIN_MAIN, INFO\WIN_XMIN, INFO\WIN_YMIN, INFO\WIN_WIDTH, INFO\WIN_HEIGHT, INFO\WIN_TITLE$, INFO\WIN_OPTION)
  INFO\WIN_XMIN = WindowX(#WIN_MAIN)
  INFO\WIN_YMIN = WindowY(#WIN_MAIN)
  ;{ définitions menu
  If CreateMenu(#MNU_MAIN,WindowID(#WIN_MAIN))
    MenuTitle("Fichier")
    MenuItem(#MNU_MAIN_OUVRIR,"Ouvrir...")
    MenuBar()
    MenuItem(#MNU_MAIN_ENREGISTRER_SOUS,"Enregistrer sous...")
    MenuBar()
    MenuItem(#MNU_MAIN_QUIT,"Quitter"+Chr(9)+"ALT+F4")
    ;MenuTitle("Edition")
    ;MenuTitle("Vue")
    ;MenuTitle("Insérer")
    ;MenuTitle("Format")
    ;MenuTitle("Outils")
    MenuTitle("Dessin")
    MenuItem(#MNU_MAIN_LIGNE,"Ligne")
    MenuItem(#MNU_MAIN_CERCLE,"Cercle")
    ;MenuTitle("Cotation")
    MenuTitle("Modifier")
    MenuItem(#MNU_MAIN_PROPRIETE,"Propriétés")
    MenuBar()
    MenuItem(#MNU_MAIN_SELECTIONNER,"Selectionner")
    MenuItem(#MNU_MAIN_EFFACER,"Effacer")
   
  EndIf
  ;}
  ;{ définitions gadgets
  ; If CreateGadgetList(WindowID(#WIN_MAIN))
    ;
  ; EndIf
  If CreateStatusBar(#GDT_STB_MAIN,WindowID(#WIN_MAIN))
    AddStatusBarField(50)
    AddStatusBarField(50)
    AddStatusBarField(200)
  EndIf
  ;}
 
  INFO\HWND_WIN_MAIN = WindowID(#WIN_MAIN)
  AddKeyboardShortcut(#WIN_MAIN, #PB_Shortcut_Escape, #TOUCHE_ECHAP_APPUYEE) ; qui generera un evenement de valeur 15.
 
  FondEcran()
 
  SetWindowCallback(@WindowCallback())
  quit.b = 0
  Repeat
    event = WaitWindowEvent()
   
    ;FlipBuffer()
    mx = WindowMouseX(#WIN_MAIN) : my = WindowMouseY(#WIN_MAIN)
   
    StatusBarText(#GDT_STB_MAIN, 0, "X:"+Str(mx))
    StatusBarText(#GDT_STB_MAIN, 1, "Y:"+Str(my))
   
    Select event
      ;{ traitement evénement gadgets
      Case #PB_Event_Gadget
        Select EventGadget()
         
        EndSelect ;}
        ;{ traitement évenement menu + pop-up menu
      Case #PB_Event_Menu
        Select EventMenu()
          Case #TOUCHE_ECHAP_APPUYEE
            DRAW_ENT = -1
           
          ;{ traitement menu fichier
          Case #MNU_MAIN_OUVRIR
           
          Case #MNU_MAIN_ENREGISTRER_SOUS
           
            INFO\fichier_dessin = SaveFileRequester("Enregistrer le dessin sous ...",INFO\DEFAULT_FILE$,INFO\PATTERN$,INFO\PATTERN_POSITION)
            INFO\type_fichier = SelectedFilePattern()
           
            Select INFO\type_fichier
              Case #CVS_FILE ;= 0
                If UCase(Right(INFO\fichier_dessin,4))<>".CVS"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".CVS"
                EndIf
                Fichier_sauvegarder(#CVS_FILE)
               
              Case #SCR_FILE ;= 1
                If UCase(Right(INFO\fichier_dessin,4))<>".SCR"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".SCR"
                EndIf
                Fichier_sauvegarder(#SCR_FILE)
               
              Case #DXF_FILE ;= 2
                If UCase(Right(INFO\fichier_dessin,4))<>".DXF"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".DXF"
                EndIf
                Fichier_sauvegarder(#DXF_FILE)
               
              Case #JPG_FILE ;= 3
                If UCase(Right(INFO\fichier_dessin,4))<>".JPG"
                  INFO\fichier_dessin = INFO\fichier_dessin + ".JPG"
                EndIf
                Fichier_sauvegarder(#JPG_FILE)
               
              Case #ALL_FILE ;= 4
               
            EndSelect
            StatusBarText(#GDT_STB_MAIN, 2, "...."+Right(INFO\fichier_dessin,30))
           
           
          Case #MNU_MAIN_QUIT
            quit = #TERMINER_APPLICATION
          ;}
          ;{ traitement menu dessin 
          Case #MNU_MAIN_LIGNE
            DRAW_ENT = #ENT_LINE
            StatusBarText(#GDT_STB_MAIN, 2, "Ligne, 1er point...")
          Case #MNU_MAIN_CERCLE
            DRAW_ENT = #ENT_CIRCLE
            StatusBarText(#GDT_STB_MAIN, 2, "Cercle, Centre...")
            ;}
          ;{ traitement menu modifier
          Case #MNU_MAIN_PROPRIETE
            If GetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE)=0
              SetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE,1)
              PopupWin_Prop()
              INFO\PROP_SHOW=1
            Else
              SetMenuItemState(#MNU_MAIN,#MNU_MAIN_PROPRIETE,0)
              CloseWindow(#WIN_PROP)
              INFO\PROP_SHOW=0
            EndIf
           
          Case #MNU_MAIN_SELECTIONNER
            DRAW_ENT = #ENT_SEL
            StatusBarText(#GDT_STB_MAIN, 2, "Selectionner une entitée...")
           
          Case #MNU_MAIN_EFFACER
            DRAW_ENT = #ENT_DEL
            StatusBarText(#GDT_STB_MAIN, 2, "Supprimer une entitée...")
            ;}
           
        EndSelect ;}
        ;{ traitement autres évenements
      Case #PB_Event_CloseWindow
        quit = #TERMINER_APPLICATION
     
      Case #WM_CHAR
        Debug wParam
        Debug lParam
       
      Case #MOUSE_MOVE
        sommet_selection = -1

      Case #WM_LBUTTONUP
        Select DRAW_ENT
          ;{ dessiner
          Case #ENT_LINE
            DessineLigne()
            FondEcran()
           
          Case #ENT_CIRCLE
            DessineCercle()
            FondEcran()
         ;}
          ;{ supprimer une entitée
          Case #ENT_DEL
            ; si on clique sur une entité, affiche ses caractéristique dans la fenêtre propriété
            FlipBuffer()
            StatusBarText(#GDT_STB_MAIN, 2, "Cliquer sur l'entité à supprimer...")
            SelectionEntite()  ; + met a jour entite_selection = renvoie n° entite
            If Left(entite_selection,1)<>"R"
              code_entite = Val(Left(entite_selection,4))
              num_entite = Val(Right(entite_selection,8))
              Entite_supprime(code_entite,num_entite)
            EndIf
          ;}
          ;{ selectionner une entitée
          Case #ENT_SEL
            ; si on clique sur une entité, affiche ses caractéristique dans la fenêtre propriété
            ;sommet_selection = -1 : entite_selection = ""
            FlipBuffer()
            SelectionEntite()  ; + met a jour entite_selection = renvoie n° entite
            If Left(entite_selection,1)<>"R"
              code_entite = Val(Left(entite_selection,4))
              num_entite = Val(Right(entite_selection,8))
              refreshWin_prop(code_entite,num_entite)
            EndIf
            ;}
           
        EndSelect
        ;}
    EndSelect
  Until quit>0
EndIf

DeleteFile("PureCAD.ini")
FichierPreference()

End
;} 
Répondre