Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-04-09 07:49:41

0001 #pragma once
0002 /**
0003 snode.h : structural "volume" nodes
0004 =====================================
0005 
0006 snode are structural nodes residing in the the stree.h
0007 vectors *stree::nds* and *stree::rem* that are populated
0008 from Geant4 volumes by U4Tree.h U4Tree::initNodes_r
0009 
0010 There are no transform references in snode.h as all
0011 the below vectors are populated together so the node
0012 index also corresponds to the other indices::
0013 
0014    stree::nds
0015    stree::digs
0016    stree::m2w
0017    stree::w2m
0018    stree::gtd
0019 
0020 For traversal examples see *stree::get_children*
0021 
0022 Q: Is repeat_index always zero for global nodes, including triangulated ones ?
0023 A: Yes, see stree::desc_repeat_index() as shown by::
0024 
0025    TEST=desc_repeat_index ~/o/sysrap/tests/stree_load_test.sh
0026 
0027    The artificial "triangulated" solid that is tacked on last,  has ridx 0
0028    as does the first global analytic solid.
0029 
0030 
0031 **/
0032 
0033 #include <string>
0034 #include <cstring>
0035 #include <sstream>
0036 #include <iomanip>
0037 #include <vector>
0038 
0039 struct snode_field
0040 {
0041     static constexpr const char* INDEX          = "INDEX" ;
0042     static constexpr const char* DEPTH          = "DEPTH" ;
0043     static constexpr const char* SIBDEX         = "SIBDEX" ;
0044     static constexpr const char* PARENT         = "PARENT" ;
0045     static constexpr const char* NUM_CHILD      = "NUM_CHILD" ;
0046     static constexpr const char* FIRST_CHILD    = "FIRST_CHILD" ;
0047     static constexpr const char* NEXT_SIBLING   = "NEXT_SIBLING" ;
0048     static constexpr const char* LVID           = "LVID" ;
0049     static constexpr const char* COPYNO         = "COPYNO" ;
0050     static constexpr const char* SENSOR_ID      = "SENSOR_ID" ;
0051     static constexpr const char* SENSOR_INDEX   = "SENSOR_INDEX" ;
0052     static constexpr const char* REPEAT_INDEX   = "REPEAT_INDEX" ;
0053     static constexpr const char* REPEAT_ORDINAL = "REPEAT_ORDINAL" ;
0054     static constexpr const char* BOUNDARY       = "BOUNDARY" ;
0055     static constexpr const char* SENSOR_NAME    = "SENSOR_NAME" ;
0056 
0057     static int Idx(const char* attrib);
0058 };
0059 
0060 inline int snode_field::Idx(const char* attrib)
0061 {
0062     int idx = -1 ;
0063     if(     0==strcmp(attrib,INDEX))          idx = 0 ;
0064     else if(0==strcmp(attrib,DEPTH))          idx = 1 ;
0065     else if(0==strcmp(attrib,SIBDEX))         idx = 2 ;
0066     else if(0==strcmp(attrib,PARENT))         idx = 3 ;
0067     else if(0==strcmp(attrib,NUM_CHILD))      idx = 4 ;
0068     else if(0==strcmp(attrib,FIRST_CHILD))    idx = 5 ;
0069     else if(0==strcmp(attrib,NEXT_SIBLING))   idx = 6 ;
0070     else if(0==strcmp(attrib,LVID))           idx = 7 ;
0071     else if(0==strcmp(attrib,COPYNO))         idx = 8 ;
0072     else if(0==strcmp(attrib,SENSOR_ID))      idx = 9 ;
0073     else if(0==strcmp(attrib,SENSOR_INDEX))   idx = 10 ;
0074     else if(0==strcmp(attrib,REPEAT_INDEX))   idx = 11 ;
0075     else if(0==strcmp(attrib,REPEAT_ORDINAL)) idx = 12 ;
0076     else if(0==strcmp(attrib,BOUNDARY))       idx = 13 ;
0077     else if(0==strcmp(attrib,SENSOR_NAME))    idx = 14 ;
0078     return idx ;
0079 }
0080 
0081 
0082 struct snode
0083 {
0084     static constexpr const int NV = 15 ;
0085 
0086     int index ;        // 0
0087     int depth ;        // 1
0088     int sibdex ;       // 2    0-based sibling index
0089     int parent ;       // 3
0090 
0091     int num_child ;    // 4
0092     int first_child ;  // 5
0093     int next_sibling ; // 6
0094     int lvid ;         // 7
0095 
0096     int copyno ;       // 8
0097     int sensor_id ;    // 9  : -1 signifies "not-a-sensor"
0098     int sensor_index ; // 10
0099     int repeat_index ; // 11
0100 
0101     int repeat_ordinal ; // 12
0102     int boundary ;       // 13
0103     int sensor_name ;    // 14
0104 
0105     std::string desc() const ;
0106     int*        data();
0107     const int*  cdata() const ;
0108     int    get_attrib(int idx) const ;
0109     static std::string Brief_(const std::vector<snode>& nodes );
0110 };
0111 
0112 
0113 inline std::string snode::desc() const
0114 {
0115     std::stringstream ss ;
0116     ss << "snode"
0117        << " ix:" << std::setw(7) << index
0118        << " dh:" << std::setw(2) << depth
0119        << " sx:" << std::setw(5) << sibdex
0120        << " pt:" << std::setw(7) << parent
0121        << " nc:" << std::setw(5) << num_child
0122        << " fc:" << std::setw(7) << first_child
0123        << " ns:" << std::setw(7) << next_sibling
0124        << " lv:" << std::setw(3) << lvid
0125        << " cp:" << std::setw(7) << copyno
0126        << " se:" << std::setw(7) << sensor_id
0127        << " se:" << std::setw(7) << sensor_index
0128        << " ri:" << std::setw(2) << repeat_index
0129        << " ro:" << std::setw(5) << repeat_ordinal
0130        << " bd:" << std::setw(3) << boundary
0131        << " sn:" << std::setw(2) << sensor_name
0132        ;
0133     std::string str = ss.str();
0134     return str ;
0135 }
0136 
0137 inline int*       snode::data(){ return &index ; }
0138 inline const int* snode::cdata() const { return &index ; }
0139 
0140 inline int snode::get_attrib(int idx) const
0141 {
0142     const int* aa = reinterpret_cast<const int*>(this) ;
0143     return idx > -1 && idx < NV ? aa[idx] : -1 ;
0144 }
0145 
0146 inline std::string snode::Brief_(const std::vector<snode>& nodes )
0147 {
0148     int num_nodes = nodes.size();
0149     std::stringstream ss ;
0150     ss << "snode::Brief_ num_nodes " << num_nodes << std::endl ;
0151     for(int i=0; i < num_nodes ; i++) ss << nodes[i].desc() << std::endl ;
0152     std::string str = ss.str();
0153     return str ;
0154 }