2 // ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
4 // + This file is part of enGrid. +
6 // + Copyright 2008,2009 Oliver Gloth +
8 // + enGrid is free software: you can redistribute it and/or modify +
9 // + it under the terms of the GNU General Public License as published by +
10 // + the Free Software Foundation, either version 3 of the License, or +
11 // + (at your option) any later version. +
13 // + enGrid is distributed in the hope that it will be useful, +
14 // + but WITHOUT ANY WARRANTY; without even the implied warranty of +
15 // + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +
16 // + GNU General Public License for more details. +
18 // + You should have received a copy of the GNU General Public License +
19 // + along with enGrid. If not, see <http://www.gnu.org/licenses/>. +
21 // ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
29 #include "egvtkobject.h"
31 #include <vtkUnstructuredGrid.h>
32 #include <vtkCellType.h>
33 #include <vtkSmartPointer.h>
37 #include <QListWidget>
41 class OperationThread
: public QThread
54 void setOperation(Operation
*an_op
) { op
= an_op
; };
64 ostream
& operator<<(ostream
&out
, stencil_t S
);
67 * This is the base class for all mesh operations.
68 * Operations will typically be triggered by a Qt event; the MainWindow
69 * object will call operator() with the current grid as parameter.
71 class Operation
: public EgVtkObject
74 friend class OperationThread
;
75 OperationThread thread
;
77 private: // static attributes
79 static QSet
<Operation
*> garbage_operations
;
81 private: // attributes
83 QVector
<vtkIdType
> nodes_map
;
84 QVector
<vtkIdType
> cells_map
;
93 protected: // attributes
95 vtkUnstructuredGrid
*grid
;
96 QVector
<vtkIdType
> cells
;
98 QVector
<vtkIdType
> nodes
;
100 QVector
<QSet
<int> > n2c
;
101 QVector
<QSet
<int> > n2n
;
102 QVector
<QVector
<int> > c2c
;
103 QVector
<bool> node_fixed
;
104 QVector
<bool> cell_fixed
;
106 protected: // methods
110 GuiMainWindow
* mainWindow();
111 virtual void operate() = 0;
116 virtual ~Operation();
119 void setGrid(vtkUnstructuredGrid
*ug
) { grid
= ug
; };
121 void setAllVolumeCells();
122 void setAllSurfaceCells();
123 vtkIdType
getNewNode(vtkIdType id_old_node
) { return nodes_map
[_nodes
[id_old_node
]] ; };
124 vtkIdType
getNewCell(vtkIdType id_old_cell
) { return cells_map
[_cells
[id_old_cell
]] ; };
125 void setNewNode(vtkIdType id_old_node
, vtkIdType id_new_node
) { nodes_map
[_nodes
[id_old_node
]] = id_new_node
; };
126 void setNewCell(vtkIdType id_old_cell
, vtkIdType id_new_cell
) { cells_map
[_cells
[id_old_cell
]] = id_new_cell
; };
127 void setGui() { gui
= true; };
128 OperationThread
& getThread() { return thread
; };
129 void enableAutoSet() { autoset
= true; };
130 void disableAutoSet() { autoset
= false; };
133 * Fill a QListWidget with all available boundary codes from a grid.
134 * @param lw The QListWidget to fill.
135 * @param grid The grid to use.
137 void populateBoundaryCodes(QListWidget
*lw
);
139 virtual void operator()();
141 template <class T
> void setCells(const T
&cls
);
142 template <class T
> void setNodes(const T
&nds
);
144 static void collectGarbage();
145 stencil_t
getStencil(vtkIdType id_cell1
, int j1
);
147 vtkIdType
getClosestNode(vtkIdType a_id_node
,vtkUnstructuredGrid
* a_grid
);
148 vtkIdType
getFarthestNode(vtkIdType a_id_node
,vtkUnstructuredGrid
* a_grid
);
150 bool SwapCells(vtkUnstructuredGrid
* a_grid
, stencil_t S
);
151 void quad2triangle(vtkUnstructuredGrid
* src
,vtkIdType quadcell
);
152 void quad2triangle(vtkUnstructuredGrid
* src
,vtkIdType quadcell
,vtkIdType MovingPoint
);
154 bool DeletePoint(vtkUnstructuredGrid
*src
, vtkIdType DeadNode
);
155 int NumberOfCommonPoints(vtkIdType node1
, vtkIdType node2
, bool& IsTetra
);
156 vtkIdType
FindSnapPoint(vtkUnstructuredGrid
*src
, vtkIdType DeadNode
);
157 bool EmptyVolume(vtkIdType DeadNode
, vtkIdType PSP
);
159 vec3_t
GetCenter(vtkIdType cellId
, double& R
);
163 void Operation::setCells(const T
&cls
)
165 cells
.resize(cls
.size());
166 qCopy(cls
.begin(), cls
.end(), cells
.begin());
167 getNodesFromCells(cells
, nodes
, grid
);
168 createCellMapping(cells
, _cells
, grid
);
169 createNodeMapping(nodes
, _nodes
, grid
);
170 createNodeToCell(cells
, nodes
, _nodes
, n2c
, grid
);
171 createNodeToNode(cells
, nodes
, _nodes
, n2n
, grid
);
172 createCellToCell(cells
, c2c
, grid
);
173 node_fixed
.fill(nodes
.size(), false);
174 cell_fixed
.fill(cells
.size(), false);
179 void Operation::setNodes(const T
&nds
)
181 nodes
.resize(nds
.size());
182 qCopy(nds
.begin(), nds
.end(), nodes
.begin());
183 createNodeMapping(nodes
, _nodes
, grid
);
185 for (vtkIdType id_cell
= 0; id_cell
< grid
->GetNumberOfCells(); ++id_cell
) {
186 vtkIdType
*pts
, N_pts
;
187 grid
->GetCellPoints(id_cell
, N_pts
, pts
);
188 for (int i_pts
= 0; i_pts
< N_pts
; ++i_pts
) {
189 if (_nodes
[pts
[i_pts
]] >= 0) {
195 cells
.resize(cls
.size());
196 qCopy(cls
.begin(), cls
.end(), cells
.begin());
197 createCellMapping(cells
, _cells
, grid
);
198 createNodeToCell(cells
, nodes
, _nodes
, n2c
, grid
);
199 createNodeToNode(cells
, nodes
, _nodes
, n2n
, grid
);
200 createCellToCell(cells
, c2c
, grid
);
201 node_fixed
.fill(nodes
.size(), false);
202 cell_fixed
.fill(cells
.size(), false);
206 //////////////////////////////////////////////
207 double CurrentVertexAvgDist(vtkIdType a_vertex
,QVector
< QSet
< int > > &n2n
,vtkUnstructuredGrid
*a_grid
);
208 double CurrentMeshDensity(vtkIdType a_vertex
,QVector
< QSet
< int > > &n2n
,vtkUnstructuredGrid
*a_grid
);
209 double DesiredVertexAvgDist(vtkIdType a_vertex
,QVector
< QSet
< int > > &n2n
,vtkUnstructuredGrid
*a_grid
);
210 double DesiredMeshDensity(vtkIdType a_vertex
,QVector
< QSet
< int > > &n2n
,vtkUnstructuredGrid
*a_grid
);