[Debian-astro-commits] [gyoto] 192/221: + Add Gyoto::Object::get/set(std::string const &property_name ...) + Gyoto::Value::operator [unsigned] long() work also if the other type of long was set + Python: * bugfix: avoid segfault when outputting a NULL SmartPointer; * new typemaps around Gyoto::Value
Thibaut Jean-Claude Paumard
thibaut at moszumanska.debian.org
Fri May 22 20:52:45 UTC 2015
This is an automated email from the git hooks/post-receive script.
thibaut pushed a commit to branch master
in repository gyoto.
commit da505ec0da17ad3dc8507dca3261819ed1d6c74d
Author: Thibaut Paumard <paumard at users.sourceforge.net>
Date: Wed Jan 14 12:52:05 2015 +0100
+ Add Gyoto::Object::get/set(std::string const &property_name ...)
+ Gyoto::Value::operator [unsigned] long() work also if the other type of long was set
+ Python:
* bugfix: avoid segfault when outputting a NULL SmartPointer;
* new typemaps around Gyoto::Value
---
include/GyotoObject.h | 12 ++++
lib/Object.C | 32 +++++++++
lib/Value.C | 28 +++++++-
python/example.py | 14 ++--
python/gyoto.i | 186 ++++++++++++++++++++++++++++++++++++++++++++++++--
5 files changed, 257 insertions(+), 15 deletions(-)
diff --git a/include/GyotoObject.h b/include/GyotoObject.h
index 7fba758..57a6000 100644
--- a/include/GyotoObject.h
+++ b/include/GyotoObject.h
@@ -188,12 +188,24 @@ class Gyoto::Object
/// Set Value (expressed in unit) of a Property
void set(Property const &p, Value val, std::string const &unit);
+ /// Set Value of a Property
+ void set(std::string const &pname, Value val);
+
+ /// Set Value (expressed in unit) of a Property
+ void set(std::string const &pname, Value val, std::string const &unit);
+
/// Get Value of a Property
Value get(Property const &p) const;
+ /// Get Value of a Property
+ Value get(std::string const &pname) const;
+
/// Get Value of a Property, converted to unit
Value get(Property const &p, std::string const &unit) const;
+ /// Get Value of a Property, converted to unit
+ Value get(std::string const &pname, std::string const &unit) const;
+
/// Find property by name
/**
* Look into the Property list for a Property whose \a name (or
diff --git a/lib/Object.C b/lib/Object.C
index bb2dc2f..b2df225 100644
--- a/lib/Object.C
+++ b/lib/Object.C
@@ -120,6 +120,20 @@ void Object::set(Property const &p, Value val) {
# undef ___local_case
}
+void Object::set(std::string const &pname, Value val) {
+ Property const * p = property(pname);
+ if (!p) throwError("No Property by that name");
+ set(*p, ((p->type == Property::bool_t && pname == p->name_false)?
+ Value(!val):val));
+}
+
+void Object::set(std::string const &pname, Value val, std::string const &unit) {
+ Property const * p = property(pname);
+ if (!p) throwError("No Property by that name");
+ set(*p, ((p->type == Property::bool_t && pname == p->name_false)?
+ Value(!val):val), unit);
+}
+
Value Object::get(Property const &p,
std::string const &unit) const {
@@ -189,6 +203,24 @@ Value Object::get(Property const &p) const {
# undef ___local_case
}
+Value Object::get(std::string const &pname) const {
+ Property const * p = property(pname);
+ if (!p) throwError("No Property by that name");
+ Value res = get(*p);
+ if (p->type == Property::bool_t && pname == p->name_false)
+ return !bool(res);
+ return res;
+}
+
+Value Object::get(std::string const &pname, std::string const &unit) const{
+ Property const * p = property(pname);
+ if (!p) throwError("No Property by that name");
+ Value res = get(*p, unit);
+ if (p->type == Property::bool_t && pname == p->name_false)
+ return !bool(res);
+ return res;
+}
+
Property const * Object::property(std::string const pname) const {
Property const * prop = getProperties();
while (prop) {
diff --git a/lib/Value.C b/lib/Value.C
index d3fbea4..47baa68 100644
--- a/lib/Value.C
+++ b/lib/Value.C
@@ -22,10 +22,34 @@ Value::~Value() {}
return T; \
}
+Value::Value(long val) : type(Property::long_t), Long(val){}
+Value::Value(unsigned long val) : type(Property::unsigned_long_t), ULong(val){}
+Value::operator long() const {
+ switch (type) {
+ case Property::long_t:
+ return Long;
+ case Property::unsigned_long_t:
+ return long(ULong);
+ default:
+ throwError("This Value does not hold a long (or unsigned long)");
+ }
+ return 0;
+}
+
+Value::operator unsigned long() const {
+ switch (type) {
+ case Property::long_t:
+ return (unsigned long)(Long);
+ case Property::unsigned_long_t:
+ return ULong;
+ default:
+ throwError("This Value does not hold a long (or unsigned long)");
+ }
+ return 0;
+}
+
___local_stuff(double, double_t, Double)
___local_stuff(bool, bool_t, Bool)
-___local_stuff(long, long_t, Long)
-___local_stuff(unsigned long, unsigned_long_t, ULong)
___local_stuff(std::string, string_t, String)
___local_stuff(std::vector<double>, vector_double_t, VDouble)
___local_stuff(std::vector<unsigned long>, vector_unsigned_long_t, VULong)
diff --git a/python/example.py b/python/example.py
index fa185b2..c338f9c 100644
--- a/python/example.py
+++ b/python/example.py
@@ -218,13 +218,14 @@ kerr=gyoto.Metric('KerrBL')
# Most properties that can be set in an XML file can also be accessed
# from Python using the Property/Value mechanism:
+# Low-level access:
p=tt.property("SmallRadius")
+p.type==gyoto.Property.double_t
tt.set(p, gyoto.Value(0.2))
-tt.get(p).toDouble() == 0.2
-
-p=kerr.property("Spin")
-kerr.set(p, gyoto.Value(0.95))
-kerr.get(p).toDouble() == 0.95
+tt.get(p) == 0.2
+# Higher-level:
+kerr.set("Spin", 0.95)
+kerr.get("Spin") == 0.95
# However, we also have Python extensions around the standard Gyoto
# plug-ins. Beware that the plug-in must be loaded into Gyoto before
@@ -241,8 +242,7 @@ tr2=gyoto_std.Torus()
# and we can cast a generic pointer (from the gyoto extension) to a
# derived class:
tr=gyoto_std.Torus(tt)
-p=tt.property("SmallRadius")
-tt.get(p).toDouble() == tr.smallRadius()
+tt.get("SmallRadius") == tr.smallRadius()
# Another example: using a complex (i.e. compound) Astrobj:
cplx=gyoto_std.ComplexAstrobj()
diff --git a/python/gyoto.i b/python/gyoto.i
index 8a24a84..fad8fea 100644
--- a/python/gyoto.i
+++ b/python/gyoto.i
@@ -92,10 +92,11 @@
Gyoto::SmartPointer<gtype> (gtype *)
{
gtype* normal_pointer=(gtype *) (Gyoto::SmartPointer<gtype>(result));
- normal_pointer->incRefCount();
+ if (normal_pointer) normal_pointer->incRefCount();
$result = SWIG_NewPointerObj( normal_pointer, stype, SWIG_POINTER_OWN | 0 );
}
-%typemap(typecheck) Gyoto::SmartPointer<gtype>, gtype * {
+%typemap(typecheck,precedence=SWIG_TYPECHECK_VOIDPTR)
+Gyoto::SmartPointer<gtype>, gtype * {
void *vptr = 0;
int res = SWIG_ConvertPtr($input, &vptr, stype, 0);
$1 = SWIG_CheckState(res);
@@ -145,7 +146,7 @@
Gyoto::SmartPointer<Gyoto::klass::Generic> pres=
Gyoto::klass::getSubcontractor(nm.c_str())(NULL);
Gyoto::klass::Generic * res = (Gyoto::klass::Generic *)(pres);
- res -> incRefCount();
+ if (res) res -> incRefCount();
return res;
}
};
@@ -242,6 +243,177 @@ GyotoSmPtrTypeMapClassDerived(Units, Converter);
GyotoSmPtrTypeMapClassDerived(Worldline, IntegState);
GyotoSmPtrTypeMapClassDerived(Astrobj, Properties);
+// Typemaps for Gyoto::Value:
+// In: cast from Python representations for all the supported types.
+// Implementation is specific to Python.
+%typemap(in) Gyoto::Value {
+ int res=0;
+ void *argp=0;
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Value, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::Value * temp = reinterpret_cast< Gyoto::Value * >(argp);
+ $1 = *temp;
+ if (SWIG_IsNewObj(res)) delete temp;
+ }
+
+ if (!SWIG_IsOK(res)) {
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Metric__Generic, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::SmartPointer<Gyoto::Metric::Generic> temp = reinterpret_cast< Gyoto::Metric::Generic * >(argp);
+ $1 = Gyoto::Value(temp);
+ }
+ }
+
+ if (!SWIG_IsOK(res)) {
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Astrobj__Generic, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::SmartPointer<Gyoto::Astrobj::Generic> temp = reinterpret_cast< Gyoto::Astrobj::Generic * >(argp);
+ $1 = Gyoto::Value(temp);
+ }
+ }
+
+ if (!SWIG_IsOK(res)) {
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Spectrum__Generic, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::SmartPointer<Gyoto::Spectrum::Generic> temp = reinterpret_cast< Gyoto::Spectrum::Generic * >(argp);
+ $1 = Gyoto::Value(temp);
+ }
+ }
+
+ if (!SWIG_IsOK(res)) {
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Spectrometer__Generic, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::SmartPointer<Gyoto::Spectrometer::Generic> temp = reinterpret_cast< Gyoto::Spectrometer::Generic * >(argp);
+ $1 = Gyoto::Value(temp);
+ }
+ }
+
+ if (!SWIG_IsOK(res)) {
+ res=SWIG_ConvertPtr($input, &argp, SWIGTYPE_p_Gyoto__Screen, 0);
+ if (SWIG_IsOK(res)) {
+ Gyoto::SmartPointer<Gyoto::Screen> temp = reinterpret_cast< Gyoto::Screen * >(argp);
+ $1 = Gyoto::Value(temp);
+ }
+ }
+
+ if (!SWIG_IsOK(res)) {
+ std::string *temp = 0;
+ res = SWIG_AsPtr_std_string ($input, &temp) ;
+ if (SWIG_IsOK(res)) $1 = Gyoto::Value(*temp);
+ if (SWIG_IsNewObj(res) && temp) delete temp;
+ }
+
+ if (!SWIG_IsOK(res)) {
+ std::vector<unsigned long> *temp=0;
+ res = swig::traits_asptr< std::vector<unsigned long> >::asptr($input, &temp);
+ if (SWIG_IsOK(res)) $1 = Gyoto::Value(*temp);
+ if (SWIG_IsNewObj(res) && temp) delete temp;
+ }
+
+ if (!SWIG_IsOK(res)) {
+ std::vector<double> *temp=0;
+ res = swig::traits_asptr< std::vector<double> >::asptr($input, &temp);
+ if (SWIG_IsOK(res)) $1 = Gyoto::Value(*temp);
+ if (SWIG_IsNewObj(res) && temp) delete temp;
+ }
+
+ /*
+ // This would help in making this language-agnostic, but it become
+ // difficult to distinguish the various subtypes (long vs bool vs
+ // double):
+ if (!SWIG_IsOK(res)) {
+ bool temp=false;
+ res = SWIG_AsVal(bool)($input, &temp)
+ if (SWIG_IsOK(res)) $1 = Gyoto::Value(temp);
+ }
+ */
+
+ if (SWIG_IsOK(res)) ; // done
+ else if (PyBool_Check($input)) $1 = Gyoto::Value($input == Py_True);
+ else if (PyInt_Check($input)) $1 = Gyoto::Value(long(PyInt_AsLong($input)));
+ else if (PyLong_Check($input)) $1 = Gyoto::Value(long(PyLong_AsLong($input)));
+ else if (PyFloat_Check($input)) $1 = Gyoto::Value(PyFloat_AsDouble($input));
+ else {
+ SWIG_exception_fail(SWIG_ArgError(res), "argument of type 'Gyoto::Value*'");
+ }
+ }
+// Typecheck: should be debugged, does not seem to filter anything
+%typemap(typecheck) Gyoto::Value {
+ void *vptr = 0;
+ int res = SWIG_ConvertPtr(argv[0], &vptr, SWIGTYPE_p_Gyoto__Value, 0);
+ $1 = res;
+ // $1 = res ||
+ // PyInt_Check($input) ||
+ // PyLong_Check($input)
+ // ;
+}
+// Out: cast from Gyoto::Value to language-specific representation
+// for each sub-type. Probably language-agnostic.
+%typemap(out) Gyoto::Value {
+ switch ($1.type) {
+ case Gyoto::Property::unsigned_long_t:
+ $result = SWIG_From_unsigned_SS_long((unsigned long)($1));
+ break;
+ case Gyoto::Property::long_t:
+ $result = SWIG_From_long(long($1));
+ break;
+ case Gyoto::Property::bool_t:
+ $result = SWIG_From_bool(bool($1));
+ break;
+ case Gyoto::Property::double_t:
+ $result = SWIG_From_double(double($1));
+ break;
+ case Gyoto::Property::filename_t:
+ case Gyoto::Property::string_t:
+ $result = SWIG_From_std_string(static_cast< std::string >($1));
+ break;
+ case Gyoto::Property::vector_double_t:
+ $result = swig::from(($1).operator std::vector<double>());
+ break;
+ case Gyoto::Property::vector_unsigned_long_t:
+ $result = swig::from(($1).operator std::vector<unsigned long>());
+ break;
+ case Gyoto::Property::metric_t:
+ {
+ Gyoto::Metric::Generic* normal_pointer=(Gyoto::Metric::Generic *) (Gyoto::SmartPointer<Gyoto::Metric::Generic>($1));
+ if (normal_pointer) normal_pointer->incRefCount();
+ $result = SWIG_NewPointerObj( normal_pointer, SWIGTYPE_p_Gyoto__Metric__Generic, SWIG_POINTER_OWN | 0 );
+ }
+ break;
+ case Gyoto::Property::astrobj_t:
+ {
+ Gyoto::Astrobj::Generic* normal_pointer=(Gyoto::Astrobj::Generic *) (Gyoto::SmartPointer<Gyoto::Astrobj::Generic>($1));
+ if (normal_pointer) normal_pointer->incRefCount();
+ $result = SWIG_NewPointerObj( normal_pointer, SWIGTYPE_p_Gyoto__Astrobj__Generic, SWIG_POINTER_OWN | 0 );
+ }
+ break;
+ case Gyoto::Property::spectrum_t:
+ {
+ Gyoto::Spectrum::Generic* normal_pointer=(Gyoto::Spectrum::Generic *) (Gyoto::SmartPointer<Gyoto::Spectrum::Generic>($1));
+ if (normal_pointer) normal_pointer->incRefCount();
+ $result = SWIG_NewPointerObj( normal_pointer, SWIGTYPE_p_Gyoto__Spectrum__Generic, SWIG_POINTER_OWN | 0 );
+ }
+ break;
+ case Gyoto::Property::spectrometer_t:
+ {
+ Gyoto::Spectrometer::Generic* normal_pointer=(Gyoto::Spectrometer::Generic *) (Gyoto::SmartPointer<Gyoto::Spectrometer::Generic>($1));
+ if (normal_pointer) normal_pointer->incRefCount();
+ $result = SWIG_NewPointerObj( normal_pointer, SWIGTYPE_p_Gyoto__Spectrometer__Generic, SWIG_POINTER_OWN | 0 );
+ }
+ break;
+ case Gyoto::Property::screen_t:
+ {
+ Gyoto::Screen* normal_pointer=(Gyoto::Screen *) (Gyoto::SmartPointer<Gyoto::Screen>($1));
+ if (normal_pointer) normal_pointer->incRefCount();
+ $result = SWIG_NewPointerObj( normal_pointer, SWIGTYPE_p_Gyoto__Screen, SWIG_POINTER_OWN | 0 );
+ }
+ break;
+ default:
+ $result = SWIG_NewPointerObj((new Gyoto::Value(static_cast< const Gyoto::Value& >($1))), SWIGTYPE_p_Gyoto__Value, SWIG_POINTER_OWN | 0 );
+ }
+}
+
+
// Non-Gyoto typemaps:
// Handle std::string
%include "std_string.i";
@@ -249,6 +421,9 @@ GyotoSmPtrTypeMapClassDerived(Astrobj, Properties);
// Handle std::vector<double> and <unsigned long int>
%include "std_vector.i";
%template(vector_double) std::vector<double>;
+%{
+ typedef unsigned long unsignedlong;
+ %}
%template(vector_unsigned_long) std::vector<unsigned long>;
// Handle some arrays as NumPy arrays
@@ -359,8 +534,7 @@ GyotoSmPtrClassDerived(Astrobj, ThinDisk)
%define _PConverter(member, method)
Gyoto::Units::Converter * method() {
Gyoto::Units::Converter * res = $self->member;
- if (!res) Gyoto::throwError(#member " converter not set");
- res -> incRefCount();
+ if (res) res -> incRefCount();
return res;
}
%enddef
@@ -377,7 +551,7 @@ GyotoSmPtrClassGeneric(Spectrometer)
%extend Gyoto::Spectrometer::Complex {
Gyoto::Spectrometer::Generic * __getitem__ (int i) {
Gyoto::Spectrometer::Generic * res = ($self)->operator[](i);
- res -> incRefCount();
+ if (res) res -> incRefCount();
return res;
}
};
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/debian-astro/packages/gyoto.git
More information about the Debian-astro-commits
mailing list