summaryrefslogtreecommitdiff
path: root/src/TopOpeBRepDS/TopOpeBRepDS_TOOL.cxx
blob: 20b520adb36f7a1966c06b192aa4a963c5f32104 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
// File:	TopOpeBRepDS_TOOL.cxx
// Created:	Mon Jan 25 14:33:44 1999
// Author:      Xuan PHAM PHU
//		<xpu@poulopox.paris1.matra-dtv.fr>


#include <TopoDS.hxx>
#include <TopExp_Explorer.hxx>
#include <BRep_Tool.hxx>
#include <TopOpeBRepTool_EXPORT.hxx>
#include <TopOpeBRepTool_TOOL.hxx>
#include <TopOpeBRepDS.hxx>
#include <TopOpeBRepDS_TOOL.ixx>
#include <TopOpeBRepDS_define.hxx>
#include <TopOpeBRepDS_ProcessInterferencesTool.hxx>
#include <TopOpeBRepDS_ListOfShapeOn1State.hxx>
#include <TopOpeBRepDS_DataMapOfShapeListOfShapeOn1State.hxx>

static void FUN_Raise()
{
#ifdef DEB
  cout<<"****************************** TopOpeBRepDS_TOOL"<<endl;
#endif
}

#define M_REVERSED(O) (O == TopAbs_REVERSED) 

static void FDS_sortGb(const Handle(TopOpeBRepDS_HDataStructure)& HDS,const TopOpeBRepDS_ListOfInterference& LI, TopOpeBRepDS_ListOfInterference& LIGb0,TopOpeBRepDS_ListOfInterference& LIGb1,TopOpeBRepDS_ListOfInterference& LIGbsd)
{
  const TopOpeBRepDS_DataStructure& BDS = HDS->DS();
  LIGb0.Clear(); LIGb1.Clear(); LIGbsd.Clear();
  TopOpeBRepDS_ListIteratorOfListOfInterference it(LI);
  for (; it.More(); it.Next()){
    const Handle(TopOpeBRepDS_Interference)& I = it.Value();
    Handle(TopOpeBRepDS_ShapeShapeInterference) SSI = Handle(TopOpeBRepDS_ShapeShapeInterference)::DownCast(I);
    if (SSI.IsNull()) {LIGb0.Append(I);continue;}

    Standard_Boolean gb1 = SSI->GBound();
    Standard_Integer G = I->Geometry();
    Standard_Boolean hsd = HDS->HasSameDomain(BDS.Shape(G));
    if (hsd)          {LIGbsd.Append(I);continue;}

    if (gb1) LIGb1.Append(I);
    else     LIGb0.Append(I);                    
  }//it(LI)  
}

//=======================================================================
//function : EShareG
//purpose  : 
//=======================================================================

#define FORWARD  (1)
#define REVERSED (2)
#define INTERNAL (3)
#define EXTERNAL (4)
#define CLOSING  (5)
Standard_Integer TopOpeBRepDS_TOOL::EShareG(const Handle(TopOpeBRepDS_HDataStructure)& HDS,const TopoDS_Edge& E,TopTools_ListOfShape& lEsd)
{
  lEsd.Clear();
  Standard_Boolean dgE = BRep_Tool::Degenerated(E);
  if (dgE) {
    Standard_Boolean hsd = HDS->HasSameDomain(E);
    if (!hsd) return 0;
    TopTools_ListIteratorOfListOfShape itsd(HDS->SameDomain(E));
    for (; itsd.More(); itsd.Next()) lEsd.Append(itsd.Value());
    return lEsd.Extent();
  }

  const TopOpeBRepDS_DataStructure& BDS = HDS->DS();
  const TopOpeBRepDS_ListOfInterference& LI = BDS.ShapeInterferences(E);
  TopOpeBRepDS_ListOfInterference LII; FDS_copy(LI,LII); 
  TopOpeBRepDS_ListOfInterference L1d; Standard_Integer n1d = FUN_selectTRASHAinterference(LII,TopAbs_EDGE,L1d);
  if (n1d == 0) return 0;
  
  TopTools_MapOfShape mapesd;
  TopOpeBRepDS_ListOfInterference l1gb0,l1gb1,l1gbsd; FDS_sortGb(HDS,L1d,l1gb0,l1gb1,l1gbsd);
#ifdef DEB
//  Standard_Integer ngb0 = l1gb0.Extent();
//  Standard_Integer ngb1 = l1gb1.Extent();
//  Standard_Integer ngbsd = l1gbsd.Extent();
#endif

  TopOpeBRepDS_ListIteratorOfListOfInterference it0(l1gb0);
  for (; it0.More(); it0.Next()) mapesd.Add(BDS.Shape(it0.Value()->Support()));        

  TopOpeBRepDS_ListIteratorOfListOfInterference it1(l1gb1);
  for (; it1.More(); it1.Next()) mapesd.Add(BDS.Shape(it1.Value()->Support()));        

  TopOpeBRepDS_ListIteratorOfListOfInterference itsd(l1gbsd);
  for (; itsd.More(); itsd.Next()) {
    const Handle(TopOpeBRepDS_Interference)& I = itsd.Value();
    const TopoDS_Edge& Esd = TopoDS::Edge(BDS.Shape(I->Support()));
    Standard_Boolean isb = mapesd.Contains(Esd);
    if (isb) continue;

    Standard_Integer G = I->Geometry();
    const TopoDS_Vertex& vG = TopoDS::Vertex(BDS.Shape(G));
    TopoDS_Vertex vsd; Standard_Boolean ok = FUN_ds_getoov(vG,BDS,vsd);
    if (!ok) {FUN_Raise(); continue;}
    Standard_Boolean Gb1 = Handle(TopOpeBRepDS_ShapeShapeInterference)::DownCast(I)->GBound();
    TopoDS_Vertex vE   = Gb1 ? vG : vsd;
    TopoDS_Vertex vEsd = Gb1 ? vsd : vG;

    Standard_Integer ovE; gp_Vec tgE; 
    ok = TopOpeBRepTool_TOOL::TgINSIDE(vE,E,tgE,ovE);
    if (!ok) continue;
    Standard_Integer ovEsd; gp_Vec tgEsd; 
    ok = TopOpeBRepTool_TOOL::TgINSIDE(vEsd,Esd,tgEsd,ovEsd);
    if (!ok) continue;
    Standard_Boolean inE   = (ovE == CLOSING)||(ovE == INTERNAL);
    Standard_Boolean inEsd = (ovEsd == CLOSING)||(ovEsd == INTERNAL);
    if (inE || inEsd) {mapesd.Add(Esd); continue;}
    Standard_Real dot = gp_Dir(tgE).Dot(gp_Dir(tgEsd));
    if (dot > 0.)      mapesd.Add(Esd);  
  }
  TopTools_MapIteratorOfMapOfShape itm(mapesd);
  for (; itm.More(); itm.Next()) lEsd.Append(itm.Key());
  return (lEsd.Extent());
}



//=======================================================================
//function : ShareG
//purpose  : 
//=======================================================================

Standard_Boolean TopOpeBRepDS_TOOL::ShareG(const Handle(TopOpeBRepDS_HDataStructure)& HDS, const Standard_Integer i1, const Standard_Integer i2)
{
  const TopoDS_Shape& s1 = HDS->Shape(i1);
  const TopoDS_Shape& s2 = HDS->Shape(i2);

  Standard_Boolean hsd1 = HDS->HasSameDomain(s1);
  if (!hsd1) return Standard_False;
  TopTools_ListIteratorOfListOfShape it1(HDS->SameDomain(s1));
  for (; it1.More(); it1.Next()){
    Standard_Boolean same = it1.Value().IsSame(s2);
    if (!same) continue;
    return Standard_True;
  }
  return Standard_False;
}



//=======================================================================
//function : GetEsd
//purpose  : 
//=======================================================================

Standard_Boolean TopOpeBRepDS_TOOL::GetEsd(const Handle(TopOpeBRepDS_HDataStructure)& HDS,
			      const TopoDS_Shape& S, const Standard_Integer ie, Standard_Integer& iesd)
{
  // recall : method ::SameDomain(s) returns an iterator on the list of shapes
  //          sdm to s (ie actually sharing geometric domain with s)
  iesd = 0;
  TopTools_MapOfShape mesdS;
  TopExp_Explorer ex(S, TopAbs_EDGE);
  for (; ex.More(); ex.Next()){
    const TopoDS_Shape& e = ex.Current();
    Standard_Boolean hs = HDS->HasShape(e);
    if (!hs) continue;
    Standard_Boolean hsd = HDS->HasSameDomain(e);
    if (!hsd) continue;
    mesdS.Add(e);
//    TopTools_ListIteratorOfListOfShape itt(HDS->SameDomain(e));
//    for (; itt.More(); itt.Next()) mesdS.Add(itt.Value());
  }

  TopTools_ListIteratorOfListOfShape it(HDS->SameDomain(HDS->Shape(ie)));
  for (; it.More(); it.Next()){
    const TopoDS_Shape& esd = it.Value();
    Standard_Boolean isb = mesdS.Contains(esd);
    if (!isb) continue;
    iesd = HDS->Shape(esd);
    return Standard_True;
  }
  return Standard_False;
}

//=======================================================================
//function : ShareSplitON
//purpose  : 
//=======================================================================

Standard_Boolean TopOpeBRepDS_TOOL::ShareSplitON(const Handle(TopOpeBRepDS_HDataStructure)& HDS,
				    const TopOpeBRepDS_DataMapOfShapeListOfShapeOn1State& MEspON,
				    const Standard_Integer i1, const Standard_Integer i2, TopoDS_Shape& spON)
{  
  spON.Nullify();
  Standard_Boolean shareg = TopOpeBRepDS_TOOL::ShareG(HDS,i1,i2);
  if (!shareg) return Standard_False;

  const TopoDS_Shape& s1 = HDS->Shape(i1);
  const TopoDS_Shape& s2 = HDS->Shape(i2);

  const TopOpeBRepDS_ListOfShapeOn1State& los1 = MEspON.Find(s1);
  Standard_Boolean issp = los1.IsSplit();
  if (!issp) return Standard_False;
  const TopTools_ListOfShape& lsp1 = los1.ListOnState();
  Standard_Integer nsp1 = lsp1.Extent();
  if (nsp1 == 0) return Standard_False;
  TopTools_MapOfShape mesp1; // map of splits on of <s1>
  TopTools_ListIteratorOfListOfShape it(lsp1);
  for (; it.More(); it.Next()) mesp1.Add(it.Value());

  const TopOpeBRepDS_ListOfShapeOn1State& los2 = MEspON.Find(s2);
  Standard_Boolean issp2 = los2.IsSplit();
  if (!issp2) return Standard_False;
  const TopTools_ListOfShape& lsp2 = los2.ListOnState();
  Standard_Integer nsp2 = lsp2.Extent();
  if (nsp2 == 0) return Standard_False;  

  it.Initialize(lsp2);
  for (; it.More(); it.Next()) {
    const TopoDS_Shape& esp = it.Value();
    Standard_Boolean isb = mesp1.Contains(esp);
    if (!isb) continue;
    spON = esp; return Standard_True;
  }
  return Standard_False;   
}



//=======================================================================
//function : GetConfig
//purpose  : returns relative geometric config
//=======================================================================
#define SAMEORIENTED (1)
#define DIFFORIENTED (2)
Standard_Boolean TopOpeBRepDS_TOOL::GetConfig(const Handle(TopOpeBRepDS_HDataStructure)& HDS,
				 const TopOpeBRepDS_DataMapOfShapeListOfShapeOn1State& MEspON,
				 const Standard_Integer ie,const Standard_Integer iesd,
				 Standard_Integer& config)
{
  config = 0;
  Standard_Boolean shareg = TopOpeBRepDS_TOOL::ShareG(HDS,ie,iesd);
  if (!shareg) return Standard_False;

  const TopoDS_Edge& e = TopoDS::Edge(HDS->Shape(ie));     TopAbs_Orientation oe = e.Orientation();
  const TopoDS_Edge& esd = TopoDS::Edge(HDS->Shape(iesd)); TopAbs_Orientation oesd = esd.Orientation();
  TopOpeBRepDS_Config conf = HDS->SameDomainOrientation(e); Standard_Boolean unsh = (conf == TopOpeBRepDS_UNSHGEOMETRY);
  TopOpeBRepDS_Config confsd = HDS->SameDomainOrientation(esd); Standard_Boolean unshsd = (confsd == TopOpeBRepDS_UNSHGEOMETRY);
  if (!unsh && !unshsd) {
    Standard_Boolean sameori = (conf == confsd);
    if (M_REVERSED(oe))   sameori = !sameori;
    if (M_REVERSED(oesd)) sameori = !sameori;
    config = sameori ? SAMEORIENTED : DIFFORIENTED;
    return Standard_True;
  }

  TopoDS_Shape eON; shareg = TopOpeBRepDS_TOOL::ShareSplitON(HDS,MEspON,ie,iesd,eON);
  if (!shareg) return Standard_False;

  Standard_Real f,l; FUN_tool_bounds(TopoDS::Edge(eON),f,l);
  Standard_Real x = 0.45678; Standard_Real parON = (1-x)*f+x*l;
  Standard_Real tole = BRep_Tool::Tolerance(TopoDS::Edge(e));
  Standard_Real pare; Standard_Boolean ok = FUN_tool_parE(TopoDS::Edge(eON),parON, e,pare, tole);
  if (!ok) return Standard_False;
  Standard_Real tolesd = BRep_Tool::Tolerance(TopoDS::Edge(esd));
  Standard_Real paresd; ok = FUN_tool_parE(TopoDS::Edge(eON),parON, esd,paresd, tolesd);
  if (!ok) return Standard_False;
  Standard_Boolean so; ok = FUN_tool_curvesSO(e,pare,esd,paresd,so);
  if (!ok) return Standard_False;
  config = (so)? SAMEORIENTED : DIFFORIENTED;  
  return Standard_True;
}