Example #1
0
def gripStretchArc(arc, ptListToStretch, offSetX, offSetY, tolerance2ApproxCurve, inverseArc = None):
   """
   Stira i punti di grip di un arco che sono contenuti in ptListToStretch
   arc = arco da stirare
   ptListToStretch = lista dei punti da stirare
   offSetX = spostamento X
   offSetY = spostamento Y
   """
   if tolerance2ApproxCurve == None:
      tolerance = QadVariables.get(QadMsg.translate("Environment variables", "TOLERANCE2APPROXCURVE"))
   else:
      tolerance = tolerance2ApproxCurve
   
   startPt = arc.getStartPt()
   endPt = arc.getEndPt()
   middlePt = arc.getMiddlePt()
   newStartPt = QgsPoint(startPt)
   newEndPt = QgsPoint(endPt)
   newMiddlePt = QgsPoint(middlePt)
   newCenter = None
   startPtChanged = endPtChanged = middlePtPtChanged = False
   for ptToStretch in ptListToStretch:
      if qad_utils.ptNear(ptToStretch, arc.center): # se i punti sono sufficientemente vicini
         newCenter = QgsPoint(arc.center.x() + offSetX, arc.center.y() + offSetY)
      else:
         if qad_utils.ptNear(startPt, ptToStretch):
            newStartPt.set(startPt.x() + offSetX, startPt.y() + offSetY)
            startPtChanged = True
         elif qad_utils.ptNear(endPt, ptToStretch):
            newEndPt.set(endPt.x() + offSetX, endPt.y() + offSetY)
            endPtChanged = True
         elif qad_utils.ptNear(middlePt, ptToStretch):
            newMiddlePt.set(middlePt.x() + offSetX, middlePt.y() + offSetY)
            middlePtPtChanged = True
   
   newArc = qad_arc.QadArc()
   if newArc.fromStartSecondEndPts(newStartPt, newMiddlePt, newEndPt) == False:
      return None
   
   # se il centro era nei punti di grip
   if newCenter is not None:
      # se i tre punti dell'arco erano nei punti di grip oppure
      # allora non cambio il centro
      if (startPtChanged and endPtChanged and middlePtPtChanged):
         pass
      else:
         newArc.center.set(newCenter.x(), newCenter.y())
      
   if inverseArc is not None: # se l'arco faceva parte di una linestring
      # verifico il verso del nuovo arco
      if qad_utils.ptNear(newStartPt, newArc.getStartPt()):
         # stesso verso del vecchio arco
         return newArc, inverseArc
      else:
         return newArc, not inverseArc
      
   return newArc
Example #2
0
    def canvasMoveEvent(self, event):
        QadGetPoint.canvasMoveEvent(self, event)

        self.__highlight.reset()
        ok = False

        # noti il punto iniziale e finale dell'arco si richiede il punto intermedio
        if self.mode == Qad_gripLineToArcConvert_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_SECOND_PT:
            if self.linearObject is None:
                return
            arc = QadArc()
            if arc.fromStartSecondEndPts(self.startPt, self.tmpPoint,
                                         self.endPt) == False:
                return
            if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                self.linearObject.setArc(arc, False)  # arco non inverso
            else:
                self.linearObject.setArc(arc, True)  # arco inverso
            ok = True

        if ok:
            pts = self.linearObjectList.asPolyline(self.tolerance2ApproxCurve)
            if self.layer.geometryType() == QGis.Polygon:
                geom = QgsGeometry.fromPolygon([pts])
            else:
                geom = QgsGeometry.fromPolyline(pts)
            # trasformo la geometria nel crs del layer
            self.__highlight.addGeometry(
                self.mapToLayerCoordinates(self.layer, geom), self.layer)
Example #3
0
def gripStretchCircle(circle, basePt, ptListToStretch, offSetX, offSetY, tolerance2ApproxCurve):
   """
   Stira i punti di grip di un cerchio che sono contenuti in ptListToStretch
   circle = cerchio da stirare
   basePt = punto base
   ptListToStretch = lista dei punti da stirare
   offSetX = spostamento X
   offSetY = spostamento Y
   """
   if tolerance2ApproxCurve == None:
      tolerance = QadVariables.get(QadMsg.translate("Environment variables", "TOLERANCE2APPROXCURVE"))
   else:
      tolerance = tolerance2ApproxCurve
   
   newCenter = QgsPoint(circle.center)
   newRadius = circle.radius
   
   for ptToStretch in ptListToStretch:
      if qad_utils.ptNear(ptToStretch, circle.center): # se i punti sono sufficientemente vicini
         newCenter.set(circle.center.x() + offSetX, circle.center.y() + offSetY)
      elif circle.isPtOnCircle(ptToStretch):
         newPt = QgsPoint(basePt.x() + offSetX, basePt.y() + offSetY)
         newRadius = qad_utils.getDistance(circle.center, newPt)

   newCircle = qad_circle.QadCircle()
   if newCircle.set(newCenter, newRadius) == False:
      return None
   
   return newCircle
Example #4
0
 def canvasMoveEvent(self, event):
    QadGetPoint.canvasMoveEvent(self, event)
    
    self.__highlight.reset()
    ok = False
     
    # noti il punto iniziale e finale dell'arco si richiede il punto intermedio
    if self.mode == Qad_gripLineToArcConvert_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_SECOND_PT:
       if self.linearObject is None:
          return
       arc = QadArc()
       if arc.fromStartSecondEndPts(self.startPt, self.tmpPoint, self.endPt) == False:
          return
       if qad_utils.ptNear(self.startPt, arc.getStartPt()):
          self.linearObject.setArc(arc, False) # arco non inverso
       else:
          self.linearObject.setArc(arc, True) # arco inverso
       ok = True
    
    if ok:
       pts = self.linearObjectList.asPolyline(self.tolerance2ApproxCurve)
       if self.layer.geometryType() == QGis.Polygon:
          geom = QgsGeometry.fromPolygon([pts])
       else:
          geom = QgsGeometry.fromPolyline(pts)
       # trasformo la geometria nel crs del layer
       self.__highlight.addGeometry(self.mapToLayerCoordinates(self.layer, geom), self.layer)
Example #5
0
def isPtContainedForStretch(point, containerGeom, tolerance=None):
   """
   Funzione di ausilio per le funzioni di stretch (stretchPoint e stretchQgsLineStringGeometry).
   Se containerGeom è un oggetto QgsGeometry allora ritorna True se il punto è contenuto a livello spaziale
   dalla geometria containerGeom.
   Se containerGeom è una lista di punti allora ritorna True se il punto è fra quelli della lista.
   """
   if tolerance is None:
      tolerance = qad_utils.TOLERANCE
   if type(containerGeom) == QgsGeometry: # geometria   
      return containerGeom.contains(point)
   elif type(containerGeom) == list: # lista di punti
      for containerPt in containerGeom:
         if qad_utils.ptNear(containerPt, point, tolerance): # se i punti sono sufficientemente vicini
            return True
   return False 
Example #6
0
def isPtContainedForStretch(point, containerGeom, tolerance=None):
   """
   Funzione di ausilio per le funzioni di stretch (stretchPoint e stretchQgsLineStringGeometry).
   Se containerGeom è un oggetto QgsGeometry allora ritorna True se il punto è contenuto a livello spaziale
   dalla geometria containerGeom.
   Se containerGeom è una lista di punti allora ritorna True se il punto è fra quelli della lista.
   """
   if tolerance is None:
      tolerance = qad_utils.TOLERANCE
   if type(containerGeom) == QgsGeometry: # geometria   
      return containerGeom.contains(point)
   elif type(containerGeom) == list: # lista di punti
      for containerPt in containerGeom:
         if qad_utils.ptNear(containerPt, point, tolerance): # se i punti sono sufficientemente vicini
            return True
   return False 
Example #7
0
def stretchQgsLineStringGeometry(geom, containerGeom, offSetX, offSetY, tolerance2ApproxCurve):
   """
   Stira i punti di una linestring che sono contenuti in containerGeom
   point = punto da tirare
   containerGeom = può essere una QgsGeometry rappresentante un poligono contenente i punti di geom da stirare
                   oppure una lista dei punti da stirare
   offSetX = spostamento X
   offSetY = spostamento Y
   """
   obj = qad_utils.whatGeomIs(0, geom)
   if (type(obj) != list and type(obj) != tuple):
      objType = obj.whatIs()
      if objType == "CIRCLE": # se é cerchio
         if isPtContainedForStretch(obj.center, containerGeom): # se il punto è contenuto in containerGeom
            obj.center.setX(obj.center.x() + offSetX)
            obj.center.setY(obj.center.y() + offSetY)
         return QgsGeometry.fromPolyline(obj.asPolyline(tolerance2ApproxCurve))         

   stretchedGeom = QgsGeometry(geom)
   snapper = QadSnapper()
   points = snapper.getEndPoints(stretchedGeom)
   del snapper

   linearObjectListToStretch = qad_utils.QadLinearObjectList()
   linearObjectListToStretch.fromPolyline(geom.asPolyline())
   
   for point in points:
      if isPtContainedForStretch(point, containerGeom): # se il punto è contenuto in containerGeom
         atPart = linearObjectListToStretch.containsPt(point)
         while atPart >= 0:
            linearObject = linearObjectListToStretch.getLinearObjectAt(atPart)
            pt = linearObject.getStartPt()        
            if qad_utils.ptNear(pt, point): # cambio punto iniziale
               pt.setX(pt.x() + offSetX)
               pt.setY(pt.y() + offSetY)
               if linearObject.isSegment():
                  linearObject.setStartPt(pt)
               else:
                  oldArc = linearObject.getArc()
                  middlePt = oldArc.getMiddlePt()
                  distFromMiddleChord = qad_utils.getDistance(middlePt, qad_utils.getPerpendicularPointOnInfinityLine(oldArc.getStartPt(), oldArc.getEndPt(), middlePt))
                  
                  newArc = QadArc()
                  if linearObject.isInverseArc():                  
                     middlePt = qad_utils.getMiddlePoint(pt, oldArc.getStartPt())
                     middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                 qad_utils.getAngleBy2Pts(pt, oldArc.getStartPt()) + math.pi / 2, \
                                                                 distFromMiddleChord)                  
                     if newArc.fromStartSecondEndPts(oldArc.getStartPt(), middlePt, pt) == False:
                        return None
                  else:
                     middlePt = qad_utils.getMiddlePoint(pt, oldArc.getEndPt())
                     middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                 qad_utils.getAngleBy2Pts(pt, oldArc.getEndPt()) - math.pi / 2, \
                                                                 distFromMiddleChord)                  
                     if newArc.fromStartSecondEndPts(pt, middlePt, oldArc.getEndPt()) == False:
                        return None
                  linearObject.setArc(newArc, linearObject.isInverseArc())         
            else:
               pt = linearObject.getEndPt()
               if qad_utils.ptNear(pt, point): # cambio punto finale
                  pt.setX(pt.x() + offSetX)
                  pt.setY(pt.y() + offSetY)
                  if linearObject.isSegment():
                     linearObject.setEndPt(pt)
                  else:
                     oldArc = linearObject.getArc()
                     middlePt = oldArc.getMiddlePt()
                     distFromMiddleChord = qad_utils.getDistance(middlePt, qad_utils.getPerpendicularPointOnInfinityLine(oldArc.getStartPt(), oldArc.getEndPt(), middlePt))
                     
                     newArc = QadArc()
                     if linearObject.isInverseArc():
                        middlePt = qad_utils.getMiddlePoint(pt, oldArc.getEndPt())
                        middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                    qad_utils.getAngleBy2Pts(pt, oldArc.getEndPt()) - math.pi / 2, \
                                                                    distFromMiddleChord)                  
                        if newArc.fromStartSecondEndPts(pt, middlePt, oldArc.getEndPt()) == False:
                           return None
                     else:
                        middlePt = qad_utils.getMiddlePoint(pt, oldArc.getStartPt())
                        middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                    qad_utils.getAngleBy2Pts(pt, oldArc.getStartPt()) + math.pi / 2, \
                                                                    distFromMiddleChord)                  
                        if newArc.fromStartSecondEndPts(oldArc.getStartPt(), middlePt, pt) == False:
                           return None
                     linearObject.setArc(newArc, linearObject.isInverseArc())            
                  
            atPart = linearObjectListToStretch.containsPt(point, atPart + 1)
            
   pts = linearObjectListToStretch.asPolyline(tolerance2ApproxCurve)
   stretchedGeom = QgsGeometry.fromPolyline(pts)    
      
   return stretchedGeom   
    def run(self, msgMapTool=False, msg=None):
        if self.plugIn.canvas.mapSettings().destinationCrs().geographicFlag():
            self.showMsg(
                QadMsg.translate(
                    "QAD",
                    "\nThe coordinate reference system of the project must be a projected coordinate system.\n"
                ))
            return True  # fine comando

        #=========================================================================
        # RICHIESTA PUNTO o ENTITA'
        if self.step == 0:  # inizio del comando
            # si appresta ad attendere un punto o un numero reale
            # msg, inputType, default, keyWords, valori non nulli
            self.waitFor(self.msg, \
                         QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                         self.angle, "", \
                         QadInputModeEnum.NOT_NULL)

            if self.startPt is not None:
                # imposto il map tool
                self.getPointMapTool().setDrawMode(
                    QadGetPointDrawModeEnum.ELASTIC_LINE)
                self.getPointMapTool().setStartPoint(self.startPt)

            self.step = 1
            return False

        #=========================================================================
        # RISPOSTA ALLA RICHIESTA PUNTO O NUMERO REALE
        elif self.step == 1:  # dopo aver atteso un punto si riavvia il comando
            if msgMapTool == True:  # il punto arriva da una selezione grafica
                # la condizione seguente si verifica se durante la selezione di un punto
                # é stato attivato un altro plugin che ha disattivato Qad
                # quindi stato riattivato il comando che torna qui senza che il maptool
                # abbia selezionato un punto
                if self.getPointMapTool(
                ).point is None:  # il maptool é stato attivato senza un punto
                    if self.getPointMapTool(
                    ).rightButton == True:  # se usato il tasto destro del mouse
                        return True  # fine comando
                    else:
                        self.setMapTool(
                            self.getPointMapTool())  # riattivo il maptool
                        return False

                value = self.getPointMapTool().point
            else:  # il punto o il numero reale arriva come parametro della funzione
                value = msg

            if value is None:
                return True  # fine comando

            if type(value) == float:
                self.angle = qad_utils.toRadians(value)
                return True  # fine comando
            elif type(value) == QgsPoint:
                # il/i punto/i indicato/i da questa questa funzione non devono alterare lastpoint
                self.plugIn.setLastPoint(self.__prevLastPoint)

                if self.startPt is not None:
                    self.angle = qad_utils.getAngleBy2Pts(self.startPt, value)
                    return True  # fine comando
                else:
                    self.startPt = value
                    # imposto il map tool
                    self.getPointMapTool().setDrawMode(
                        QadGetPointDrawModeEnum.ELASTIC_LINE)
                    self.getPointMapTool().setStartPoint(self.startPt)
                    # si appresta ad attendere un punto
                    self.waitForPoint(
                        QadMsg.translate("QAD", "Specify second point: "))
                    self.step = 2

            return False

        #=========================================================================
        # RISPOSTA ALLA RICHIESTA SECONDO PUNTO DELLA ANGOLO (da step = 1)
        elif self.step == 2:  # dopo aver atteso un punto si riavvia il comando
            if msgMapTool == True:  # il punto arriva da una selezione grafica
                # la condizione seguente si verifica se durante la selezione di un punto
                # é stato attivato un altro plugin che ha disattivato Qad
                # quindi stato riattivato il comando che torna qui senza che il maptool
                # abbia selezionato un punto
                if self.getPointMapTool(
                ).point is None:  # il maptool é stato attivato senza un punto
                    if self.getPointMapTool(
                    ).rightButton == True:  # se usato il tasto destro del mouse
                        return True  # fine comando
                    else:
                        self.setMapTool(
                            self.getPointMapTool())  # riattivo il maptool
                        return False

                value = self.getPointMapTool().point
            else:  # il punto arriva come parametro della funzione
                value = msg

            # il/i punto/i indicato/i da questa questa funzione non devono alterare lastpoint
            self.plugIn.setLastPoint(self.__prevLastPoint)

            if qad_utils.ptNear(self.startPt, value):
                self.showMsg(
                    QadMsg.translate("QAD", "\nThe points must be different."))
                # si appresta ad attendere un punto
                self.waitForPoint(
                    QadMsg.translate("QAD", "Specify second point: "))
                return False
            else:
                self.angle = qad_utils.getAngleBy2Pts(self.startPt, value)
                return True  # fine comando
Example #9
0
   def run(self, msgMapTool = False, msg = None):
      if self.plugIn.canvas.mapSettings().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando

      #=========================================================================
      # RICHIESTA PUNTO o ENTITA'
      if self.step == 0: # inizio del comando
         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, valori non nulli
         self.waitFor(self.msg, \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                      self.angle, "", \
                      QadInputModeEnum.NOT_NULL)
         
         if self.startPt is not None:            
            # imposto il map tool
            self.getPointMapTool().setDrawMode(QadGetPointDrawModeEnum.ELASTIC_LINE)
            self.getPointMapTool().setStartPoint(self.startPt)
                           
         self.step = 1
         return False

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO O NUMERO REALE
      elif self.step == 1: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False
               
            value = self.getPointMapTool().point
         else: # il punto o il numero reale arriva come parametro della funzione
            value = msg

         if value is None:
            return True # fine comando
         
         if type(value) == float:
            self.angle = qad_utils.toRadians(value)
            return True # fine comando
         elif type(value) == QgsPoint:
            # il/i punto/i indicato/i da questa questa funzione non devono alterare lastpoint 
            self.plugIn.setLastPoint(self.__prevLastPoint)
            
            if self.startPt is not None:
               self.angle = qad_utils.getAngleBy2Pts(self.startPt, value)
               return True # fine comando
            else:            
               self.startPt = value            
               # imposto il map tool
               self.getPointMapTool().setDrawMode(QadGetPointDrawModeEnum.ELASTIC_LINE)
               self.getPointMapTool().setStartPoint(self.startPt)
               # si appresta ad attendere un punto
               self.waitForPoint(QadMsg.translate("QAD", "Specify second point: "))
               self.step = 2

         return False
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO DELLA ANGOLO (da step = 1)
      elif self.step == 2: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         # il/i punto/i indicato/i da questa questa funzione non devono alterare lastpoint 
         self.plugIn.setLastPoint(self.__prevLastPoint)
         
         if qad_utils.ptNear(self.startPt, value):
            self.showMsg(QadMsg.translate("QAD", "\nThe points must be different."))
            # si appresta ad attendere un punto
            self.waitForPoint(QadMsg.translate("QAD", "Specify second point: "))
            return False
         else:
            self.angle = qad_utils.getAngleBy2Pts(self.startPt, value)
            return True # fine comando
Example #10
0
   def run(self, msgMapTool = False, msg = None):
      if self.plugIn.canvas.mapSettings().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando
            
      #=========================================================================
      # RICHIESTA SELEZIONE OGGETTI
      if self.step == 0: # inizio del comando
         if self.entitySet.isEmpty(): # non ci sono oggetti da ruotare
            return True
         self.showMsg(QadMsg.translate("Command_GRIPMIRROR", "\n** MIRROR **\n"))
         # si appresta ad attendere il secondo punto di specchio
         self.waitForMirrorPoint()

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO PER SPECCHIO
      elif self.step == 1: # dopo aver atteso un punto si riavvia il comando
         ctrlKey = False
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  value = None
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            ctrlKey = self.getPointMapTool().ctrlKey
            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("Command_GRIPMIRROR", "Base point") or value == "Base point":
               # si appresta ad attendere il punto base
               self.waitForBasePt()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "Copy") or value == "Copy":
               # Copia entità lasciando inalterate le originali
               self.copyEntities = True                     
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "Undo") or value == "Undo":
               if self.nOperationsToUndo > 0: 
                  self.nOperationsToUndo = self.nOperationsToUndo - 1
                  self.plugIn.undoEditCommand()
               else:
                  self.showMsg(QadMsg.translate("QAD", "\nThe command has been canceled."))                  
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "eXit") or value == "eXit":
               return True # fine comando
         elif type(value) == QgsPoint: # se é stato inserito il secondo punto
            if qad_utils.ptNear(self.basePt, value):
               self.showMsg(QadMsg.translate("Command_GRIPMIRROR", "\nThe points must be different."))
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
               return False
            
            self.secondMirrorPt.set(value.x(), value.y())

            if ctrlKey:
               self.copyEntities = True

            self.mirrorGeoms()

            if self.copyEntities == False:
               return True

            # si appresta ad attendere il secondo punto di specchio
            self.waitForMirrorPoint()

         else:
            if self.copyEntities == False:
               self.skipToNextGripCommand = True
            return True # fine comando

         return False

              
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO BASE (da step = 1)
      elif self.step == 2: # dopo aver atteso un punto
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  pass # opzione di default "spostamento"
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint: # se é stato inserito il punto base
            self.basePt.set(value.x(), value.y())
            
         # si appresta ad attendere il secondo punto di specchio
         self.waitForMirrorPoint()

         return False
Example #11
0
   def run(self, msgMapTool = False, msg = None):
      if self.plugIn.canvas.mapSettings().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando
            
      #=========================================================================
      # RICHIESTA SELEZIONE OGGETTI
      if self.step == 0: # inizio del comando
         if self.SSGetClass.run(msgMapTool, msg) == True:
            # selezione terminata
            self.step = 1
            self.getPointMapTool().refreshSnapType() # aggiorno lo snapType che può essere variato dal maptool di selezione entità                    
            return self.run(msgMapTool, msg)
      
      #=========================================================================
      # SPECCHIA OGGETTI
      elif self.step == 1:
         self.entitySet.set(self.SSGetClass.entitySet)
         
         if self.entitySet.count() == 0:
            return True # fine comando

         # imposto il map tool
         self.getPointMapTool().entitySet.set(self.entitySet)
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_FIRST_PT)                                
   
         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify first point of mirror line: "))
         self.step = 2      
         return False
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO BASE (da step = 1)
      elif self.step == 2: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  # si appresta ad attendere un punto
                  self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify first point of mirror line: "))
                  return False
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.firstMirrorPt.set(value.x(), value.y())

         # imposto il map tool
         self.getPointMapTool().firstMirrorPt = self.firstMirrorPt
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.FIRST_PT_KNOWN_ASK_FOR_SECOND_PT)                                
         
         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
         self.step = 3
         
         return False 
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO PER SPECCHIO (da step = 2)
      elif self.step == 3: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  # si appresta ad attendere un punto
                  self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if qad_utils.ptNear(self.firstMirrorPt, value):
            self.showMsg(QadMsg.translate("Command_MIRROR", "\nThe points must be different."))
            # si appresta ad attendere un punto
            self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
            return False
         
         self.secondMirrorPt.set(value.x(), value.y())
         
         keyWords = QadMsg.translate("QAD", "Yes") + "/" + \
                    QadMsg.translate("QAD", "No")                                       
         if self.copyFeatures == False:
            default = QadMsg.translate("QAD", "Yes")
         else: 
            default = QadMsg.translate("QAD", "No")
         prompt = QadMsg.translate("Command_MIRROR", "Erase source objects ? [{0}] <{1}>: ").format(keyWords, default)
             
         englishKeyWords = "Yes" + "/" + "No"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere enter o una parola chiave         
         # msg, inputType, default, keyWords, nessun controllo
         self.waitFor(prompt, \
                      QadInputTypeEnum.KEYWORDS, \
                      default, \
                      keyWords, QadInputModeEnum.NONE)
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_FIRST_PT)                                         
         self.step = 4

         return False
            

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA DI CANCELLAZIONE OGGETTO SORGENTE (da step = 3)
      elif self.step == 4: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
               value = QadMsg.translate("QAD", "No")   
            else:
               self.setMapTool(self.getPointMapTool()) # riattivo il maptool
               return False
         else: # il valore arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("QAD", "Yes") or value == "Yes":
               self.copyFeatures = False
            elif value == QadMsg.translate("QAD", "No") or value == "No":
               self.copyFeatures = True
                     
            self.mirrorGeoms()
            return True # fine comando

         return False
Example #12
0
def stretchQgsLineStringGeometry(geom, containerGeom, offSetX, offSetY, tolerance2ApproxCurve = None):
   """
   Stira i punti di una linestring che sono contenuti in containerGeom
   point = punto da tirare
   containerGeom = può essere una QgsGeometry rappresentante un poligono contenente i punti di geom da stirare
                   oppure una lista dei punti da stirare
   offSetX = spostamento X
   offSetY = spostamento Y
   """
   if tolerance2ApproxCurve == None:
      tolerance = QadVariables.get(QadMsg.translate("Environment variables", "TOLERANCE2APPROXCURVE"))
   else:
      tolerance = tolerance2ApproxCurve

   obj = qad_utils.whatGeomIs(0, geom)
   if (type(obj) != list and type(obj) != tuple):
      objType = obj.whatIs()
      if objType == "CIRCLE": # se é cerchio
         if isPtContainedForStretch(obj.center, containerGeom): # se il punto è contenuto in containerGeom
            obj.center.setX(obj.center.x() + offSetX)
            obj.center.setY(obj.center.y() + offSetY)
         return QgsGeometry.fromPolyline(obj.asPolyline(tolerance))

   stretchedGeom = QgsGeometry(geom)
   snapper = QadSnapper()
   points = snapper.getEndPoints(stretchedGeom)
   del snapper

   linearObjectListToStretch = qad_utils.QadLinearObjectList()
   linearObjectListToStretch.fromPolyline(geom.asPolyline())
   
   for point in points:
      if isPtContainedForStretch(point, containerGeom): # se il punto è contenuto in containerGeom
         atPart = linearObjectListToStretch.containsPt(point)
         while atPart >= 0:
            linearObject = linearObjectListToStretch.getLinearObjectAt(atPart)
            pt = linearObject.getStartPt()        
            if qad_utils.ptNear(pt, point): # cambio punto iniziale
               pt.setX(pt.x() + offSetX)
               pt.setY(pt.y() + offSetY)
               if linearObject.isSegment():
                  linearObject.setStartPt(pt)
               else:
                  oldArc = linearObject.getArc()
                  middlePt = oldArc.getMiddlePt()
                  distFromMiddleChord = qad_utils.getDistance(middlePt, qad_utils.getPerpendicularPointOnInfinityLine(oldArc.getStartPt(), oldArc.getEndPt(), middlePt))
                  
                  newArc = QadArc()
                  if linearObject.isInverseArc():                  
                     middlePt = qad_utils.getMiddlePoint(pt, oldArc.getStartPt())
                     middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                 qad_utils.getAngleBy2Pts(pt, oldArc.getStartPt()) + math.pi / 2, \
                                                                 distFromMiddleChord)                  
                     if newArc.fromStartSecondEndPts(oldArc.getStartPt(), middlePt, pt) == False:
                        return None
                  else:
                     middlePt = qad_utils.getMiddlePoint(pt, oldArc.getEndPt())
                     middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                 qad_utils.getAngleBy2Pts(pt, oldArc.getEndPt()) - math.pi / 2, \
                                                                 distFromMiddleChord)                  
                     if newArc.fromStartSecondEndPts(pt, middlePt, oldArc.getEndPt()) == False:
                        return None
                  linearObject.setArc(newArc, linearObject.isInverseArc())         
            else:
               pt = linearObject.getEndPt()
               if qad_utils.ptNear(pt, point): # cambio punto finale
                  pt.setX(pt.x() + offSetX)
                  pt.setY(pt.y() + offSetY)
                  if linearObject.isSegment():
                     linearObject.setEndPt(pt)
                  else:
                     oldArc = linearObject.getArc()
                     middlePt = oldArc.getMiddlePt()
                     distFromMiddleChord = qad_utils.getDistance(middlePt, qad_utils.getPerpendicularPointOnInfinityLine(oldArc.getStartPt(), oldArc.getEndPt(), middlePt))
                     
                     newArc = QadArc()
                     if linearObject.isInverseArc():
                        middlePt = qad_utils.getMiddlePoint(pt, oldArc.getEndPt())
                        middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                    qad_utils.getAngleBy2Pts(pt, oldArc.getEndPt()) - math.pi / 2, \
                                                                    distFromMiddleChord)                  
                        if newArc.fromStartSecondEndPts(pt, middlePt, oldArc.getEndPt()) == False:
                           return None
                     else:
                        middlePt = qad_utils.getMiddlePoint(pt, oldArc.getStartPt())
                        middlePt = qad_utils.getPolarPointByPtAngle(middlePt, \
                                                                    qad_utils.getAngleBy2Pts(pt, oldArc.getStartPt()) + math.pi / 2, \
                                                                    distFromMiddleChord)                  
                        if newArc.fromStartSecondEndPts(oldArc.getStartPt(), middlePt, pt) == False:
                           return None
                     linearObject.setArc(newArc, linearObject.isInverseArc())            
                  
            atPart = linearObjectListToStretch.containsPt(point, atPart + 1)
            
   pts = linearObjectListToStretch.asPolyline(tolerance)
   stretchedGeom = QgsGeometry.fromPolyline(pts)    
      
   return stretchedGeom   
Example #13
0
   def run(self, msgMapTool = False, msg = None):
      if self.plugIn.canvas.mapRenderer().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando
            
      #=========================================================================
      # RICHIESTA SELEZIONE OGGETTI
      if self.step == 0: # inizio del comando
         if self.SSGetClass.run(msgMapTool, msg) == True:
            # selezione terminata
            self.step = 1
            self.getPointMapTool().refreshSnapType() # aggiorno lo snapType che può essere variato dal maptool di selezione entità                    
            return self.run(msgMapTool, msg)
      
      #=========================================================================
      # SPECCHIA OGGETTI
      elif self.step == 1:
         self.entitySet.set(self.SSGetClass.entitySet)
         
         if self.entitySet.count() == 0:
            return True # fine comando

         # imposto il map tool
         self.getPointMapTool().entitySet.set(self.entitySet)
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_FIRST_PT)                                
   
         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify first point of mirror line: "))
         self.step = 2      
         return False
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO BASE (da step = 1)
      elif self.step == 2: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  # si appresta ad attendere un punto
                  self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify first point of mirror line: "))
                  return False
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.firstMirrorPt.set(value.x(), value.y())

         # imposto il map tool
         self.getPointMapTool().firstMirrorPt = self.firstMirrorPt
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.FIRST_PT_KNOWN_ASK_FOR_SECOND_PT)                                
         
         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
         self.step = 3
         
         return False 
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO PER SPECCHIO (da step = 2)
      elif self.step == 3: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  # si appresta ad attendere un punto
                  self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if qad_utils.ptNear(self.firstMirrorPt, value):
            self.showMsg(QadMsg.translate("Command_MIRROR", "\nThe points must be different."))
            # si appresta ad attendere un punto
            self.waitForPoint(QadMsg.translate("Command_MIRROR", "Specify second point of mirror line: "))
            return False
         
         self.secondMirrorPt.set(value.x(), value.y())
         
         keyWords = QadMsg.translate("QAD", "Yes") + "/" + \
                    QadMsg.translate("QAD", "No")                                       
         if self.copyFeatures == False:
            default = QadMsg.translate("QAD", "Yes")
         else: 
            default = QadMsg.translate("QAD", "No")
         prompt = QadMsg.translate("Command_MIRROR", "Erase source objects ? [{0}] <{1}>: ").format(keyWords, default)
             
         englishKeyWords = "Yes" + "/" + "No"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere enter o una parola chiave         
         # msg, inputType, default, keyWords, nessun controllo
         self.waitFor(prompt, \
                      QadInputTypeEnum.KEYWORDS, \
                      default, \
                      keyWords, QadInputModeEnum.NONE)
         self.getPointMapTool().setMode(Qad_mirror_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_FIRST_PT)                                         
         self.step = 4

         return False
            

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA DI CANCELLAZIONE OGGETTO SORGENTE (da step = 3)
      elif self.step == 4: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
               value = QadMsg.translate("QAD", "No")   
            else:
               self.setMapTool(self.getPointMapTool()) # riattivo il maptool
               return False
         else: # il valore arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("QAD", "Yes") or value == "Yes":
               self.copyFeatures = False
            elif value == QadMsg.translate("QAD", "No") or value == "No":
               self.copyFeatures = True
                     
            self.mirrorGeoms()
            return True # fine comando

         return False
Example #14
0
    def fromPolyline(self, points, startVertex, atLeastNSegment=None):
        """
      setta le caratteristiche del primo arco incontrato nella lista di punti
      partendo dalla posizione startVertex (0-indexed)
      ritorna la posizione nella lista del punto iniziale e finale se é stato trovato un arco
      altrimenti None
      N.B. in punti NON devono essere in coordinate geografiche
      """
        if atLeastNSegment is None:
            _atLeastNSegment = QadVariables.get(
                QadMsg.translate("Environment variables", "ARCMINSEGMENTQTY"),
                12)
        else:
            _atLeastNSegment = atLeastNSegment

        totPoints = len(points)
        # perché sia un    arco ci vogliono almeno _atLeastNSegment segmenti
        if (totPoints -
                1) - startVertex < _atLeastNSegment or _atLeastNSegment < 2:
            return None

        # per problemi di approssimazione dei calcoli
        epsilon = 1.e-4  # percentuale del raggio per ottenere max diff. di una distanza con il raggio

        InfinityLinePerpOnMiddle1 = None
        InfinityLinePerpOnMiddle2 = None

        nSegment = 0
        i = startVertex
        while i < totPoints - 1:
            if InfinityLinePerpOnMiddle1 is None:
                InfinityLinePerpOnMiddle1 = qad_utils.getInfinityLinePerpOnMiddle(
                    points[i], points[i + 1])
                nStartVertex = i
                nSegment = 1
                i = i + 1
                continue
            elif InfinityLinePerpOnMiddle2 is None:
                InfinityLinePerpOnMiddle2 = qad_utils.getInfinityLinePerpOnMiddle(
                    points[i], points[i + 1])
                if InfinityLinePerpOnMiddle2 is None:
                    InfinityLinePerpOnMiddle1 = None
                    nSegment = 0
                else:
                    # calcolo il presunto centro con 2 segmenti
                    center = qad_utils.getIntersectionPointOn2InfinityLines(InfinityLinePerpOnMiddle1[0], \
                                                                            InfinityLinePerpOnMiddle1[1], \
                                                                            InfinityLinePerpOnMiddle2[0], \
                                                                            InfinityLinePerpOnMiddle2[1])
                    if center is None:  # linee parallele
                        InfinityLinePerpOnMiddle1 = InfinityLinePerpOnMiddle2
                        InfinityLinePerpOnMiddle2 = None
                        nStartVertex = i
                        nSegment = 1
                    else:
                        nSegment = nSegment + 1
                        radius = qad_utils.getDistance(
                            center,
                            points[i + 1])  # calcolo il presunto raggio
                        tolerance = radius * epsilon

                        # calcolo il verso dell'arco e l'angolo dell'arco
                        # se un punto intermedio dell'arco è a sinistra del
                        # segmento che unisce i due punti allora il verso è antiorario
                        startClockWise = True if qad_utils.leftOfLine(
                            points[i], points[i - 1], points[i +
                                                             1]) < 0 else False
                        angle = qad_utils.getAngleBy3Pts(
                            points[i - 1], center, points[i + 1],
                            startClockWise)
                        prevInfinityLinePerpOnMiddle = InfinityLinePerpOnMiddle2
            else:  # e sono già stati valutati almeno 2 segmenti
                notInArc = False
                currInfinityLinePerpOnMiddle = qad_utils.getInfinityLinePerpOnMiddle(
                    points[i], points[i + 1])
                if currInfinityLinePerpOnMiddle is None:
                    notInArc = True
                else:
                    # calcolo il presunto centro con 2 segmenti
                    currCenter = qad_utils.getIntersectionPointOn2InfinityLines(prevInfinityLinePerpOnMiddle[0], \
                                                                                prevInfinityLinePerpOnMiddle[1], \
                                                                                currInfinityLinePerpOnMiddle[0], \
                                                                                currInfinityLinePerpOnMiddle[1])
                    if currCenter is None:  # linee parallele
                        notInArc = True
                    else:
                        # calcolo il verso dell'arco e l'angolo
                        clockWise = True if qad_utils.leftOfLine(
                            points[i], points[i - 1], points[i +
                                                             1]) < 0 else False
                        angle = angle + qad_utils.getAngleBy3Pts(
                            points[i], center, points[i + 1], startClockWise)

                        # se la distanza è così vicina a quella del raggio
                        # il verso dell'arco deve essere quello iniziale
                        # l'angolo dell'arco non può essere >= 360 gradi
                        if qad_utils.ptNear(center, currCenter, tolerance) and \
                           startClockWise == clockWise and \
                           angle < 2 * math.pi:
                            nSegment = nSegment + 1  # anche questo segmento fa parte dell'arco
                            prevInfinityLinePerpOnMiddle = currInfinityLinePerpOnMiddle
                        else:
                            notInArc = True

                # questo segmento non fa parte del cerchio
                if notInArc:
                    # se sono stati trovati un numero sufficiente di segmenti successivi
                    if nSegment >= _atLeastNSegment:
                        # se é un angolo giro e il primo punto = ultimo punto allora points é un cerchio
                        if qad_utils.doubleNear(
                                angle,
                                2 * math.pi) and points[0] == points[-1]:
                            return None
                        break
                    else:
                        i = i - 2
                        InfinityLinePerpOnMiddle1 = None
                        InfinityLinePerpOnMiddle2 = None

            i = i + 1

        # se sono stati trovati un numero sufficiente di segmenti successivi
        if nSegment >= _atLeastNSegment:
            nEndVertex = nStartVertex + nSegment
            # se il punto iniziale e quello finale non coincidono é un arco
            if points[nStartVertex] != points[nEndVertex]:
                self.center = center
                self.radius = radius

                # se il verso é orario
                if startClockWise:
                    # inverto l'angolo iniziale con quello finale
                    self.endAngle = qad_utils.getAngleBy2Pts(
                        center, points[nStartVertex])
                    self.startAngle = qad_utils.getAngleBy2Pts(
                        center, points[nEndVertex])
                else:
                    self.startAngle = qad_utils.getAngleBy2Pts(
                        center, points[nStartVertex])
                    self.endAngle = qad_utils.getAngleBy2Pts(
                        center, points[nEndVertex])

                return nStartVertex, nEndVertex

        return None
Example #15
0
   def run(self, msgMapTool = False, msg = None):
      self.isValidPreviousInput = True # per gestire il comando anche in macro
           
      if self.plugIn.canvas.mapRenderer().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando
      
      currLayer, errMsg = qad_layer.getCurrLayerEditable(self.plugIn.canvas, QGis.Line)
      if currLayer is None:
         self.showErr(errMsg)
         return True # fine comando

      #=========================================================================
      # RICHIESTA PRIMO PUNTO o CENTRO
      if self.step == 0: # inizio del comando
         # imposto il map tool
         self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_START_PT)        
         keyWords = QadMsg.translate("Command_ARC", "Center")
         
         prompt = QadMsg.translate("Command_ARC", "Specify the start point of the arc or [{0}]:").format(keyWords)                 
         
         englishKeyWords = "Center"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere un punto o enter o una parola chiave         
         # msg, inputType, default, keyWords, nessun controllo di modo
         self.waitFor(prompt, \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                      None, \
                      keyWords, QadInputModeEnum.NONE)         
         self.step = 1
         
         return False

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PRIMO PUNTO o CENTRO
      elif self.step == 1: # dopo aver atteso un punto o enter o una parola chiave si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if value is None:
            if self.plugIn.lastPoint is not None:
               value = self.plugIn.lastPoint
            else:
               return True # fine comando

         if type(value) == QgsPoint: # se é stato inserito il punto iniziale dell'arco           
            self.startPt = value
            self.plugIn.setLastPoint(value)
            
            # imposto il map tool
            self.getPointMapTool().arcStartPt = self.startPt
            self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_PT_KNOWN_ASK_FOR_SECOND_PT)
                                
            keyWords = QadMsg.translate("Command_ARC", "Center") + "/" + \
                       QadMsg.translate("Command_ARC", "End")
            
            prompt = QadMsg.translate("Command_ARC", "Specify second point of the arc or [{0}]:").format(keyWords)                 
            
            englishKeyWords = "Center" + "/" + "End"
            keyWords += "_" + englishKeyWords
            # si appresta ad attendere un punto o una parola chiave         
            # msg, inputType, default, keyWords
            self.waitFor(prompt, \
                         QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                         None, \
                         keyWords, QadInputModeEnum.NONE)
            
            self.step = 2
            return False
         else: # si vuole inserire il centro dell'arco
            # imposto il map tool
            self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.NONE_KNOWN_ASK_FOR_CENTER_PT)
            # si appresta ad attendere un punto
            self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the center of the arc: "))
            
            self.step = 13
            return False

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO o CENTRO o FINE
      elif self.step == 2: # dopo aver atteso un punto o una parola chiave si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("Command_ARC", "Center") or value == "Center":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_PT_KNOWN_ASK_FOR_CENTER_PT)
               # si appresta ad attendere un punto
               self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the center of the arc: "))
               self.step = 4           
            elif value == QadMsg.translate("Command_ARC", "End") or value == "End":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_PT_KNOWN_ASK_FOR_END_PT)
               # si appresta ad attendere un punto
               self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the final point of the arc: "))
               self.step = 8     
         elif type(value) == QgsPoint: # se é stato inserito il secondo punto dell'arco            
            self.secondPt = value
            # imposto il map tool
            self.getPointMapTool().arcSecondPt = self.secondPt
            self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_SECOND_PT_KNOWN_ASK_FOR_END_PT)

            # si appresta ad attendere un punto
            self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the final point of the arc: "))
            self.step = 3
                  
         return False

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO FINALE DELL'ARCO (da step = 2)
      elif self.step == 3: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.endPt = value
         
         arc = QadArc()         
         if arc.fromStartSecondEndPts(self.startPt, self.secondPt, self.endPt) == True:
            self.plugIn.setLastPoint(arc.getEndPt())
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
                  
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando
      
         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the final point of the arc: "))
         self.isValidPreviousInput = False # per gestire il comando anche in macro     
         return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA CENTRO DELL'ARCO (da step = 2)
      elif self.step == 4: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False
               
            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.centerPt = value
         self.plugIn.setLastPoint(value)
         
         # imposto il map tool
         self.getPointMapTool().arcCenterPt = self.centerPt
         self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_CENTER_PT_KNOWN_ASK_FOR_END_PT)
         
         keyWords = QadMsg.translate("Command_ARC", "Angle") + "/" + \
                    QadMsg.translate("Command_ARC", "chord Length")
                             
         prompt = QadMsg.translate("Command_ARC", "Specify the final point of the arc or [{0}]: ").format(keyWords)                 
                         
         englishKeyWords = "Angle" + "/" + "chord Length"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere un punto o una parola chiave         
         # msg, inputType, default, keyWords, valori nulli non ammessi
         self.waitFor(prompt, \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                      None, \
                      keyWords, QadInputModeEnum.NOT_NULL)
         
         self.step = 5
         return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare punto finale dell'arco o [Angolo/Lunghezza corda]: " (da step = 4)
      elif self.step == 5: # dopo aver atteso un punto o una parola chiave si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == unicode:  
            if value == QadMsg.translate("Command_ARC", "Angle") or value == "Angle":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_CENTER_PT_KNOWN_ASK_FOR_ANGLE)
               # si appresta ad attendere un punto o un numero reale         
               # msg, inputType, default, keyWords, valori nulli non ammessi
               self.waitFor(QadMsg.translate("Command_ARC", "Specify the included angle: "), \
                            QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                            None, "", \
                            QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO)
               self.step = 6
               return False                              
            elif value == QadMsg.translate("Command_ARC", "chord Length") or value == "chord Length":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_CENTER_PT_KNOWN_ASK_FOR_CHORD)
               # si appresta ad attendere un punto o un numero reale         
               # msg, inputType, default, keyWords, valori positivi
               self.waitFor(QadMsg.translate("Command_ARC", "Specify the chord length: "), \
                            QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                            None, "", \
                            QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO | QadInputModeEnum.NOT_NEGATIVE)
               self.step = 7
               return False                              
         elif type(value) == QgsPoint: # se é stato inserito il punto finale dell'arco
            self.endPt = value
                     
            arc = QadArc()         
            if arc.fromStartCenterEndPts(self.startPt, self.centerPt, self.endPt) == True:
               self.plugIn.setLastPoint(arc.getEndPt())
               points = arc.asPolyline()
               if points is not None:
                  # se i punti sono così vicini da essere considerati uguali
                  if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                     self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
                  else:
                     self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
                  
                  qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
                  return True # fine comando
            
            keyWords = QadMsg.translate("Command_ARC", "Angle") + "/" + \
                       QadMsg.translate("Command_ARC", "chord Length")
            prompt = QadMsg.translate("Command_ARC", "Specify the final point of the arc or [{0}]: ").format(keyWords)                 

            englishKeyWords = "Angle" + "/" + "chord Length"
            keyWords += "_" + englishKeyWords
            # si appresta ad attendere un punto o una parola chiave         
            # msg, inputType, default, keyWords, valori nulli non ammessi
            self.waitFor(prompt, \
                         QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                         None, \
                         keyWords, QadInputModeEnum.NOT_NULL)
            self.isValidPreviousInput = False # per gestire il comando anche in macro
            return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare angolo inscritto: " (da step = 5)
      elif self.step == 6: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint:
            self.angle = qad_utils.getAngleBy2Pts(self.centerPt, value)             
         else:
            self.angle = value

         arc = QadArc()         
         if arc.fromStartCenterPtsAngle(self.startPt, self.centerPt, self.angle) == True:
            self.plugIn.setLastPoint(arc.getEndPt())            
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
               
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando

         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, valori nulli non ammessi
         self.waitFor(QadMsg.translate("Command_ARC", "Specify the included angle: "), \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                      None, "", \
                      QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO)
         self.isValidPreviousInput = False # per gestire il comando anche in macro         
         return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare lunghezza della corda: " (da step = 5)
      elif self.step == 7: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint:
            self.chord = qad_utils.getDistance(self.startPt, value)             
         else:
            self.chord = value

         arc = QadArc()         
         if arc.fromStartCenterPtsChord(self.startPt, self.centerPt, self.chord) == True:
            self.plugIn.setLastPoint(arc.getEndPt())
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
               
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando

         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, valori positivi ammessi
         self.waitFor(QadMsg.translate("Command_ARC", "Specify the chord length: "), \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                      None, "", \
                      QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO | QadInputModeEnum.NOT_NEGATIVE)
         self.isValidPreviousInput = False # per gestire il comando anche in macro         
         return False
                 
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare punto finale dell'arco: " (da step = 1)
      elif self.step == 8: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.endPt = value
         self.plugIn.setLastPoint(self.endPt)

         # imposto il map tool
         self.getPointMapTool().arcEndPt = self.endPt
         self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_CENTER)
      
         keyWords = QadMsg.translate("Command_ARC", "Angle") + "/" + \
                    QadMsg.translate("Command_ARC", "Direction") + "/" + \
                    QadMsg.translate("Command_ARC", "Radius")
                    
         prompt = QadMsg.translate("Command_ARC", "Specify the center point of the arc or [{0}]: ").format(keyWords)                 

         englishKeyWords = "Angle" + "/" + "Direction" + "/" + "Radius"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere un punto o una parola chiave         
         # msg, inputType, default, keyWords, valori nulli non ammessi
         self.waitFor(prompt, \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                      None, \
                      keyWords, QadInputModeEnum.NOT_NULL)
         
         self.step = 9
         return False
         
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare centro dell'arco o [Angolo/Direzione/Raggio]: " (da step = 8)
      elif self.step == 9: # dopo aver atteso un punto o una parola chiave si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("Command_ARC", "Angle") or value == "Angle":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_ANGLE)
               # si appresta ad attendere un punto o un numero reale         
               # msg, inputType, default, keyWords, isNullable
               self.waitFor(QadMsg.translate("Command_ARC", "Specify the included angle: "), \
                            QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                            None, "", QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO)
               self.step = 10
               return False                              
            elif value == QadMsg.translate("Command_ARC", "Direction") or value == "Direction":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_TAN)
               # si appresta ad attendere un punto o un numero reale         
               # msg, inputType, default, keyWords, isNullable
               self.waitFor(QadMsg.translate("Command_ARC", "Specify the tangent direction for the start point of the arc: "), \
                            QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                            None, "", QadInputModeEnum.NOT_NULL)
               self.step = 11
               return False            
            elif value == QadMsg.translate("Command_ARC", "Radius") or value == "Radius":
               # imposto il map tool
               self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_END_PT_KNOWN_ASK_FOR_RADIUS)
               # si appresta ad attendere un punto o un numero reale         
               # msg, inputType, default, keyWords, isNullable
               self.waitFor(QadMsg.translate("Command_ARC", "Specify the radius of the arc: "), \
                            QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                            None, "", \
                            QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO | QadInputModeEnum.NOT_NEGATIVE)
               self.step = 12
               return False                              
         elif type(value) == QgsPoint: # se é stato inserito il centro dell'arco
            self.centerPt = value

            arc = QadArc()         
            if arc.fromStartCenterEndPts(self.startPt, self.centerPt, self.endPt) == True:
               self.plugIn.setLastPoint(arc.getEndPt())
               points = arc.asPolyline()
               if points is not None:
                  # se i punti sono così vicini da essere considerati uguali
                  if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                     self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
                  else:
                     self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
                  
                  qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
                  return True # fine comando
            
            keyWords = QadMsg.translate("Command_ARC", "Angle") + "/" + \
                       QadMsg.translate("Command_ARC", "Direction") + "/" + \
                       QadMsg.translate("Command_ARC", "Radius")
                       
            prompt = QadMsg.translate("Command_ARC", "Specify the center point of the arc or [{0}]: ").format(keyWords)                 
                      
            englishKeyWords = "Angle" + "/" + "Direction" + "/" + "Radius"
            keyWords += "_" + englishKeyWords
            # si appresta ad attendere un punto o una parola chiave         
            # msg, inputType, default, keyWords, isNullable
            self.waitFor(prompt, \
                         QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                         None, \
                         keyWords, QadInputModeEnum.NOT_NULL)
            self.isValidPreviousInput = False # per gestire il comando anche in macro                     
            return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare angolo inscritto: " (da step = 9)
      elif self.step == 10: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint:
            self.angle = qad_utils.getAngleBy2Pts(self.startPt, value)             
         else:
            self.angle = value
            
         arc = QadArc()         
         if arc.fromStartEndPtsAngle(self.startPt, self.endPt, self.angle) == True:
            self.plugIn.setLastPoint(arc.getEndPt())
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
               
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando

         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, valori non nulli
         self.waitFor(QadMsg.translate("Command_ARC", "Specify the included angle: "), \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                      None, "", \
                      QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO)
         self.isValidPreviousInput = False # per gestire il comando anche in macro         
         return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare direzione tangente per il punto iniziale dell'arco: " (da step = 9)
      elif self.step == 11: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint:
            self.angleTan = qad_utils.getAngleBy2Pts(self.startPt, value)             
         else:
            self.angleTan = value

         arc = QadArc()         
         if arc.fromStartEndPtsTan(self.startPt, self.endPt, self.angleTan) == True:
            self.plugIn.setLastPoint(arc.getEndPt())
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
               
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando

         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, isNullable
         self.waitFor(QadMsg.translate("Command_ARC", "Specify the tangent direction for the start point of the arc: "), \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.ANGLE, \
                      None, "", QadInputModeEnum.NOT_NULL)
         self.isValidPreviousInput = False # per gestire il comando anche in macro
         return False
      
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA "Specificare raggio dell'arco: " (da step = 9)
      elif self.step == 12: # dopo aver atteso un punto o un numero reale si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint:
            self.radius = qad_utils.getDistance(self.endPt, value)             
         else:
            self.radius = value

         self.plugIn.setLastRadius(self.radius)
         
         arc = QadArc()
         if arc.fromStartEndPtsRadius(self.startPt, self.endPt, self.radius) == True:
            self.plugIn.setLastPoint(arc.getEndPt())
            points = arc.asPolyline()
            if points is not None:
               # se i punti sono così vicini da essere considerati uguali
               if qad_utils.ptNear(self.startPt, arc.getStartPt()):
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnEndPt())
               else:
                  self.plugIn.setLastSegmentAng(arc.getTanDirectionOnStartPt() + math.pi)
               
               qad_layer.addLineToLayer(self.plugIn, currLayer, points)               
               return True # fine comando

         # si appresta ad attendere un punto o un numero reale         
         # msg, inputType, default, keyWords, valori positivi
         self.waitFor(QadMsg.translate("Command_ARC", "Specify the radius of the arc: "), \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.FLOAT, \
                      None, "", \
                      QadInputModeEnum.NOT_NULL | QadInputModeEnum.NOT_ZERO | QadInputModeEnum.NOT_NEGATIVE)
         self.isValidPreviousInput = False # per gestire il comando anche in macro
         return False

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA CENTRO DELL'ARCO (da step = 1)
      elif self.step == 13: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.centerPt = value
         self.plugIn.setLastPoint(value)

         # imposto il map tool
         self.getPointMapTool().arcCenterPt = self.centerPt
         self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.CENTER_PT_KNOWN_ASK_FOR_START_PT)

         # si appresta ad attendere un punto
         self.waitForPoint(QadMsg.translate("Command_ARC", "Specify the start point of the arc: "))
         self.step = 14
         
         return False


      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO INIZIALE DELL'ARCO (da step = 13)
      elif self.step == 14: # dopo aver atteso un punto si riavvia il comando
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  return True # fine comando
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         self.startPt = value
         self.plugIn.setLastPoint(value)

         # imposto il map tool
         self.getPointMapTool().arcStartPt = self.startPt
         self.getPointMapTool().setMode(Qad_arc_maptool_ModeEnum.START_CENTER_PT_KNOWN_ASK_FOR_END_PT)
         
         keyWords = QadMsg.translate("Command_ARC", "Angle") + "/" + \
                    QadMsg.translate("Command_ARC", "chord Length")
         
         prompt = QadMsg.translate("Command_ARC", "Specify the final point of the arc or [{0}]: ").format(keyWords)                 
                           
         englishKeyWords = "Angle" + "/" + "chord Length"
         keyWords += "_" + englishKeyWords
         # si appresta ad attendere un punto o una parola chiave         
         # msg, inputType, default, keyWords, isNullable
         self.waitFor(prompt, \
                      QadInputTypeEnum.POINT2D | QadInputTypeEnum.KEYWORDS, \
                      None, \
                      keyWords, QadInputModeEnum.NOT_NULL)
         
         self.step = 5
         return False
Example #16
0
   def run(self, msgMapTool = False, msg = None):
      if self.plugIn.canvas.mapRenderer().destinationCrs().geographicFlag():
         self.showMsg(QadMsg.translate("QAD", "\nThe coordinate reference system of the project must be a projected coordinate system.\n"))
         return True # fine comando
            
      #=========================================================================
      # RICHIESTA SELEZIONE OGGETTI
      if self.step == 0: # inizio del comando
         if self.entitySet.isEmpty(): # non ci sono oggetti da ruotare
            return True
         self.showMsg(QadMsg.translate("Command_GRIPMIRROR", "\n** MIRROR **\n"))
         # si appresta ad attendere il secondo punto di specchio
         self.waitForMirrorPoint()

      #=========================================================================
      # RISPOSTA ALLA RICHIESTA SECONDO PUNTO PER SPECCHIO
      elif self.step == 1: # dopo aver atteso un punto si riavvia il comando
         ctrlKey = False
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  value = None
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            ctrlKey = self.getPointMapTool().ctrlKey
            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == unicode:
            if value == QadMsg.translate("Command_GRIPMIRROR", "Base point") or value == "Base point":
               # si appresta ad attendere il punto base
               self.waitForBasePt()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "Copy") or value == "Copy":
               # Copia entità lasciando inalterate le originali
               self.copyEntities = True                     
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "Undo") or value == "Undo":
               if self.nOperationsToUndo > 0: 
                  self.nOperationsToUndo = self.nOperationsToUndo - 1
                  self.plugIn.undoEditCommand()
               else:
                  self.showMsg(QadMsg.translate("QAD", "\nThe command has been canceled."))                  
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
            elif value == QadMsg.translate("Command_GRIPMIRROR", "eXit") or value == "eXit":
               return True # fine comando
         elif type(value) == QgsPoint: # se é stato inserito il secondo punto
            if qad_utils.ptNear(self.basePt, value):
               self.showMsg(QadMsg.translate("Command_GRIPMIRROR", "\nThe points must be different."))
               # si appresta ad attendere il secondo punto di specchio
               self.waitForMirrorPoint()
               return False
            
            self.secondMirrorPt.set(value.x(), value.y())

            if ctrlKey:
               self.copyEntities = True

            self.mirrorGeoms()

            if self.copyEntities == False:
               return True

            # si appresta ad attendere il secondo punto di specchio
            self.waitForMirrorPoint()

         else:
            if self.copyEntities == False:
               self.skipToNextGripCommand = True
            return True # fine comando

         return False

              
      #=========================================================================
      # RISPOSTA ALLA RICHIESTA PUNTO BASE (da step = 1)
      elif self.step == 2: # dopo aver atteso un punto
         if msgMapTool == True: # il punto arriva da una selezione grafica
            # la condizione seguente si verifica se durante la selezione di un punto
            # é stato attivato un altro plugin che ha disattivato Qad
            # quindi stato riattivato il comando che torna qui senza che il maptool
            # abbia selezionato un punto            
            if self.getPointMapTool().point is None: # il maptool é stato attivato senza un punto
               if self.getPointMapTool().rightButton == True: # se usato il tasto destro del mouse
                  pass # opzione di default "spostamento"
               else:
                  self.setMapTool(self.getPointMapTool()) # riattivo il maptool
                  return False

            value = self.getPointMapTool().point
         else: # il punto arriva come parametro della funzione
            value = msg

         if type(value) == QgsPoint: # se é stato inserito il punto base
            self.basePt.set(value.x(), value.y())
            
         # si appresta ad attendere il secondo punto di specchio
         self.waitForMirrorPoint()

         return False
Example #17
0
File: qad_arc.py Project: gam17/QAD
   def fromPolyline(self, points, startVertex, atLeastNSegment = None):
      """
      setta le caratteristiche del primo arco incontrato nella lista di punti
      partendo dalla posizione startVertex (0-indexed)
      ritorna la posizione nella lista del punto iniziale e finale se é stato trovato un arco
      altrimenti None
      N.B. in punti NON devono essere in coordinate geografiche
      """
      if atLeastNSegment is None:
         _atLeastNSegment = QadVariables.get(QadMsg.translate("Environment variables", "ARCMINSEGMENTQTY"), 12)
      else:
         _atLeastNSegment = atLeastNSegment
      
      totPoints = len(points)
      # perché sia un    arco ci vogliono almeno _atLeastNSegment segmenti
      if (totPoints - 1) - startVertex < _atLeastNSegment or _atLeastNSegment < 2:
         return None
      
      # per problemi di approssimazione dei calcoli
      epsilon = 1.e-4 # percentuale del raggio per ottenere max diff. di una distanza con il raggio

      InfinityLinePerpOnMiddle1 = None
      InfinityLinePerpOnMiddle2 = None
                                  
      nSegment = 0
      i = startVertex
      while i < totPoints - 1:
         if InfinityLinePerpOnMiddle1 is None:
            InfinityLinePerpOnMiddle1 = qad_utils.getInfinityLinePerpOnMiddle(points[i], points[i + 1])
            nStartVertex = i
            nSegment = 1
            i = i + 1
            continue
         elif InfinityLinePerpOnMiddle2 is None:     
            InfinityLinePerpOnMiddle2 = qad_utils.getInfinityLinePerpOnMiddle(points[i], points[i + 1])
            if InfinityLinePerpOnMiddle2 is None:
               InfinityLinePerpOnMiddle1 = None
               nSegment = 0
            else:
               # calcolo il presunto centro con 2 segmenti
               center = qad_utils.getIntersectionPointOn2InfinityLines(InfinityLinePerpOnMiddle1[0], \
                                                                       InfinityLinePerpOnMiddle1[1], \
                                                                       InfinityLinePerpOnMiddle2[0], \
                                                                       InfinityLinePerpOnMiddle2[1])
               if center is None: # linee parallele
                  InfinityLinePerpOnMiddle1 = InfinityLinePerpOnMiddle2
                  InfinityLinePerpOnMiddle2 = None
                  nStartVertex = i
                  nSegment = 1
               else:
                  nSegment = nSegment + 1
                  radius = qad_utils.getDistance(center, points[i + 1]) # calcolo il presunto raggio
                  tolerance = radius * epsilon
                  
                  # calcolo il verso dell'arco e l'angolo dell'arco                 
                  # se un punto intermedio dell'arco è a sinistra del
                  # segmento che unisce i due punti allora il verso è antiorario
                  startClockWise = True if qad_utils.leftOfLine(points[i], points[i - 1], points[i + 1]) < 0 else False
                  angle = qad_utils.getAngleBy3Pts(points[i - 1], center, points[i + 1], startClockWise)
                  prevInfinityLinePerpOnMiddle = InfinityLinePerpOnMiddle2
         else: # e sono già stati valutati almeno 2 segmenti
            notInArc = False
            currInfinityLinePerpOnMiddle = qad_utils.getInfinityLinePerpOnMiddle(points[i], points[i + 1])
            if currInfinityLinePerpOnMiddle is None:
               notInArc = True
            else:
               # calcolo il presunto centro con 2 segmenti
               currCenter = qad_utils.getIntersectionPointOn2InfinityLines(prevInfinityLinePerpOnMiddle[0], \
                                                                           prevInfinityLinePerpOnMiddle[1], \
                                                                           currInfinityLinePerpOnMiddle[0], \
                                                                           currInfinityLinePerpOnMiddle[1])
               if currCenter is None: # linee parallele
                  notInArc = True
               else:
                  # calcolo il verso dell'arco e l'angolo                 
                  clockWise = True if qad_utils.leftOfLine(points[i], points[i - 1], points[i + 1]) < 0 else False           
                  angle = angle + qad_utils.getAngleBy3Pts(points[i], center, points[i + 1], startClockWise) 
                             
                  # se la distanza è così vicina a quella del raggio
                  # il verso dell'arco deve essere quello iniziale
                  # l'angolo dell'arco non può essere >= 360 gradi
                  if qad_utils.ptNear(center, currCenter, tolerance) and \
                     startClockWise == clockWise and \
                     angle < 2 * math.pi:                              
                     nSegment = nSegment + 1 # anche questo segmento fa parte dell'arco
                     prevInfinityLinePerpOnMiddle = currInfinityLinePerpOnMiddle
                  else:
                     notInArc = True

            # questo segmento non fa parte del cerchio
            if notInArc:
               # se sono stati trovati un numero sufficiente di segmenti successivi
               if nSegment >= _atLeastNSegment:
                  # se é un angolo giro e il primo punto = ultimo punto allora points é un cerchio
                  if qad_utils.doubleNear(angle, 2 * math.pi) and points[0] == points[-1]: 
                     return None
                  break
               else:
                  i = i - 2
                  InfinityLinePerpOnMiddle1 = None
                  InfinityLinePerpOnMiddle2 = None

         i = i + 1
                        
      # se sono stati trovati un numero sufficiente di segmenti successivi
      if nSegment >= _atLeastNSegment:
         nEndVertex = nStartVertex + nSegment
         # se il punto iniziale e quello finale non coincidono é un arco         
         if points[nStartVertex] != points[nEndVertex]:
            self.center = center
            self.radius = radius
                           
            # se il verso é orario
            if startClockWise:
               # inverto l'angolo iniziale con quello finale
               self.endAngle = qad_utils.getAngleBy2Pts(center, points[nStartVertex])
               self.startAngle = qad_utils.getAngleBy2Pts(center, points[nEndVertex])
            else:
               self.startAngle = qad_utils.getAngleBy2Pts(center, points[nStartVertex])
               self.endAngle = qad_utils.getAngleBy2Pts(center, points[nEndVertex])                    

            return nStartVertex, nEndVertex
         
      return None