00001
00002
00003
00004 #include "GaudiKernel/DeclareFactoryEntries.h"
00005 #include "GaudiKernel/MsgStream.h"
00006
00007 #include <xercesc/dom/DOMElement.hpp>
00008 #include <xercesc/dom/DOMDocument.hpp>
00009 #include <xercesc/dom/DOMNodeList.hpp>
00010 #include <xercesc/dom/DOMNode.hpp>
00011
00012 #include <boost/regex.hpp>
00013
00014 using namespace xercesc;
00015
00016 #include "XmlTools/IXmlSvc.h"
00017
00018 #include <DetDesc/Material.h>
00019 #include <DetDesc/ILVolume.h>
00020 #include <DetDesc/LogVolumeException.h>
00021
00022 #include "VisualizationSvc.h"
00023
00024
00025
00026
00027
00028
00029
00030 DECLARE_SERVICE_FACTORY(VisualizationSvc);
00031
00032
00033
00034
00035 const std::string dom2Std (const XMLCh* aString) {
00036 char *cString = xercesc::XMLString::transcode(aString);
00037 std::string stdString;
00038 if (cString) {
00039 stdString = cString;
00040 xercesc::XMLString::release(&cString);
00041 }
00042 return stdString;
00043 }
00044
00045
00046
00047
00048 VisualizationSvc::VisualizationSvc (const std::string& name, ISvcLocator* svc) :
00049 Service (name, svc) {
00050 declareProperty ("ColorDbLocation", m_colorDbLocation="empty" );
00051 }
00052
00053
00054
00055
00056 StatusCode VisualizationSvc::initialize() {
00057
00058 StatusCode status = Service::initialize();
00059 if (!status.isSuccess()) {
00060 return status;
00061 }
00062 if( m_colorDbLocation.empty() || "empty" == m_colorDbLocation ) {
00063 if ( 0 != getenv("XMLVISROOT") ) {
00064 m_colorDbLocation = getenv("XMLVISROOT");
00065 m_colorDbLocation += "/xml/colors.xml";
00066 } else {
00067 m_colorDbLocation = "";
00068 }
00069 }
00070
00071 reload();
00072
00073 return StatusCode::SUCCESS;
00074 }
00075
00076
00077
00078
00079 void VisualizationSvc::clear () {
00080 m_attributeSet.clear();
00081 m_material2Vis.clear();
00082 m_logvol2Vis.clear();
00083 m_logvol_regex_2Vis.clear();
00084 }
00085
00086
00087
00088
00089 void VisualizationSvc::reload () {
00090 MsgStream log (msgSvc(), "VisualizationSvc");
00091
00092
00093 clear();
00094
00095
00096 IXmlSvc* xmlSvc;
00097 StatusCode status = serviceLocator()->service("XmlCnvSvc", xmlSvc, true);
00098 if (status.isFailure()) {
00099 log << MSG::ERROR << "Unable to get XmlCnvSvc. The visualization "
00100 << "attributes will not be loaded." << endmsg;
00101 return;
00102 }
00103 log << MSG::INFO << "Loading visualization attributes file \""
00104 << m_colorDbLocation << "\" ..." << endmsg;
00105
00106
00107 IOVDOMDocument* iovDoc = xmlSvc->parse(m_colorDbLocation.c_str());
00108 if (!iovDoc) {
00109 log << MSG::ERROR << "Unable to parse file " << m_colorDbLocation
00110 << ". The visualization attributes will not be loaded." << endmsg;
00111 return;
00112 }
00113 DOMDocument* document = iovDoc->getDOM();
00114 if (!document) {
00115 log << MSG::ERROR << "Document does not exist " << m_colorDbLocation
00116 << ". The visualization attributes will not be loaded." << endmsg;
00117 xmlSvc->releaseDoc(iovDoc);
00118 return;
00119 }
00120
00121
00122 XMLCh* xs = xercesc::XMLString::transcode("VisAtt");
00123 DOMNodeList* domAttrList = document->getElementsByTagName(xs);
00124 if(!domAttrList) {
00125 xmlSvc->releaseDoc(iovDoc);
00126 return;
00127 }
00128
00129 xercesc::XMLString::release(&xs);
00130 unsigned int i;
00131 for (i = 0; i < domAttrList->getLength(); i++) {
00132 DOMNode* attrNode = domAttrList->item(i);
00133 DOMElement* attr = (DOMElement*) attrNode;
00134
00135 xs = xercesc::XMLString::transcode("name");
00136 std::string name = dom2Std (attr->getAttribute (xs));
00137 xercesc::XMLString::release(&xs);
00138
00139 xs = xercesc::XMLString::transcode("visible");
00140 std::string visibleAttribute = dom2Std (attr->getAttribute (xs));
00141 xercesc::XMLString::release(&xs);
00142
00143 xs = xercesc::XMLString::transcode("opened");
00144 std::string openedAttribute = dom2Std (attr->getAttribute (xs));
00145 xercesc::XMLString::release(&xs);
00146
00147 xs = xercesc::XMLString::transcode("mode");
00148 std::string modeAttribute = dom2Std (attr->getAttribute (xs));
00149 xercesc::XMLString::release(&xs);
00150
00151
00152 VisAttribute::Visibility visible = VisAttribute::NO_VISIBILITY;
00153 if ("Yes" == visibleAttribute) {
00154 visible = VisAttribute::VISIBLE;
00155 } else if ("No" == visibleAttribute) {
00156 visible = VisAttribute::NOT_VISIBLE;
00157 }
00158 VisAttribute::OpenStatus opened = VisAttribute::NO_STATUS;
00159 if ("Yes" == openedAttribute) {
00160 opened = VisAttribute::OPENED;
00161 } else if ("No" == openedAttribute) {
00162 opened = VisAttribute::CLOSED;
00163 }
00164 VisAttribute::DisplayMode mode = VisAttribute::NO_MODE;
00165 if ("Plain" == modeAttribute) {
00166 mode = VisAttribute::PLAIN;
00167 } else if ("WireFrame" == modeAttribute) {
00168 mode = VisAttribute::WIRE_FRAME;
00169 }
00170
00171
00172 Color color;
00173 xs = xercesc::XMLString::transcode("Color");
00174 DOMNodeList* domColorList = attr->getElementsByTagName(xs);
00175 xercesc::XMLString::release(&xs);
00176
00177 if (domColorList && domColorList->getLength() > 0) {
00178 DOMNode* colorNode = domColorList->item(0);
00179 DOMElement* colorElement = (DOMElement*) colorNode;
00180
00181 xs = xercesc::XMLString::transcode("R");
00182 std::string RAttribute = dom2Std (colorElement->getAttribute (xs));
00183 xercesc::XMLString::release(&xs);
00184
00185 xs = xercesc::XMLString::transcode("G");
00186 std::string GAttribute = dom2Std (colorElement->getAttribute (xs));
00187 xercesc::XMLString::release(&xs);
00188
00189 xs = xercesc::XMLString::transcode("B");
00190 std::string BAttribute = dom2Std (colorElement->getAttribute (xs));
00191 xercesc::XMLString::release(&xs);
00192
00193 xs = xercesc::XMLString::transcode("A");
00194 std::string AAttribute = dom2Std (colorElement->getAttribute (xs));
00195 xercesc::XMLString::release(&xs);
00196
00197
00198 float red = 0.0;
00199 float green = 0.0;
00200 float blue = 0.0;
00201 float alpha = 0.0;
00202 if (!RAttribute.empty()) {
00203 red = (float)xmlSvc->eval(RAttribute, false);
00204 }
00205 if (!GAttribute.empty()) {
00206 green = (float)xmlSvc->eval(GAttribute, false);
00207 }
00208 if (!BAttribute.empty()) {
00209 blue = (float)xmlSvc->eval(BAttribute, false);
00210 }
00211 if (!AAttribute.empty()) {
00212 alpha = (float)xmlSvc->eval(AAttribute, false);
00213 }
00214
00215
00216 color = Color (red, green, blue, alpha);
00217 }
00218
00219
00220 m_attributeSet[name] = VisAttribute(visible, opened, mode, color);
00221 }
00222
00223
00224 xs = xercesc::XMLString::transcode("Materials");
00225 DOMNodeList* domMaterialsList = document->getElementsByTagName(xs);
00226 xercesc::XMLString::release(&xs);
00227
00228 if (domMaterialsList && domMaterialsList->getLength() > 0) {
00229 DOMNode* materialsNode = domMaterialsList->item(0);
00230 DOMElement* materialsElement = (DOMElement*) materialsNode;
00231
00232 xs = xercesc::XMLString::transcode("Item");
00233 DOMNodeList* domMaterialList = materialsElement->getElementsByTagName(xs);
00234 xercesc::XMLString::release(&xs);
00235
00236 if(domMaterialList) {
00237 unsigned int i;
00238 for (i = 0; i < domMaterialList->getLength(); i++) {
00239 DOMNode* materialNode = domMaterialList->item(i);
00240 DOMElement* material = (DOMElement*) materialNode;
00241
00242 xs = xercesc::XMLString::transcode("name");
00243 std::string name = dom2Std (material->getAttribute (xs));
00244 xercesc::XMLString::release(&xs);
00245
00246 xs = xercesc::XMLString::transcode("attr");
00247 std::string attr = dom2Std (material->getAttribute (xs));
00248 xercesc::XMLString::release(&xs);
00249
00250
00251 m_material2Vis[name] = attr;
00252 }
00253 }
00254 }
00255
00256
00257 xs = xercesc::XMLString::transcode("LogVols");
00258 DOMNodeList* domLogvolsList = document->getElementsByTagName(xs);
00259 xercesc::XMLString::release(&xs);
00260
00261 if (domLogvolsList->getLength() > 0) {
00262 DOMNode* logvolsNode = domLogvolsList->item(0);
00263 DOMElement* logvolsElement = (DOMElement*) logvolsNode;
00264
00265 xs = xercesc::XMLString::transcode("Item");
00266 DOMNodeList* domLogvolList = logvolsElement->getElementsByTagName(xs);
00267 xercesc::XMLString::release(&xs);
00268
00269 unsigned int i;
00270 for (i = 0; i < domLogvolList->getLength(); i++) {
00271 DOMNode* logvolNode = domLogvolList->item(i);
00272 DOMElement* logvol = (DOMElement*) logvolNode;
00273
00274 xs = xercesc::XMLString::transcode("name");
00275 std::string sname = dom2Std (logvol->getAttribute (xs));
00276 xercesc::XMLString::release(&xs);
00277
00278 xs = xercesc::XMLString::transcode("regex");
00279 std::string sregex = dom2Std (logvol->getAttribute (xs));
00280 xercesc::XMLString::release(&xs);
00281
00282 xs = xercesc::XMLString::transcode("attr");
00283 std::string attr = dom2Std (logvol->getAttribute (xs));
00284 xercesc::XMLString::release(&xs);
00285
00286
00287 if(sname.size()) {
00288 m_logvol2Vis[sname] = attr;
00289 } else if(sregex.size()) {
00290 m_logvol_regex_2Vis[sregex] = attr;
00291 } else {
00292 MsgStream log(msgSvc(), name());
00293 log << MSG::WARNING << "LogVol with empty name or regex attribute."
00294 << endmsg;
00295 }
00296 }
00297 }
00298
00299 xmlSvc->releaseDoc(iovDoc);
00300
00301 }
00302
00303
00304
00305
00306 const VisAttribute
00307 VisualizationSvc::visAttribute (const Material* mat) const {
00308 VisAttribute attr;
00309
00310 if (0 != mat) {
00311 Dictionnary::const_iterator it =
00312 m_material2Vis.find (mat->registry()->identifier());
00313 if (it != m_material2Vis.end()) {
00314 AttributeSet::const_iterator it2 = m_attributeSet.find (it->second);
00315 if (it2 != m_attributeSet.end()) {
00316 attr = it2->second;
00317 } else {
00318 MsgStream log(msgSvc(), name());
00319 log << MSG::WARNING << "VisAttribute " << it->second << " unknown but"
00320 << " used for material " << mat->name() << "." << endmsg;
00321 }
00322 }
00323 }
00324 return attr;
00325 }
00326
00327
00328
00329
00330
00331 const VisAttribute
00332 VisualizationSvc::visAttribute (const ILVolume* vol) const {
00333 VisAttribute attr;
00334
00335 if (0 != vol) {
00336
00337 std::string bnn = vol->name();
00338
00339 Dictionnary::const_iterator it = m_logvol2Vis.find (bnn);
00340 if (it != m_logvol2Vis.end()) {
00341 AttributeSet::const_iterator it2 = m_attributeSet.find (it->second);
00342 if (it2 != m_attributeSet.end()) {
00343 attr = it2->second;
00344
00345 if (attr.color().isValid() &&
00346 VisAttribute::NO_VISIBILITY != attr.visible() &&
00347 VisAttribute::NO_STATUS != attr.openStatus() &&
00348 VisAttribute::NO_MODE != attr.displayMode()) {
00349 return attr;
00350 }
00351 } else {
00352 MsgStream log(msgSvc(), name());
00353 log << MSG::WARNING << "VisAttribute " << it->second
00354 << " unknown but"
00355 << " used for logical volume " << vol->name() << "." << endmsg;
00356 return attr;
00357 }
00358 }
00359
00360
00361 {Dictionnary::const_iterator it;
00362 for(it=m_logvol_regex_2Vis.begin();it!=m_logvol_regex_2Vis.end();it++) {
00363 boost::regex re(it->first);
00364 if(boost::regex_search(bnn,re)) {
00365
00366
00367
00368 AttributeSet::const_iterator it2 = m_attributeSet.find (it->second);
00369 if (it2 != m_attributeSet.end()) {
00370 attr = it2->second;
00371
00372 if (attr.color().isValid() &&
00373 VisAttribute::NO_VISIBILITY != attr.visible() &&
00374 VisAttribute::NO_STATUS != attr.openStatus() &&
00375 VisAttribute::NO_MODE != attr.displayMode()) {
00376 return attr;
00377 }
00378 } else {
00379 MsgStream log(msgSvc(), name());
00380 log << MSG::WARNING << "VisAttribute " << it->second
00381 << " unknown but"
00382 << " used for logical volume " << vol->name() << "." << endmsg;
00383 return attr;
00384 }
00385
00386 break;
00387 }
00388 }}
00389
00390
00391
00392 try {
00393 const VisAttribute attr2 = visAttribute(vol->material());
00394 attr.merge(attr2);
00395 } catch (LogVolumeException ex) {
00396
00397
00398 MsgStream log (msgSvc(), "VisualizationSvc");
00399 log << MSG::WARNING
00400 << "Exception received in VisualizationSvc::logvolColor : "
00401 << endmsg;
00402 ex.printOut (log);
00403 log << MSG::WARNING << "Visualization attribute will be corrupted."
00404 << endmsg;
00405 }
00406 }
00407
00408 return attr;
00409
00410 }
00411
00412
00413
00414
00415 StatusCode
00416 VisualizationSvc::queryInterface(const InterfaceID& riid, void** ppvInterface) {
00417 if (IID_IVisualizationSvc.versionMatch(riid)) {
00418 *ppvInterface = (IVisualizationSvc*)this;
00419 addRef();
00420 return StatusCode::SUCCESS;
00421 } else {
00422
00423 return Service::queryInterface(riid, ppvInterface);
00424 }
00425 }