00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include <robot/ManipulatorDescription>
00026
00027 #include <base/Externalizer>
00028 #include <base/externalization_error>
00029 #include <base/Application>
00030 #include <base/VFile>
00031
00032 using robot::ManipulatorDescription;
00033
00034 using base::Externalizer;
00035 using base::externalization_error;
00036 using base::Application;
00037 using base::VFile;
00038 using base::PathName;
00039 using base::dom::DOMNode;
00040 using base::dom::DOMElement;
00041
00042
00043
00044 void ManipulatorDescription::outputElementXML(base::Externalizer& e, DOMElement* manipElem, String format, Real version) const
00045 {
00046 e.setElementAttribute(manipElem,"name",getName());
00047 e.setElementAttribute(manipElem,"type", ((mtype==Serial)?"serial":"parallel") );
00048
00049 if (mtype == Serial) {
00050
00051 e.appendComment(manipElem,"matrix transform from mount point of manipulator to origin of link 0");
00052
00053 DOMElement* btElem = e.createElement("basetransform");
00054 manipElem->appendChild(btElem);
00055
00056 e.appendText(btElem, e.toString(baseTransform) );
00057
00058 e.pushContext(manipElem);
00059 kinematicChain.externalize(e, format, version);
00060 e.popContext();
00061
00062 }
00063 else {
00064 Unimplemented;
00065 }
00066
00067 e.appendElement(manipElem);
00068 }
00069
00070
00071
00072
00073
00074
00075 void ManipulatorDescription::inputElementXML(base::Externalizer& e, DOMElement* manipElem, String format, Real version)
00076 {
00077 setName( e.getDefaultedElementAttribute(manipElem, "name", "manipulator") );
00078 if ( e.getDefaultedElementAttribute(manipElem, "type", "serial") == "serial" )
00079 mtype = Serial;
00080 else
00081 mtype = Parallel;
00082
00083 if (mtype == Serial) {
00084 DOMElement* btElem = e.getFirstChildElement(manipElem, "basetransform",false);
00085
00086 if (btElem) {
00087
00088
00089
00090
00091 Logln("Warning: a 'basetransform' specification as part of the manipulator description has been depricated. Use 'mounttransform' instead.");
00092
00093
00094
00095
00096
00097 bool isMatrix = true;
00098 Vector trans(zeroVector(3));
00099 Orient rot;
00100 DOMElement* btTransElem = e.getFirstChildElement(btElem, "translation",false);
00101 if (btTransElem != 0) {
00102 isMatrix = false;
00103 String transText = e.getContainedText(btTransElem);
00104 trans = e.toVector(transText,true);
00105 if (trans.size() != 3)
00106 throw new externalization_error(Exception("basetransform translation vector must have 3 elements"));
00107 }
00108
00109 DOMElement* btRotElem = e.getFirstChildElement(btElem, "rotation",false);
00110 if (btRotElem != 0) {
00111 isMatrix = false;
00112 String rotText = e.getContainedText(btRotElem);
00113 Vector ov = e.toVector(rotText,true);
00114 if (ov.size() == 3)
00115 rot = Orient(ov[0],ov[1],ov[2]);
00116 else if (ov.size() == 4)
00117 rot = Orient(Quat4(ov[0],ov[1],ov[2],ov[3]));
00118 else
00119 throw new externalization_error(Exception("basetransform rotation must have 3 (for EulerRPY) or 4 (for Quat) elements"));
00120 }
00121
00122 if (!isMatrix)
00123 baseTransform = Transform(toVector3(trans),rot).getTransform();
00124 else {
00125 String btText = e.getContainedText(btElem,true);
00126 baseTransform = e.toMatrix4(btText);
00127 }
00128 }
00129 else
00130 baseTransform.setIdentity();
00131
00132 e.pushContext(manipElem);
00133 kinematicChain.externalize(e, format, version);
00134 e.popContext();
00135
00136 }
00137 }
00138
00139
00140
00141
00142
00143
00144 void ManipulatorDescription::externalize(base::Externalizer& e, String format, Real version)
00145 {
00146 if (format == "") format = "xml";
00147
00148 if (!formatSupported(format,version,e.ioType()))
00149 throw std::invalid_argument(Exception(String("format ")+format+" v"+base::realToString(version)+" unsupported"));
00150
00151 if (e.isOutput()) {
00152
00153 DOMElement* manipElem = e.createElement("manipulator");
00154 outputElementXML(e, manipElem, format, version);
00155 e.appendElement(manipElem);
00156
00157 } else {
00158
00159 DOMNode* context = e.context();
00160 DOMElement* manipElem = e.getFirstElement(context, "manipulator");
00161
00162
00163 String link = e.getElementAttribute(manipElem,"link",false);
00164 if (link != "") {
00165
00166 ref<VFile> linkFile = Application::getInstance()->universe()->cache()->findFile(link,e.getArchivePath());
00167 load(linkFile,format,version);
00168 }
00169 else {
00170 inputElementXML(e,manipElem, format, version);
00171 }
00172
00173 e.removeElement(manipElem);
00174
00175 }
00176 }