Geant4 Cross Reference

Cross-Referencing   Geant4
Geant4/externals/g4tools/include/tools/sg/ellipse

Version: [ ReleaseNotes ] [ 1.0 ] [ 1.1 ] [ 2.0 ] [ 3.0 ] [ 3.1 ] [ 3.2 ] [ 4.0 ] [ 4.0.p1 ] [ 4.0.p2 ] [ 4.1 ] [ 4.1.p1 ] [ 5.0 ] [ 5.0.p1 ] [ 5.1 ] [ 5.1.p1 ] [ 5.2 ] [ 5.2.p1 ] [ 5.2.p2 ] [ 6.0 ] [ 6.0.p1 ] [ 6.1 ] [ 6.2 ] [ 6.2.p1 ] [ 6.2.p2 ] [ 7.0 ] [ 7.0.p1 ] [ 7.1 ] [ 7.1.p1 ] [ 8.0 ] [ 8.0.p1 ] [ 8.1 ] [ 8.1.p1 ] [ 8.1.p2 ] [ 8.2 ] [ 8.2.p1 ] [ 8.3 ] [ 8.3.p1 ] [ 8.3.p2 ] [ 9.0 ] [ 9.0.p1 ] [ 9.0.p2 ] [ 9.1 ] [ 9.1.p1 ] [ 9.1.p2 ] [ 9.1.p3 ] [ 9.2 ] [ 9.2.p1 ] [ 9.2.p2 ] [ 9.2.p3 ] [ 9.2.p4 ] [ 9.3 ] [ 9.3.p1 ] [ 9.3.p2 ] [ 9.4 ] [ 9.4.p1 ] [ 9.4.p2 ] [ 9.4.p3 ] [ 9.4.p4 ] [ 9.5 ] [ 9.5.p1 ] [ 9.5.p2 ] [ 9.6 ] [ 9.6.p1 ] [ 9.6.p2 ] [ 9.6.p3 ] [ 9.6.p4 ] [ 10.0 ] [ 10.0.p1 ] [ 10.0.p2 ] [ 10.0.p3 ] [ 10.0.p4 ] [ 10.1 ] [ 10.1.p1 ] [ 10.1.p2 ] [ 10.1.p3 ] [ 10.2 ] [ 10.2.p1 ] [ 10.2.p2 ] [ 10.2.p3 ] [ 10.3 ] [ 10.3.p1 ] [ 10.3.p2 ] [ 10.3.p3 ] [ 10.4 ] [ 10.4.p1 ] [ 10.4.p2 ] [ 10.4.p3 ] [ 10.5 ] [ 10.5.p1 ] [ 10.6 ] [ 10.6.p1 ] [ 10.6.p2 ] [ 10.6.p3 ] [ 10.7 ] [ 10.7.p1 ] [ 10.7.p2 ] [ 10.7.p3 ] [ 10.7.p4 ] [ 11.0 ] [ 11.0.p1 ] [ 11.0.p2 ] [ 11.0.p3, ] [ 11.0.p4 ] [ 11.1 ] [ 11.1.1 ] [ 11.1.2 ] [ 11.1.3 ] [ 11.2 ] [ 11.2.1 ] [ 11.2.2 ] [ 11.3.0 ]

  1 // Copyright (C) 2010, Guy Barrand. All rights reserved.
  2 // See the file tools.license for terms.
  3 
  4 #ifndef tools_sg_ellipse
  5 #define tools_sg_ellipse
  6 
  7 // same logic as ROOT/TEllipse.
  8 
  9 #include "node"
 10 #include "sf"
 11 #include "render_action"
 12 #include "pick_action"
 13 #include "bbox_action"
 14 
 15 #include "../mathf"
 16 #include "../curve"
 17 
 18 namespace tools {
 19 namespace sg {
 20 
 21 class ellipse : public node,public curve {
 22   TOOLS_NODE_NO_CAST(ellipse,tools::sg::ellipse,node)
 23 public:
 24   virtual void* cast(const std::string& a_class) const {
 25     if(void* p = cmp_cast<ellipse>(this,a_class)) return p;
 26     if(void* p = cmp_cast<curve>(this,a_class)) return p;
 27     return node::cast(a_class);
 28   }
 29 public:
 30   sf<float> rx;
 31   sf<float> ry;
 32   sf<float> phi_min;  //radians
 33   sf<float> phi_max;  //radians
 34   sf<unsigned int> steps;
 35 public:
 36   virtual const desc_fields& node_desc_fields() const {
 37     TOOLS_FIELD_DESC_NODE_CLASS(tools::sg::ellipse)
 38     static const desc_fields s_v(parent::node_desc_fields(),5, //WARNING : take care of count.
 39       TOOLS_ARG_FIELD_DESC(rx),
 40       TOOLS_ARG_FIELD_DESC(ry),
 41       TOOLS_ARG_FIELD_DESC(phi_min),
 42       TOOLS_ARG_FIELD_DESC(phi_max),
 43       TOOLS_ARG_FIELD_DESC(steps)
 44     );
 45     return s_v;
 46   }
 47 private:
 48   void add_fields(){
 49     add_field(&rx);
 50     add_field(&ry);
 51     add_field(&phi_min);
 52     add_field(&phi_max);
 53     add_field(&steps);
 54   }
 55 public: //curve
 56   virtual bool pos_tan_nor(float /*a_s*/,
 57                            vec3f& a_pos,
 58                            vec3f& a_tan,
 59                            vec3f& a_nor) const {
 60 
 61     //float r = radius.value();
 62     //float cs = fcos(a_s);
 63     //float sn = fsin(a_s);
 64 
 65     float x,y,z;
 66 
 67    {//x = r*cs;y = r*sn;z = 0;
 68     x = 0;y = 0;z = 0;
 69     m_model.mul_3f(x,y,z);
 70     a_pos.set_value(x,y,z);}
 71 
 72    {//x = -sn;y = cs;z = 0;
 73     x = 0;y = 1;z = 0;
 74     m_model.mul_dir_3(x,y,z);
 75     a_tan.set_value(x,y,z);}
 76 
 77    {x = 0;y = 0;z = 1;
 78     m_model.mul_dir_3(x,y,z);
 79     a_nor.set_value(x,y,z);}
 80 
 81     return true;
 82   }
 83 public:
 84   virtual void copy(curve*& a_new) const {a_new = new ellipse(*this);}
 85 public:
 86   virtual void render(render_action& a_action) {
 87     if(touched()) {
 88       update_sg();
 89       reset_touched();
 90     }
 91     //Same logic as Inventor SoLightModel.model = BASE_COLOR.
 92     const state& state = a_action.state();
 93     a_action.set_lighting(false);
 94     a_action.add_line_strip(m_xyzs);
 95     a_action.set_lighting(state.m_GL_LIGHTING);
 96   }
 97 
 98   virtual void pick(pick_action& a_action) {
 99     if(touched()) {
100       update_sg();
101       reset_touched();
102     }
103     if(a_action.stop_at_first()){
104       a_action.add_line_strip(m_xyzs);
105       if(a_action.done()) a_action.set_node(this);
106     } else {
107       a_action.set_done(false);
108       a_action.zs().clear();
109       a_action.ws().clear();
110       a_action.add_line_strip(m_xyzs);
111       if(a_action.done()) {
112         a_action.add_pick(*this,a_action.zs(),a_action.ws(),a_action.state());
113         a_action.set_done(false);
114       }
115     }
116   }
117   virtual void bbox(bbox_action& a_action) {
118     if(touched()) {
119       update_sg();
120       reset_touched();
121     }
122     a_action.add_line_strip(m_xyzs);
123   }
124 public:
125   ellipse()
126   :parent()
127   ,curve()
128   ,rx(1)
129   ,ry(1)
130   ,phi_min(0)
131   ,phi_max(tools::ftwo_pi())
132   ,steps(40)
133   {
134     add_fields();
135   }
136   virtual ~ellipse(){}
137 public:
138   ellipse(const ellipse& a_from)
139   :parent(a_from)
140   ,curve(a_from)
141   ,rx(a_from.rx)
142   ,ry(a_from.ry)
143   ,phi_min(a_from.phi_min)
144   ,phi_max(a_from.phi_max)
145   ,steps(a_from.steps)
146   {
147     add_fields();
148   }
149   ellipse& operator=(const ellipse& a_from){
150     parent::operator=(a_from);
151     curve::operator=(a_from);
152     rx = a_from.rx;
153     ry = a_from.ry;
154     phi_min = a_from.phi_min;
155     phi_max = a_from.phi_max;
156     steps = a_from.steps;
157     return *this;
158   }
159 protected:
160   void update_sg() {
161     m_xyzs.clear();
162     if(!steps.value()) return;
163 
164     unsigned int num = steps.value();
165 
166    //set number of points approximatively proportional to the ellipse circumference
167    //float circ = kPI*(r1+r2)*(phi2-phi1)/360;
168    //Int_t n = (Int_t)(np*circ/((gPad->GetX2()-gPad->GetX1())+(gPad->GetY2()-gPad->GetY1())));
169    //if (n < 8) n= 8;
170    //if (n > np) n = np;
171 
172     m_xyzs.resize((num+1)*3);
173 
174     float phimin = phi_min.value();
175     float phimax = phi_max.value();
176     float r1 = rx.value();
177     float r2 = ry.value();
178 
179     float phi1 = mn<float>(phimin,phimax);
180     float phi2 = mx<float>(phimin,phimax);
181 
182     float angle,dx,dy;
183     float dphi = (phi2-phi1)/float(num);
184     size_t pos = 0;
185     for(unsigned int i=0;i<=num;i++) {
186       angle = phi1 + float(i)*dphi;
187       dx    = r1*fcos(angle);
188       dy    = r2*fsin(angle);
189       m_xyzs[pos]  = dx;pos++;
190       m_xyzs[pos]  = dy;pos++;
191       m_xyzs[pos]  = 0;pos++;
192     }
193     /*
194     TString opt = option;
195     opt.ToLower();
196     if (phi2-phi1 >= 360 ) {
197       if (GetFillStyle()) gPad->PaintFillArea(n,x,y);
198       if (GetLineStyle()) gPad->PaintPolyLine(n+1,x,y);
199     } else {
200       x[n+1] = gPad->XtoPad(x1);
201       y[n+1] = gPad->YtoPad(y1);
202       x[n+2] = x[0];
203       y[n+2] = y[0];
204       if (GetFillStyle()) gPad->PaintFillArea(n+2,x,y);
205       if (GetLineStyle()) {
206          if (TestBit(kNoEdges) || opt.Contains("only")) gPad->PaintPolyLine(n+1,x,y);
207          else                                           gPad->PaintPolyLine(n+3,x,y);
208       }
209     }
210     */
211 
212   }
213 
214 protected:
215   std::vector<float> m_xyzs;
216 };
217 
218 }}
219 
220 #endif