private void _Inicializa() { Minimos = new Punto(); Maximos = new Punto(); }
public double Distancia(Punto Pto) { double Res = Math.Sqrt(Math.Pow(this.X - Pto.X, 2) + Math.Pow(this.Y - Pto.Y, 2) + Math.Pow(this.Z - Pto.Z, 2)); return(double.Parse(Res.ToString())); }
public bool EsInterior(Punto Pto) { //variación del windingnumber solo teniendo en cuenta el cambio de cuadrante bool Res = false; if (this._Puntos.Count > 2) { int CuadranteAnterior = 0, CuadranteActual = 0, ConteoCuadrantes = 0; IList <Punto> _Borde_ = new List <Punto>(); foreach (Punto p in this._Puntos) { _Borde_.Add(p); } _Borde_.Add(this._Puntos[0]);//repite contra el primero Punto pAnt = new Punto(); foreach (Punto p in _Borde_) { CuadranteActual = _Cuadrante(Pto, p); if (CuadranteAnterior == 0) { //evita que el primer cálculo cuente como salto de cuadrante; CuadranteAnterior = CuadranteActual; } if (CuadranteActual != 0 && CuadranteActual != CuadranteAnterior) { //evalúa si se suman pasos por cuadrantes o se restan int SaltoCuadrantes = CuadranteActual - CuadranteAnterior; if (SaltoCuadrantes == 1 || SaltoCuadrantes == -1) { //paso a un cuadrante adyacente if (SaltoCuadrantes > 0) { ConteoCuadrantes += SaltoCuadrantes; } } else if (SaltoCuadrantes == 2 || SaltoCuadrantes == -2) { //Evalúa si el salto de dos cuadrantes se realiza en sentido horario (-) o no (+); int SignoSalto = Segmento.Lado(pAnt, p, Pto); if (SignoSalto == 0) { //el punto se encuentra en la frontera del polígono Res = true; break; } else { ConteoCuadrantes += SignoSalto * 2; } } else if (SaltoCuadrantes == 3 || SaltoCuadrantes == -3) { //salto entre el cuadrante 4 y el 1 //se invierte el SaltoCuadrante ConteoCuadrantes -= SaltoCuadrantes / 3; } } else { //puntos coincidentes o en el mismo cuadrante se omiten //pertenece al polígono Res = true; break; } pAnt = p; } if (!Res) { //evalua si se ha producido una revolución if (ConteoCuadrantes >= 4 || ConteoCuadrantes <= -4) { Res = true; } /*else * { * Res = false; * }*/ } /*else * { * //salida forzada porcoincidencia etre punto y vértice * Res = true; * }*/ } return(Res); }
public IList <Segmento> SegmentosInteriores(Segmento Rayo, bool Invertido = false) { IList <Segmento> Res = new List <Segmento>(); IList <Punto> TempCortes = new List <Punto>(); Punto pAnt = this._Puntos.Last <Punto>(); //añado el punto inicial y final si se encuentran dentro del polígono if (this.EsInterior(Rayo.Inicio)) { TempCortes.Add(Rayo.Inicio); } if (this.EsInterior(Rayo.Final)) { TempCortes.Add(Rayo.Final); } foreach (Punto p in this._Puntos) { Segmento s = new Segmento(pAnt, p); Punto TempPto = new Punto(); //calcula el corte real con el borde if (s.Corta(Rayo, out TempPto)) { if (!TempCortes.Contains <Punto>(TempPto)) { TempCortes.Add(TempPto); } } pAnt = p; } //TODO: //ordeno en función de la distancia a Rayo.Inicio TempCortes = TempCortes.OrderBy <Punto, double>(p => p.Distancia(Rayo.Inicio)).ToList <Punto>(); //con TempCortes voy generando segmentos por pares y evaluando si el punto medio se encuentra dentro o no del polígono for (int p = 1; p < TempCortes.Count; p++) { bool Añadir = false; if (this.EsInterior(new Punto((TempCortes[p].X + TempCortes[p - 1].X) / 2.0, (TempCortes[p].Y + TempCortes[p - 1].Y) / 2.0, (TempCortes[p].Z + TempCortes[p - 1].Z) / 2.0))) { if (!Invertido)//lo añado { Añadir = true; } } else { if (Invertido)//lo añado { Añadir = true; } } if (Añadir) { Res.Add(new Segmento(TempCortes[p - 1], TempCortes[p])); } } return(Res); }
public void AddPunto(int Indice, Punto Punto) { _area = double.NaN; //ya no es válido cualquier valor anterior del área. _Puntos.Insert(Indice, Punto); Bownding.Actualizar(Punto); }