Allow setting enumeration values from python based on string

This commit is contained in:
Thomas Krijnen
2013-07-23 23:17:37 -07:00
parent 871ee13e05
commit 4987753a47
5 changed files with 1921 additions and 196 deletions
+35 -4
View File
@@ -357,7 +357,7 @@ class Classdef:
entity_map[self.class_name] = self
def get_attributes(self, get_parent=True):
s = entity_map[self.parent_class].get_attributes() if get_parent and self.parent_class else []
s += [(a.name,not not a.optional,a.type.type_enum()) for a in self.arguments.l]
s += [(a.name,not not a.optional,a.type.type_enum(),a.type.type if a.is_enum() else None) for a in self.arguments.l]
return s
def get_constructor_args(self):
s = entity_map[self.parent_class].get_constructor_args() if self.parent_class else []
@@ -580,6 +580,8 @@ namespace Type {
IfcUtil::ArgumentType GetAttributeType(Enum t, unsigned char a);
const std::string& GetAttributeName(Enum t, unsigned char a);
bool GetAttributeOptional(Enum t, unsigned char a);
std::pair<const char*, int> GetEnumerationIndex(Enum t, const std::string& a);
Enum GetAttributeEnumerationClass(Enum t, unsigned char a);
}}
#endif
@@ -657,6 +659,7 @@ print >>cpp_file
print >>cpp_file, "std::map<std::string,Type::Enum> string_map;"
print >>cpp2_file, "std::map<Type::Enum,IfcEntityDescriptor*> entity_descriptor_map;"
print >>cpp2_file, "std::map<Type::Enum,IfcEnumerationDescriptor*> enumeration_descriptor_map;"
maxlen = max([len(e) for e in all_enumerations])
string_map,attribute_count_map,attribute_index_map,attribute_name_map,attribute_optional_map,attribute_type_map = [""]*6
print >>cpp2_file, "void InitDescriptorMap() {"
@@ -676,9 +679,19 @@ while True:
parent_descriptor = ("entity_descriptor_map.find(Type::%s)->second"%e.parent_class) if e.parent_class else "0"
print >>cpp2_file, " current = entity_descriptor_map[Type::%s] = new IfcEntityDescriptor(Type::%s,%s);"%(e.class_name,e.class_name,parent_descriptor)
for a,i in zip(args,range(len(args))):
name,optional,type = a
print >>cpp2_file, " current->add(\"%s\",%s,%s);"%(name,"true" if optional else "false",type)
name,optional,type,enum_class = a
if enum_class:
print >>cpp2_file, " current->add(\"%s\",%s,%s,Type::%s);"%(name,"true" if optional else "false",type,enum_class)
else:
print >>cpp2_file, " current->add(\"%s\",%s,%s);"%(name,"true" if optional else "false",type)
print >>cpp2_file, " // Enumerations"
print >>cpp2_file, " IfcEnumerationDescriptor* current_enum;"
print >>cpp2_file, " std::vector<std::string> values;"
for e, name in [(e, name) for name, e in simple_types.items() if name in enumerations]:
print >>cpp2_file, " values.clear(); values.reserve(128);"
for value in e.type.v:
print >>cpp2_file, " values.push_back(\"%s\");"%value[0]
print >>cpp2_file, " current_enum = enumeration_descriptor_map[Type::%s] = new IfcEnumerationDescriptor(Type::%s, values);"%(name,name)
print >>cpp2_file, "}"
for e in all_enumerations:
@@ -745,4 +758,22 @@ bool Type::GetAttributeOptional(Enum t, unsigned char a) {
if ( i == entity_descriptor_map.end() ) throw IfcException("Type not found");
else return i->second->getArgumentOptional(a);
}
std::pair<const char*, int> Type::GetEnumerationIndex(Enum t, const std::string& a) {
if (enumeration_descriptor_map.empty()) ::InitDescriptorMap();
std::map<Type::Enum,IfcEnumerationDescriptor*>::const_iterator i = enumeration_descriptor_map.find(t);
if ( i == enumeration_descriptor_map.end() ) throw IfcException("Value not found");
else return i->second->getIndex(a);
}
Type::Enum Type::GetAttributeEnumerationClass(Enum t, unsigned char a) {
if (entity_descriptor_map.empty()) ::InitDescriptorMap();
std::map<Type::Enum,IfcEntityDescriptor*>::const_iterator i = entity_descriptor_map.find(t);
if ( i == entity_descriptor_map.end() ) throw IfcException("Type not found");
else {
Type::Enum t = i->second->getArgumentEnumerationClass(a);
if ( t == Type::ALL ) throw IfcException("Not an enumeration");
else return t;
}
}
"""
+1838 -178
View File
File diff suppressed because it is too large Load Diff
+2
View File
@@ -36,6 +36,8 @@ namespace Type {
IfcUtil::ArgumentType GetAttributeType(Enum t, unsigned char a);
const std::string& GetAttributeName(Enum t, unsigned char a);
bool GetAttributeOptional(Enum t, unsigned char a);
std::pair<const char*, int> GetEnumerationIndex(Enum t, const std::string& a);
Enum GetAttributeEnumerationClass(Enum t, unsigned char a);
}}
#endif
+2 -1
View File
@@ -90,7 +90,8 @@ void Ifc::IfcUntypedEntity::setArgument(unsigned int i, const std::string& a) {
if (arg_type == Argument_STRING) {
writable_entity()->setArgument(i,a);
} else if (arg_type == Argument_ENUMERATION) {
writable_entity()->setArgument(i,a);
std::pair<const char*, int> enum_data = Ifc2x3::Type::GetEnumerationIndex(Ifc2x3::Type::GetAttributeEnumerationClass(_type, i), a);
writable_entity()->setArgument(i, enum_data.second, enum_data.first);
} else invalid_argument(i,"STRING");
}
void Ifc::IfcUntypedEntity::setArgument(unsigned int i, const std::vector<int>& v) {
+44 -13
View File
@@ -24,6 +24,7 @@
#include <vector>
#include <sstream>
#include <iostream>
#include <algorithm>
#include "../ifcparse/SharedPointer.h"
#include "../ifcparse/Ifc2x3enum.h"
@@ -52,6 +53,29 @@ inline T* reinterpret_pointer_cast(F* from) {
namespace IfcUtil {
class IfcEnumerationDescriptor {
private:
Ifc2x3::Type::Enum type;
std::vector<std::string> values;
public:
IfcEnumerationDescriptor(Ifc2x3::Type::Enum type, const std::vector<std::string>& values)
: type(type), values(values) {}
std::pair<const char*, int> getIndex(const std::string& value) const {
std::vector<std::string>::const_iterator it = std::find(values.begin(), values.end(), value);
if (it != values.end()) {
return std::make_pair(it->c_str(), std::distance(it, values.begin()));
} else {
throw IfcParse::IfcException("Invalid enumeration value");
}
}
const std::vector<std::string>& getValues() {
return values;
}
Ifc2x3::Type::Enum getType() {
return type;
}
};
class IfcEntityDescriptor {
public:
class IfcArgumentDescriptor
@@ -59,49 +83,56 @@ namespace IfcUtil {
public:
std::string name;
bool optional;
ArgumentType type;
IfcArgumentDescriptor(const std::string& name, bool optional, ArgumentType type)
: name(name), optional(optional), type(type) {}
ArgumentType argument_type;
Ifc2x3::Type::Enum data_type;
IfcArgumentDescriptor(const std::string& name, bool optional, ArgumentType argument_type, Ifc2x3::Type::Enum data_type)
: name(name), optional(optional), argument_type(argument_type), data_type(data_type) {}
};
private:
Ifc2x3::Type::Enum type;
IfcEntityDescriptor* parent;
std::vector<IfcArgumentDescriptor> arguments;
unsigned argument_start() {
unsigned argument_start() const {
return parent ? parent->getArgumentCount() : 0;
}
IfcArgumentDescriptor& get_argument(unsigned i) {
const IfcArgumentDescriptor& get_argument(unsigned i) const {
if (i < arguments.size()) return arguments[i];
else throw IfcParse::IfcException("Argument out of range");
}
public:
IfcEntityDescriptor(Ifc2x3::Type::Enum type, IfcEntityDescriptor* parent)
: type(type), parent(parent) {}
void add(const std::string& name, bool optional, ArgumentType type) {
arguments.push_back(IfcArgumentDescriptor(name, optional, type));
void add(const std::string& name, bool optional, ArgumentType argument_type, Ifc2x3::Type::Enum data_type = Ifc2x3::Type::ALL) {
arguments.push_back(IfcArgumentDescriptor(name, optional, argument_type, data_type));
}
unsigned getArgumentCount() {
unsigned getArgumentCount() const {
return (parent ? parent->getArgumentCount() : 0) + arguments.size();
}
std::string& getArgumentName(unsigned i) {
const std::string& getArgumentName(unsigned i) const {
const unsigned a = argument_start();
return i < a
? parent->getArgumentName(i)
: get_argument(i-a).name;
}
ArgumentType getArgumentType(unsigned i) {
ArgumentType getArgumentType(unsigned i) const {
const unsigned a = argument_start();
return i < a
? parent->getArgumentType(i)
: get_argument(i-a).type;
: get_argument(i-a).argument_type;
}
bool getArgumentOptional(unsigned i) {
bool getArgumentOptional(unsigned i) const {
const unsigned a = argument_start();
return i < a
? parent->getArgumentOptional(i)
: get_argument(i-a).optional;
}
unsigned getArgumentIndex(const std::string& s) {
Ifc2x3::Type::Enum getArgumentEnumerationClass(unsigned i) const {
const unsigned a = argument_start();
return i < a
? parent->getArgumentEnumerationClass(i)
: get_argument(i-a).data_type;
}
unsigned getArgumentIndex(const std::string& s) const {
unsigned a = argument_start();
for(std::vector<IfcArgumentDescriptor>::const_iterator i = arguments.begin(); i != arguments.end(); ++i) {
if (i->name == s) return a;