//======================================================================= //function : HasIntersection3 //purpose : Auxilare for HasIntersection() // find intersection point between triangle (P1,P2,P3) // and segment [PC,P] //======================================================================= static bool HasIntersection3(const gp_Pnt& P, const gp_Pnt& PC, gp_Pnt& Pint, const gp_Pnt& P1, const gp_Pnt& P2, const gp_Pnt& P3) { //cout<<"HasIntersection3"<<endl; //cout<<" PC("<<PC.X()<<","<<PC.Y()<<","<<PC.Z()<<")"<<endl; //cout<<" P("<<P.X()<<","<<P.Y()<<","<<P.Z()<<")"<<endl; //cout<<" P1("<<P1.X()<<","<<P1.Y()<<","<<P1.Z()<<")"<<endl; //cout<<" P2("<<P2.X()<<","<<P2.Y()<<","<<P2.Z()<<")"<<endl; //cout<<" P3("<<P3.X()<<","<<P3.Y()<<","<<P3.Z()<<")"<<endl; gp_Vec VP1(P1,P2); gp_Vec VP2(P1,P3); IntAna_Quadric IAQ(gp_Pln(P1,VP1.Crossed(VP2))); IntAna_IntConicQuad IAICQ(gp_Lin(PC,gp_Dir(gp_Vec(PC,P))),IAQ); if(IAICQ.IsDone()) { if( IAICQ.IsInQuadric() ) return false; if( IAICQ.NbPoints() == 1 ) { gp_Pnt PIn = IAICQ.Point(1); double preci = 1.e-6; // check if this point is internal for segment [PC,P] bool IsExternal = ( (PC.X()-PIn.X())*(P.X()-PIn.X()) > preci ) || ( (PC.Y()-PIn.Y())*(P.Y()-PIn.Y()) > preci ) || ( (PC.Z()-PIn.Z())*(P.Z()-PIn.Z()) > preci ); if(IsExternal) { return false; } // check if this point is internal for triangle (P1,P2,P3) gp_Vec V1(PIn,P1); gp_Vec V2(PIn,P2); gp_Vec V3(PIn,P3); if( V1.Magnitude()<preci || V2.Magnitude()<preci || V3.Magnitude()<preci ) { Pint = PIn; return true; } gp_Vec VC1 = V1.Crossed(V2); gp_Vec VC2 = V2.Crossed(V3); gp_Vec VC3 = V3.Crossed(V1); if(VC1.Magnitude()<preci) { if(VC2.IsOpposite(VC3,preci)) { return false; } } else if(VC2.Magnitude()<preci) { if(VC1.IsOpposite(VC3,preci)) { return false; } } else if(VC3.Magnitude()<preci) { if(VC1.IsOpposite(VC2,preci)) { return false; } } else { if( VC1.IsOpposite(VC2,preci) || VC1.IsOpposite(VC3,preci) || VC2.IsOpposite(VC3,preci) ) { return false; } } Pint = PIn; return true; } } return false; }
/* * ResidueMutate * * Author: Christian Schafmeister (1991) * * Mutate the RESIDUE (rOld) into the RESIDUE (rNew). * Do this by superimposing the coordinates from rOld onto * rNew, breaking all the bonds from rOld to other residues, * and rejoining them to identically named atoms in rNew, * then building the coordinates for the rest of the atoms in rNew. * The new RESIDUE rNew should not be bonded to anything else, it * should also have EXTERNAL coordinates defined, but no INTERNALS. * */ void ResidueMutate( RESIDUE rNew, RESIDUE rOld ) { LOOP lAtoms, lSpan; ATOM aNew, aNeighbor, aOld, aAtom, aSpan, aTemp; STRING sTemp, sSpan; int i, iDum; FLAGS fBondFlags; MESSAGE(( "Mutating: %s to: %s\n", sContainerName( rOld ), sContainerName(rNew) )); /* Build internal coordinates for the new RESIDUE */ lAtoms = lLoop( (OBJEKT)rNew, ATOMS ); BuildInternalsUsingFlags( &lAtoms, ATOMPOSITIONKNOWN, 0, 0, ATOMPOSITIONKNOWN, &iDum, &iDum, &iDum ); /* Define the coordinates, and the flags */ /* if there are bonds out of the old RESIDUE, break them */ /* and rejoin them to identically named atoms in the new */ /* RESIDUE */ lAtoms = lLoop( (OBJEKT)rOld, ATOMS ); FOREACH( aOld, ATOM, lAtoms ) { MESSAGE(( "Searching for atom in new residue with name: %s\n", sContainerName(aOld) )); aNew = (ATOM)cContainerFindName( (CONTAINER)rNew, ATOMid, sContainerName(aOld) ); /* If there is a cooresponding ATOM with the same name */ /* then define its flags and coordinates */ if ( aNew != NULL ) { MESSAGE(( "--- Found one\n" )); AtomSetPosition( aNew, vAtomPosition(aOld) ); AtomDefineFlags( aNew, fAtomFlags(aOld) ); } else { MESSAGE(( "--- No atom found\n" )); } /* Search for bonds out of the old RESIDUE */ for ( i=0; i<iAtomCoordination(aOld); i++ ) { aNeighbor = aAtomBondedNeighbor( aOld, i ); MESSAGE(( "--- Looking at neighbor: %s\n", sContainerFullDescriptor( (CONTAINER)aNeighbor, sTemp ) )); if ( rOld != (RESIDUE)cContainerWithin(aNeighbor) ) { fBondFlags = fAtomBondFlags( aOld, i ); AtomRemoveBond( aOld, aNeighbor ); MESSAGE(( "Removing a bond to: %s\n", sContainerFullDescriptor( (CONTAINER)aNeighbor, sTemp ) )); if ( aNew != NULL ) { MESSAGE(( "--- And rejoining it to: %s\n", sContainerFullDescriptor( (CONTAINER)aNew, sTemp ) )); AtomBondToFlags( aNew, aNeighbor, fBondFlags ); } else { MESSAGE(( "--- Not rejoining it to anything.\n" )); VP1(( "There is no atom in residue: %s with the name: %s.\n" )); VP1(( "--- No bond could be made to the missing atom.\n" )); } } } }