File indexing completed on 2026-04-09 07:49:44
0001 #pragma once
0002
0003 #include <glm/glm.hpp>
0004
0005 #include "scuda.h"
0006 #include "stran.h"
0007 #include "sstr.h"
0008 #include "NP.hh"
0009
0010
0011 struct SPlaceCylinder
0012 {
0013 double radius ;
0014 double halfheight ;
0015 unsigned num_ring ;
0016 unsigned num_in_ring ;
0017 unsigned tot_place ;
0018
0019 SPlaceCylinder(double radius, double halfheight, unsigned num_ring, unsigned num_in_ring_);
0020 std::string desc() const ;
0021 NP* transforms(const char* opts) const ;
0022 };
0023
0024
0025 inline SPlaceCylinder::SPlaceCylinder(double radius_, double halfheight_, unsigned num_ring_, unsigned num_in_ring_)
0026 :
0027 radius(radius_),
0028 halfheight(halfheight_),
0029 num_ring(num_ring_),
0030 num_in_ring(num_in_ring_),
0031 tot_place(num_ring*num_in_ring)
0032 {
0033 }
0034
0035
0036 inline std::string SPlaceCylinder::desc() const
0037 {
0038 std::stringstream ss ;
0039 ss << "SPlaceCylinder::desc"
0040 << " radius " << radius
0041 << " halfheight " << halfheight
0042 << " num_ring " << num_ring
0043 << " num_in_ring " << num_in_ring
0044 << " tot_place " << tot_place
0045 << std::endl
0046 ;
0047 std::string s = ss.str();
0048 return s ;
0049 }
0050
0051
0052
0053
0054 inline NP* SPlaceCylinder::transforms(const char* opts) const
0055 {
0056 std::vector<std::string> vopts ;
0057 sstr::Split(opts, ',', vopts);
0058 unsigned num_opt = vopts.size();
0059 bool dump = false ;
0060
0061 NP* trs = NP::Make<double>( tot_place, num_opt, 4, 4 );
0062 double* tt = trs->values<double>();
0063 unsigned item_values = num_opt*4*4 ;
0064
0065 if(dump) std::cout
0066 << "SPlaceCylinder::transforms"
0067 << " tot_place " << tot_place
0068 << " num_opt " << num_opt
0069 << " tt " << tt
0070 << " item_values " << item_values
0071 << std::endl
0072 ;
0073
0074 double zz[num_ring] ;
0075 for(unsigned i=0 ; i < num_ring ; i++) zz[i] = -halfheight + 2.*halfheight*double(i)/double(num_ring-1) ;
0076
0077 double phi[num_in_ring] ;
0078 for(unsigned j=0 ; j < num_in_ring ; j++) phi[j] = glm::pi<double>()*2.*double(j)/double(num_in_ring) ;
0079
0080
0081 glm::tvec3<double> a(0.,0.,1.);
0082
0083 unsigned count = 0 ;
0084 for(unsigned j=0 ; j < num_in_ring ; j++)
0085 {
0086 glm::tvec3<double> u(cos(phi[j]),sin(phi[j]),0.);
0087 glm::tvec3<double> b = -u ;
0088 glm::tvec3<double> c = u*radius ;
0089
0090 for(unsigned i=0 ; i < num_ring ; i++)
0091 {
0092 c.z = zz[i] ;
0093
0094 unsigned idx = i*num_in_ring + j ;
0095
0096 count += 1 ;
0097
0098 for(unsigned k=0 ; k < num_opt ; k++)
0099 {
0100 unsigned offset = item_values*idx+16*k ;
0101 const char* opt = vopts[k].c_str();
0102
0103 if(dump) std::cout
0104 << "SPlace::AroundCylinder"
0105 << " opt " << opt
0106 << " offset " << offset
0107 << std::endl
0108 ;
0109
0110 Tran<double>::AddTransform(tt+offset, opt, a, b, c );
0111 }
0112 }
0113 }
0114 assert( count == tot_place );
0115 return trs ;
0116 }
0117
0118
0119