HyperspaceExplorer 0.7.1
|
00001 /* 00002 Hyperspace Explorer - visualizing higher-dimensional geometry 00003 Copyright (C) 2010 Lene Preuss <lene.preuss@gmail.com> 00004 00005 This program is free software; you can redistribute it and/or modify 00006 it under the terms of the GNU General Public License as published by 00007 the Free Software Foundation; either version 2 of the License, or 00008 (at your option) any later version. 00009 00010 This program is distributed in the hope that it will be useful, 00011 but WITHOUT ANY WARRANTY; without even the implied warranty of 00012 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00013 GNU General Public License for more details. 00014 00015 You should have received a copy of the GNU General Public License along 00016 with this program; if not, write to the Free Software Foundation, Inc., 00017 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 00018 00019 */ 00020 00021 #ifndef CUSTOMFUNCTION_H 00022 #define CUSTOMFUNCTION_H 00023 00024 #include <dlfcn.h> 00025 00026 #include "Displayable.h" 00027 #include "RealFunction.h" 00028 #include "Surface/ComplexFunction.h" 00029 #include "Surface/Surface.h" 00030 00031 #include <QString> 00032 00033 class QString; 00035 00040 template<class function_type> 00041 class CustomFunctionBase { 00042 public: 00043 CustomFunctionBase(): handle (NULL) {} 00045 ~CustomFunctionBase() { if (handle) dlclose (handle); } 00046 QString symbolic () const; 00047 00049 bool isValid() const { return valid; } 00050 00051 protected: 00052 bool loadFunction (const QString &, QString = "f"); 00053 00055 void setValid() { valid = true; } 00057 void setInvalid() { valid = false; } 00058 00060 function_type *func; 00061 00062 private: 00063 void *handle; 00064 bool valid; 00065 }; 00066 00068 00069 class CustomFunction: 00070 public RealFunction, 00071 public CustomFunctionBase<RealFunction::raw_function_type> { 00072 public: 00073 CustomFunction (double _tmin, double _tmax, double _dt, 00074 double _umin, double _umax, double _du, 00075 double _vmin, double _vmax, double _dv, 00076 bool final = true); 00077 virtual ~CustomFunction() { } 00078 00079 virtual std::string getFunctionName() const; 00080 00081 protected: 00082 virtual RealFunction::function_type f; 00083 }; 00084 00086 00089 class CustomPolarFunction: public CustomFunction { 00090 public: 00091 CustomPolarFunction (double _tmin, double _tmax, double _dt, 00092 double _umin, double _umax, double _du, 00093 double _vmin, double _vmax, double _dv); 00094 virtual ~CustomPolarFunction() { } 00095 00096 virtual std::string getFunctionName() const; 00097 00098 protected: 00099 virtual RealFunction::function_type f; 00100 }; 00101 00103 00104 class CustomSurface: 00105 public Surface, 00106 public CustomFunctionBase<Surface::raw_function_type> { 00107 public: 00108 CustomSurface (double _umin, double _umax, double _du, 00109 double _vmin, double _vmax, double _dv); 00110 virtual ~CustomSurface() { } 00111 00112 virtual std::string getFunctionName() const; 00113 00114 protected: 00115 virtual Surface::function_type f; 00116 }; 00117 00119 00120 class CustomComplexFunction: 00121 public ComplexFunction, 00122 public CustomFunctionBase<ComplexFunction::function_type> { 00123 00124 public: 00125 00126 CustomComplexFunction (): ComplexFunction() { } 00127 CustomComplexFunction (double _umin, double _umax, double _du, 00128 double _vmin, double _vmax, double _dv); 00129 virtual ~CustomComplexFunction() { } 00130 00131 virtual std::string getFunctionName() const; 00132 00133 protected: 00134 ComplexFunction::function_type g; 00135 }; 00136 00137 namespace { 00138 Displayable *createcustomcomplexfunction() { return new CustomComplexFunction(); } 00140 const bool registeredustomcomplexfunction = true; 00141 // TheFunctionFactory::Instance().registerFunction(createcustomcomplexfunction, "ComplexFunction"); 00142 } 00143 00148 template<class function_type> 00149 bool CustomFunctionBase<function_type>::loadFunction(const QString &libName, QString funcName) { 00150 const char *error; 00151 00152 handle = dlopen (libName.toStdString().c_str(), RTLD_LAZY); 00153 if (!handle) { 00154 std::cerr << "Error opening library: " << dlerror() << std::endl; 00155 return false; 00156 } 00157 00158 func = (function_type *)dlsym(handle, funcName.toStdString().c_str()); 00159 if ((error = dlerror()) != NULL) { 00160 std::cerr << "Error finding function: " << error << std::endl; 00161 return false; 00162 } 00163 00164 return true; 00165 } 00166 00168 template<class function_type> 00169 QString CustomFunctionBase<function_type>::symbolic () const { 00170 typedef char* STRING; 00171 STRING (*sym)(); 00172 sym = (STRING (*)())dlsym(handle, "symbolic"); 00173 const char *error; 00174 static char *ret; 00175 00176 if ((error = dlerror()) != NULL) { 00177 std::cerr << "Error finding symbolic description in " << error << std::endl; 00178 return QString ("something"); 00179 } 00180 ret=(*sym)(); 00181 return QString (ret); 00182 } 00183 00184 #endif