RINGMesh  Version 5.0.0
A programming library for geological model meshes
mesh_entity_gfx.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2012-2017, Association Scientifique pour la Geologie et ses
3  * Applications (ASGA). All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  * * Redistributions of source code must retain the above copyright
8  * notice, this list of conditions and the following disclaimer.
9  * * Redistributions in binary form must reproduce the above copyright
10  * notice, this list of conditions and the following disclaimer in the
11  * documentation and/or other materials provided with the distribution.
12  * * Neither the name of ASGA nor the
13  * names of its contributors may be used to endorse or promote products
14  * derived from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
18  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL ASGA BE LIABLE FOR ANY DIRECT,
20  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  *
27  * http://www.ring-team.org
28  *
29  * RING Project
30  * Ecole Nationale Superieure de Geologie - GeoRessources
31  * 2 Rue du Doyen Marcel Roubault - TSA 70605
32  * 54518 VANDOEUVRE-LES-NANCY
33  * FRANCE
34  */
35 
42 
43 #ifdef RINGMESH_WITH_GRAPHICS
44 
49 
52 
53 namespace
54 {
55  using namespace RINGMesh;
56 
57  std::string get_attribute_name_with_coordinate(
58  const std::string& name, index_t coordinate )
59  {
60  return name + "[" + std::to_string( coordinate ) + "]";
61  }
62 
63  void compute_attribute_range(
64  GEO::ReadOnlyScalarAttributeAdapter& attribute,
65  double& min,
66  double& max )
67  {
68  if( attribute.is_bound() )
69  {
70  for( auto i : range( attribute.size() ) )
71  {
72  double value = attribute[i];
73  min = GEO::geo_min( min, value );
74  max = GEO::geo_max( max, value );
75  }
76  }
77  }
78 } // namespace
79 
80 namespace RINGMesh
81 {
82  template < index_t DIMENSION >
83  class CellAttributeGfx : public AttributeGfx< DIMENSION >
84  {
85  public:
86  CellAttributeGfx() = default;
87 
88  virtual ~CellAttributeGfx() = default;
89 
90  static std::string location_name_static()
91  {
92  return "cells";
93  }
94 
95  std::string location_name() const override
96  {
97  return location_name_static();
98  }
99 
100  void bind_attribute() override
101  {
102  std::string attribute_name = get_attribute_name_with_coordinate(
103  this->manager_->name(), this->manager_->coordinate() );
104  this->manager_->gfx().regions.set_scalar_attribute( GEO::MESH_CELLS,
105  attribute_name, this->manager_->minimum(),
106  this->manager_->maximum(), this->manager_->colormap() );
107  }
108 
109  void unbind_attribute() override
110  {
111  this->manager_->gfx().regions.unset_scalar_attribute();
112  }
113 
114  index_t nb_coordinates() override
115  {
116  GEO::AttributeStore* store =
117  get_attribute_manager().find_attribute_store(
118  this->manager_->name() );
119 
120  if( store == nullptr )
121  return 0;
122  return store->dimension();
123  }
124 
125  GEO::AttributesManager& get_attribute_manager() override
126  {
127  const GeoModel< DIMENSION >* geomodel =
128  this->manager_->gfx().geomodel();
129  return geomodel->region( 0 ).cell_attribute_manager();
130  }
131 
132  private:
133  void do_compute_range(
134  double& attribute_min, double& attribute_max ) override
135  {
136  std::string attribute_name = get_attribute_name_with_coordinate(
137  this->manager_->name(), this->manager_->coordinate() );
138  const GeoModel< DIMENSION >* geomodel =
139  this->manager_->gfx().geomodel();
140  for( const auto& region : geomodel->regions() )
141  {
142  GEO::ReadOnlyScalarAttributeAdapter attribute(
143  region.cell_attribute_manager(), attribute_name );
144  compute_attribute_range(
145  attribute, attribute_min, attribute_max );
146  }
147  }
148  };
149 
150  template < index_t DIMENSION >
151  class CellVertexAttributeGfx : public AttributeGfx< DIMENSION >
152  {
153  public:
154  CellVertexAttributeGfx() = default;
155 
156  virtual ~CellVertexAttributeGfx() = default;
157 
158  static std::string location_name_static()
159  {
160  return "cell_vertices";
161  }
162 
163  std::string location_name() const override
164  {
165  return location_name_static();
166  }
167 
168  void bind_attribute() override
169  {
170  std::string attribute_name = get_attribute_name_with_coordinate(
171  this->manager_->name(), this->manager_->coordinate() );
172  this->manager_->gfx().regions.set_scalar_attribute(
173  GEO::MESH_VERTICES, attribute_name, this->manager_->minimum(),
174  this->manager_->maximum(), this->manager_->colormap() );
175  }
176 
177  void unbind_attribute() override
178  {
179  this->manager_->gfx().regions.unset_scalar_attribute();
180  }
181 
182  index_t nb_coordinates() override
183  {
184  GEO::AttributeStore* store =
185  get_attribute_manager().find_attribute_store(
186  this->manager_->name() );
187 
188  if( store == nullptr )
189  return 0;
190  return store->dimension();
191  }
192 
193  GEO::AttributesManager& get_attribute_manager() override
194  {
195  const GeoModel< DIMENSION >* geomodel =
196  this->manager_->gfx().geomodel();
197  return geomodel->region( 0 ).vertex_attribute_manager();
198  }
199 
200  private:
201  void do_compute_range(
202  double& attribute_min, double& attribute_max ) override
203  {
204  std::string attribute_name = get_attribute_name_with_coordinate(
205  this->manager_->name(), this->manager_->coordinate() );
206  const GeoModel< DIMENSION >* geomodel =
207  this->manager_->gfx().geomodel();
208  for( const auto& region : geomodel->regions() )
209  {
210  GEO::ReadOnlyScalarAttributeAdapter attribute(
211  region.vertex_attribute_manager(), attribute_name );
212  compute_attribute_range(
213  attribute, attribute_min, attribute_max );
214  }
215  }
216  };
217 
218  template < index_t DIMENSION >
219  class PolygonAttributeGfx : public AttributeGfx< DIMENSION >
220  {
221  public:
222  PolygonAttributeGfx() = default;
223 
224  virtual ~PolygonAttributeGfx() = default;
225 
226  static std::string location_name_static()
227  {
228  return "polygon";
229  }
230 
231  std::string location_name() const override
232  {
233  return location_name_static();
234  }
235 
236  void bind_attribute() override
237  {
238  std::string attribute_name = get_attribute_name_with_coordinate(
239  this->manager_->name(), this->manager_->coordinate() );
240  this->manager_->gfx().surfaces.set_scalar_attribute(
241  GEO::MESH_FACETS, attribute_name, this->manager_->minimum(),
242  this->manager_->maximum(), this->manager_->colormap() );
243  }
244 
245  void unbind_attribute() override
246  {
247  this->manager_->gfx().surfaces.unset_scalar_attribute();
248  }
249 
250  index_t nb_coordinates() override
251  {
252  GEO::AttributeStore* store =
253  get_attribute_manager().find_attribute_store(
254  this->manager_->name() );
255 
256  if( store == nullptr )
257  return 0;
258  return store->dimension();
259  }
260 
261  GEO::AttributesManager& get_attribute_manager() override
262  {
263  const GeoModel< DIMENSION >* geomodel =
264  this->manager_->gfx().geomodel();
265  return geomodel->surface( 0 ).polygon_attribute_manager();
266  }
267 
268  private:
269  void do_compute_range(
270  double& attribute_min, double& attribute_max ) override
271  {
272  std::string attribute_name = get_attribute_name_with_coordinate(
273  this->manager_->name(), this->manager_->coordinate() );
274  const GeoModel< DIMENSION >* geomodel =
275  this->manager_->gfx().geomodel();
276  for( const auto& surface : geomodel->surfaces() )
277  {
278  GEO::ReadOnlyScalarAttributeAdapter attribute(
279  surface.polygon_attribute_manager(), attribute_name );
280  compute_attribute_range(
281  attribute, attribute_min, attribute_max );
282  }
283  }
284  };
285 
286  template < index_t DIMENSION >
287  class PolygonVertexAttributeGfx : public AttributeGfx< DIMENSION >
288  {
289  public:
290  PolygonVertexAttributeGfx() = default;
291 
292  virtual ~PolygonVertexAttributeGfx() = default;
293 
294  static std::string location_name_static()
295  {
296  return "polygon_vertices";
297  }
298 
299  std::string location_name() const override
300  {
301  return location_name_static();
302  }
303  void bind_attribute() override
304  {
305  std::string attribute_name = get_attribute_name_with_coordinate(
306  this->manager_->name(), this->manager_->coordinate() );
307  this->manager_->gfx().surfaces.set_scalar_attribute(
308  GEO::MESH_VERTICES, attribute_name, this->manager_->minimum(),
309  this->manager_->maximum(), this->manager_->colormap() );
310  }
311  void unbind_attribute() override
312  {
313  this->manager_->gfx().surfaces.unset_scalar_attribute();
314  }
315  index_t nb_coordinates() override
316  {
317  GEO::AttributeStore* store =
318  get_attribute_manager().find_attribute_store(
319  this->manager_->name() );
320 
321  if( store == nullptr )
322  return 0;
323  return store->dimension();
324  }
325 
326  GEO::AttributesManager& get_attribute_manager() override
327  {
328  const GeoModel< DIMENSION >* geomodel =
329  this->manager_->gfx().geomodel();
330  return geomodel->surface( 0 ).vertex_attribute_manager();
331  }
332 
333  private:
334  void do_compute_range(
335  double& attribute_min, double& attribute_max ) override
336  {
337  std::string attribute_name = get_attribute_name_with_coordinate(
338  this->manager_->name(), this->manager_->coordinate() );
339  const GeoModel< DIMENSION >* geomodel =
340  this->manager_->gfx().geomodel();
341  for( const auto& surface : geomodel->surfaces() )
342  {
343  GEO::ReadOnlyScalarAttributeAdapter attribute(
344  surface.vertex_attribute_manager(), attribute_name );
345  compute_attribute_range(
346  attribute, attribute_min, attribute_max );
347  }
348  }
349  };
350 
351  template < index_t DIMENSION >
352  AttributeGfxManagerBase< DIMENSION >::AttributeGfxManagerBase(
353  GeoModelGfx< DIMENSION >& gfx )
354  : gfx_( gfx )
355  {
356  register_attribute_location< PolygonVertexAttributeGfx >();
357  register_attribute_location< PolygonAttributeGfx >();
358  }
359 
360  template < index_t DIMENSION >
361  std::string AttributeGfxManagerBase< DIMENSION >::location_name() const
362  {
363  if( attribute_ )
364  {
365  return attribute_->location_name();
366  }
367  else
368  {
369  return "location";
370  }
371  }
372 
373  template < index_t DIMENSION >
374  void AttributeGfxManagerBase< DIMENSION >::compute_range()
375  {
376  if( attribute_ )
377  {
378  attribute_->compute_range();
379  }
380  }
381 
382  template < index_t DIMENSION >
383  void AttributeGfxManagerBase< DIMENSION >::bind_attribute()
384  {
385  if( attribute_ )
386  {
387  attribute_->bind_attribute();
388  }
389  }
390 
391  template < index_t DIMENSION >
392  std::vector< std::string >
393  AttributeGfxManagerBase< DIMENSION >::get_attribute_names()
394  {
395  if( attribute_ )
396  {
397  return attribute_->get_attribute_names();
398  }
399  return std::vector< std::string >();
400  }
401 
402  template < index_t DIMENSION >
403  void AttributeGfxManagerBase< DIMENSION >::unbind_attribute()
404  {
405  if( attribute_ )
406  {
407  attribute_->unbind_attribute();
408  }
409  }
410 
411  template < index_t DIMENSION >
412  index_t AttributeGfxManagerBase< DIMENSION >::nb_coordinates() const
413  {
414  if( attribute_ )
415  {
416  return attribute_->nb_coordinates();
417  }
418  return 0;
419  }
420 
421  AttributeGfxManager< 3 >::AttributeGfxManager( GeoModelGfx< 3 >& gfx )
422  : AttributeGfxManagerBase< 3 >( gfx )
423  {
424  this->register_attribute_location< CellVertexAttributeGfx >();
425  this->register_attribute_location< CellAttributeGfx >();
426  }
427 
428  template < index_t DIMENSION >
429  std::unique_ptr< PointSetMeshGfx< DIMENSION > >
430  PointSetMeshGfx< DIMENSION >::create_gfx(
431  const PointSetMesh< DIMENSION >& mesh )
432  {
433  auto gfx = PointSetMeshGfxFactory< DIMENSION >::create(
434  mesh.type_name(), mesh );
435  if( !gfx )
436  {
437  throw RINGMeshException( "PointSetMeshGfx",
438  "Could not create mesh gfx data structure: ",
439  mesh.type_name() );
440  }
441  return gfx;
442  }
443 
444  template < index_t DIMENSION >
445  std::unique_ptr< LineMeshGfx< DIMENSION > >
446  LineMeshGfx< DIMENSION >::create_gfx(
447  const LineMesh< DIMENSION >& mesh )
448  {
449  auto gfx =
450  LineMeshGfxFactory< DIMENSION >::create( mesh.type_name(), mesh );
451  if( !gfx )
452  {
453  throw RINGMeshException( "LineMeshGfx",
454  "Could not create mesh gfx data structure: ",
455  mesh.type_name() );
456  }
457  return gfx;
458  }
459 
460  template < index_t DIMENSION >
461  std::unique_ptr< SurfaceMeshGfx< DIMENSION > >
462  SurfaceMeshGfx< DIMENSION >::create_gfx(
463  const SurfaceMesh< DIMENSION >& mesh )
464  {
465  auto gfx = SurfaceMeshGfxFactory< DIMENSION >::create(
466  mesh.type_name(), mesh );
467  if( !gfx )
468  {
469  throw RINGMeshException( "SurfaceMeshGfx",
470  "Could not create mesh gfx data structure: ",
471  mesh.type_name() );
472  }
473  return gfx;
474  }
475 
476  template < index_t DIMENSION >
477  std::unique_ptr< VolumeMeshGfx< DIMENSION > >
478  VolumeMeshGfx< DIMENSION >::create_gfx(
479  const VolumeMesh< DIMENSION >& mesh )
480  {
481  auto gfx =
482  VolumeMeshGfxFactory< DIMENSION >::create( mesh.type_name(), mesh );
483  if( !gfx )
484  {
485  throw RINGMeshException( "VolumeMeshGfx",
486  "Could not create mesh gfx data structure: ",
487  mesh.type_name() );
488  }
489  return gfx;
490  }
491 
492  template std::unique_ptr< PointSetMeshGfx< 2 > > RINGMESH_API
493  PointSetMeshGfx< 2 >::create_gfx( const PointSetMesh< 2 >& );
494  template std::unique_ptr< LineMeshGfx< 2 > >
495  RINGMESH_API LineMeshGfx< 2 >::create_gfx( const LineMesh< 2 >& );
496  template std::unique_ptr< SurfaceMeshGfx< 2 > >
497  RINGMESH_API SurfaceMeshGfx< 2 >::create_gfx( const SurfaceMesh< 2 >& );
498  template class RINGMESH_API AttributeGfxManagerBase< 2 >;
499  template class RINGMESH_API AttributeGfxManager< 2 >;
500 
501  template std::unique_ptr< PointSetMeshGfx< 3 > > RINGMESH_API
502  PointSetMeshGfx< 3 >::create_gfx( const PointSetMesh< 3 >& );
503  template std::unique_ptr< LineMeshGfx< 3 > >
504  RINGMESH_API LineMeshGfx< 3 >::create_gfx( const LineMesh< 3 >& );
505  template std::unique_ptr< SurfaceMeshGfx< 3 > >
506  RINGMESH_API SurfaceMeshGfx< 3 >::create_gfx( const SurfaceMesh< 3 >& );
507  template std::unique_ptr< VolumeMeshGfx< 3 > >
508  RINGMESH_API VolumeMeshGfx< 3 >::create_gfx( const VolumeMesh< 3 >& );
509  template class RINGMESH_API AttributeGfxManagerBase< 3 >;
510 
511 } // namespace RINGMesh
512 
513 #endif
virtual MeshType type_name() const =0
const Surface< DIMENSION > & surface(index_t index) const
Definition: geomodel.cpp:192
Classes to build GeoModel from various inputs.
Definition: algorithm.h:48