00001 #ifndef DUNE_GENERICGEOMETRY_MAPPINGPROVIDER_HH
00002 #define DUNE_GENERICGEOMETRY_MAPPINGPROVIDER_HH
00003
00004 #include <dune/grid/genericgeometry/cachedmapping.hh>
00005 #include <dune/grid/genericgeometry/hybridmapping.hh>
00006
00007 namespace Dune
00008 {
00009
00010 namespace GenericGeometry
00011 {
00012
00013
00014
00015
00016 template< class Topology, class GeometryTraits >
00017 class CachedMappingFactory
00018 {
00019 typedef CachedMappingFactory< Topology, GeometryTraits > This;
00020
00021 public:
00022 typedef CachedMapping< Topology, GeometryTraits > Mapping;
00023
00024 template< class CoordVector >
00025 static Mapping *
00026 mapping ( const GeometryType &type, const CoordVector &coords )
00027 {
00028 assert( type.dim() == Mapping :: dimension );
00029 return new Mapping( coords );
00030 }
00031 };
00032
00033
00034
00035
00036
00037
00038 template< unsigned int dim, class GeometryTraits >
00039 class VirtualMappingFactory
00040 {
00041 typedef VirtualMappingFactory< dim, GeometryTraits > This;
00042
00043 public:
00044 typedef HybridMapping< dim, GeometryTraits > Mapping;
00045
00046 private:
00047 template< bool > struct AllTypes;
00048 template< bool > struct OnlySimplexCube;
00049
00050 template< GeometryType :: BasicType type, class CoordVector >
00051 static Mapping *virtualMapping ( const CoordVector &coords )
00052 {
00053 typedef typename Convert< type, dim > :: type Topology;
00054 return new VirtualMapping< Topology, GeometryTraits >( coords );
00055 }
00056
00057 public:
00058 template< class CoordVector >
00059 static Mapping *
00060 mapping ( const GeometryType &type, const CoordVector &coords )
00061 {
00062 assert( type.dim() == Mapping :: dimension );
00063 typedef ProtectedIf< (Mapping :: dimension >= 3), AllTypes, OnlySimplexCube > Switch;
00064 return Switch :: mapping( type.basicType(), coords );
00065 }
00066 };
00067
00068
00069 template< unsigned int dim, class GeometryTraits >
00070 template< bool >
00071 struct VirtualMappingFactory< dim, GeometryTraits > :: AllTypes
00072 {
00073 template< class CoordVector >
00074 static Mapping *
00075 mapping ( GeometryType :: BasicType type, const CoordVector &coords )
00076 {
00077 switch( type )
00078 {
00079 case GeometryType :: simplex:
00080 return virtualMapping< GeometryType :: simplex, CoordVector >( coords );
00081
00082 case GeometryType :: cube:
00083 return virtualMapping< GeometryType :: cube, CoordVector >( coords );
00084
00085 case GeometryType :: prism:
00086 return virtualMapping< GeometryType :: prism, CoordVector >( coords );
00087
00088 case GeometryType :: pyramid:
00089 return virtualMapping< GeometryType :: pyramid, CoordVector >( coords );
00090
00091 default:
00092 DUNE_THROW( RangeError, "Unknown basic geometry type: " << type );
00093 }
00094 }
00095 };
00096
00097
00098 template< unsigned int dim, class GeometryTraits >
00099 template< bool >
00100 struct VirtualMappingFactory< dim, GeometryTraits > :: OnlySimplexCube
00101 {
00102 template< class CoordVector >
00103 static Mapping *
00104 mapping ( GeometryType :: BasicType type, const CoordVector &coords )
00105 {
00106 switch( type )
00107 {
00108 case GeometryType :: simplex:
00109 return virtualMapping< GeometryType :: simplex, CoordVector >( coords );
00110
00111 case GeometryType :: cube:
00112 return virtualMapping< GeometryType :: cube, CoordVector >( coords );
00113
00114 default:
00115 DUNE_THROW( RangeError, "Unknown basic geometry type: " << type );
00116 }
00117 }
00118 };
00119
00120
00121
00122
00123
00124
00125
00126 template< class ElementMapping, unsigned int codim >
00127 class MappingProvider;
00128
00129
00130 template< unsigned int dim, class GeometryTraits, unsigned int codim >
00131 class MappingProvider< HybridMapping< dim, GeometryTraits >, codim >
00132 {
00133 typedef MappingProvider< HybridMapping< dim, GeometryTraits >, codim > This;
00134
00135 public:
00136 static const unsigned int dimension = dim;
00137 static const unsigned int codimension = codim;
00138 static const unsigned int mydimension = dimension - codimension;
00139
00140 private:
00141 typedef VirtualMappingFactory< mydimension, GeometryTraits > Factory;
00142
00143 public:
00144 typedef typename Factory :: Mapping Mapping;
00145
00146 template< class CoordVector >
00147 static Mapping *
00148 mapping ( const GeometryType &type, const CoordVector &coords )
00149 {
00150 return Factory :: mapping( type, coords );
00151 }
00152 };
00153
00154
00155 template< class Topology, class GeometryTraits, unsigned int codim >
00156 class MappingProvider< CachedMapping< Topology, GeometryTraits >, codim >
00157 {
00158 typedef MappingProvider< CachedMapping< Topology, GeometryTraits >, codim > This;
00159
00160 public:
00161 static const unsigned int dimension = Topology :: dimension;
00162 static const unsigned int codimension = codim;
00163 static const unsigned int mydimension = dimension - codimension;
00164
00165 static const bool hybrid = IsCodimHybrid< Topology, codim > :: value;
00166
00167 private:
00168 template< bool >
00169 struct HybridFactory
00170 : public VirtualMappingFactory< mydimension, GeometryTraits >
00171 {};
00172
00173 template< bool >
00174 struct NonHybridFactory
00175 : public CachedMappingFactory
00176 < typename SubTopology< Topology, codim, 0 > :: type, GeometryTraits >
00177 {};
00178
00179 typedef ProtectedIf< hybrid, HybridFactory, NonHybridFactory > Factory;
00180
00181 public:
00182 typedef typename Factory :: Mapping Mapping;
00183
00184 template< class CoordVector >
00185 static Mapping *
00186 mapping ( const GeometryType &type, const CoordVector &coords )
00187 {
00188 return Factory :: mapping( type, coords );
00189 }
00190 };
00191
00192 }
00193
00194 }
00195
00196 #endif