29 , m_start_time(0.0*units::
ns)
30 , m_readout_time(5.0*units::
ms)
31 , m_tick(0.5*units::
us)
32 , m_drift_speed(1.0*units::
mm/units::us)
33 , m_time_smear(1.4*units::us)
34 , m_wire_smear_ind(0.75)
35 , m_wire_smear_col(0.95)
36 , m_smear_response_tn("smear_response")
70 put(cfg,
"continuous",
true);
110 cerr <<
"TruthSmearer["<<(
void*)
this <<
"]: failed to get anode: \"" <<
m_anode_tn <<
"\"\n";
120 m_rng = Factory::find_tn<IRandom>(
m_rng_tn);
145 for (
auto face :
m_anode->faces()) {
149 auto bb = face->sensitive();
151 if (bb.inside(depo->pos())) {
152 face_depos.push_back(depo);
157 auto ray = bb.bounds();
158 cerr <<
"TruthSmearer: anode:"<<
m_anode->ident()<<
" face:" << face->ident() <<
": processing " << face_depos.size() <<
" depos " 159 <<
"with bb: "<< ray.first <<
" --> " << ray.second <<
"\n";
162 for (
auto plane : face->planes()) {
174 for (
auto depo : face_depos) {
180 auto& wires = plane->wires();
181 int planeid = plane->ident();
183 double wire_smear = 1.0;
187 else if(planeid == 0 || planeid == 1){
191 std::cerr<<
"Truthsmearer: planeid "<< planeid <<
" cannot be identified!"<<
std::endl;
197 const double pitch = rb.
binsize();
198 const double impact = ib.binsize();
199 const int nwires = rb.nbins();
200 for (
int iwire=0; iwire<
nwires; ++iwire) {
206 const double wire_pos = rb.center(iwire);
209 const int min_impact = ib.edge_index(wire_pos - 1.5*pitch + 0.1*impact);
210 const int max_impact = ib.edge_index(wire_pos + 1.5*pitch - 0.1*impact);
217 for(
int imp = min_impact; imp < max_impact; imp++) {
220 double wire_weight = 1.0;
225 const double rel_imp_pos = ib.center(imp) - wire_pos;
226 const double dist_to_wire =
abs(rel_imp_pos/rb.binsize());
227 if( dist_to_wire <0.5){
228 wire_weight = wire_smear*1.0;
230 else if( dist_to_wire >0.5 && dist_to_wire <1.5 ){
231 wire_weight = 0.5*(1.0-wire_smear);
236 std::cerr<<
"TruthSmearer: impact "<< imp <<
" position: " 237 << ib.center(imp) <<
" out of +/-1 wire region or at wire boundary, wire pitch: " 238 << rb.binsize() <<
", "<< pitch <<
", target wire position: "<< wire_pos
249 if (charge_spectrum.empty()) {
250 std::cerr<<
"impactZipper: no charge spectrum for absolute impact number: "<< imp <<
endl;
264 bindiff.
erase(0, min_impact);
269 if (
mm.first == (
int)total_spectrum.size()) {
274 int chid = wires[iwire]->channel();
277 auto trace = make_shared<SimpleTrace>(chid, tbin, charge);
278 traces.push_back(trace);
284 frames.push_back(frame);
328 frames.push_back(
nullptr);
bool add(IDepo::pointer deposition, double sigma_time, double sigma_pitch)
const Binning & region_binning() const
void process(output_queue &frames)
bool start_processing(const input_pointer &depo)
void put(Configuration &cfg, const std::string &dotpath, const T &val)
Put value in configuration at the dotted path.
std::vector< pointer > vector
void erase(int begin_impact_index, int end_impact_index)
std::deque< output_pointer > output_queue
Binning tbins(nticks, t0, t0+readout_time)
const Binning & impact_binning() const
virtual void configure(const WireCell::Configuration &config)
Accept a configuration.
IAnodePlane::pointer m_anode
virtual bool operator()(const input_pointer &depo, output_queue &frames)
The calling signature:
ImpactData::pointer impact_data(int bin) const
Pimpos pimpos(nwires, min_wire_pitch, max_wire_pitch)
const Binning & tbins() const
WIRECELL_FACTORY(TruthSmearer, WireCell::Gen::TruthSmearer, WireCell::IDuctor, WireCell::IConfigurable) using namespace std
Json::Value Configuration
std::shared_ptr< const IDepo > input_pointer
std::string m_smear_response_tn
std::vector< float > ChargeSequence
Sequential collection of charge.
QTextStream & endl(QTextStream &s)