31#ifndef ImpulseResponse2_H
32#define ImpulseResponse2_H
38#include "drain/image/ValueHandler.h"
39#include <drain/image/CoordinatePolicy.h>
40#include "drain/image/FilePng.h"
54template <
class C,
class H=ValueHandler>
75 void addLeft(
int i,
double value,
double weight) = 0;
79 void addRight(
int i,
double value,
double weight) = 0;
83 void addDown(
int i,
double value,
double weight) = 0;
87 void addUp(
int i,
double value,
double weight) = 0;
92 double get(
int i) = 0;
103 typedef H value_handler_t;
111 value_handler_t valueHandler;
128 typename T::conf_t conf;
149 return this->conf.getName();
154 return this->conf.getDescription();
176 typedef typename T::conf_t conf_t;
197 this->
parameters.link(
"extendHorz", extendHorz,
"pix");
198 this->
parameters.link(
"extendVert", extendVert,
"pix");
199 this->
parameters.link(
"weightThreshold", weightThreshold,
"[0..1.0]");
245 void setExtensions(
int horz,
int vert){
254 double weightThreshold = 0.1;
262 Logger mout(getImgLog(), __FILE__, __FUNCTION__);
264 mout.
debug(
"delegating to traverseChannel(src, empty, dst, empty)" );
267 traverseChannel(src, empty, dst, empty);
274 Logger mout(getImgLog(), __FILE__, __FUNCTION__);
276 dst.setScaling(src.getScaling());
281 mout.
warn(dst.getProperties() );
283 traverseChannelHorz(src, srcWeight, dst, dstWeight);
284 traverseChannelVert(dst, dstWeight, dst, dstWeight);
293 Logger mout(getImgLog(), __FILE__, __FUNCTION__);
297 const bool WEIGHTED = !(srcWeight.isEmpty() || dstWeight.isEmpty());
298 mout.attention(DRAIN_LOG(WEIGHTED));
300 const int width = src.getWidth();
301 const int widthExt = src.getWidth()+extendHorz;
302 const int height = src.getHeight();
303 const double defaultWeight = 1.0;
309 T bucketOrig(this->conf);
311 bucket.
init(src,
true);
313 const ValueHandler & valueHandler = bucket.getValueHandler();
320 for (
int j=0; j<height; ++j){
326 for (
int i=-extendHorz; i<widthExt; ++i){
328 point.setLocation(i, j);
329 if (coordHandler.validate(point)){
330 value = src.
get<
double>(point);
331 if (valueHandler.validate(value)){
332 weight = srcWeight.
get<
double>(point);
333 bucket.
addLeft(point.x, value, weight);
337 point.setLocation(width-1-i, j);
338 if (coordHandler.validate(point)){
339 value = src.
get<
double>(point);
340 if (valueHandler.validate(value)){
341 weight = srcWeight.
get<
double>(point);
342 bucket.
addRight(point.x, value, weight);
349 for (
int i=0; i<width; ++i){
351 if (weight > weightThreshold){
352 dst.
put(i,j, bucket.
get(i));
356 dstWeight.
put(i,j, 0);
364 for (
int i=-extendHorz; i<widthExt; ++i){
366 point.setLocation(i, j);
367 if (coordHandler.validate(point)){
368 value = src.
get<
double>(point);
369 if (valueHandler.validate(value)){
370 bucket.
addLeft(point.x, value, defaultWeight);
374 point.setLocation(width-1-i, j);
375 if (coordHandler.validate(point)){
376 value = src.
get<
double>(point);
377 if (valueHandler.validate(value)){
378 bucket.
addRight(point.x, value, defaultWeight);
385 for (
int i=0; i<width; ++i){
386 dst.
put(i,j, bucket.
get(i));
396void ImpulseResponseOp<T>::traverseChannelVert(
const Channel & src,
const Channel & srcWeight, Channel & dst, Channel & dstWeight)
const {
398 Logger mout(getImgLog(), __FILE__, __FUNCTION__);
402 const bool WEIGHTED = !(srcWeight.isEmpty() || dstWeight.isEmpty());
404 mout.attention(DRAIN_LOG(WEIGHTED));
406 const int width = src.getWidth();
407 const int height = src.getHeight();
408 const int heightExt = src.getHeight() + extendVert;
409 const double defaultWeight = 1.0;
414 T bucketOrig(this->conf);
415 ImpulseBucket<typename T::conf_t> & bucket = bucketOrig;
416 bucket.
init(src,
false);
418 const ValueHandler & valueHandler = bucket.getValueHandler();
425 for (
int i=0; i<width; i++){
431 for (
int j=-extendVert; j<heightExt; ++j){
433 point.setLocation(i, j);
434 if (coordHandler.validate(point)){
435 value = src.get<
double>(point);
436 if (valueHandler.validate(value)){
437 weight = srcWeight.get<
double>(point);
438 bucket.addDown(point.y, value, weight);
442 point.setLocation(i, height-1-j);
443 if (coordHandler.validate(point)){
444 value = src.get<
double>(point);
445 if (valueHandler.validate(value)){
446 weight = srcWeight.get<
double>(point);
447 bucket.addUp(point.y, value, weight);
454 for (
int j=0; j<height; ++j){
455 weight = bucket.getWeight(j);
456 if (weight > weightThreshold){
457 dst.put(i,j, bucket.get(j));
458 dstWeight.put(i,j, weight);
461 dstWeight.put(i,j, 0);
469 for (
int j=-extendVert; j<heightExt; ++j){
471 point.setLocation(i, j);
472 if (coordHandler.validate(point)){
473 value = src.get<
double>(point);
474 if (valueHandler.validate(value)){
475 weight = srcWeight.get<
double>(point);
476 bucket.addLeft(point.y, value, defaultWeight);
480 point.setLocation(i, height-1-j);
481 if (coordHandler.validate(point)){
482 value = src.get<
double>(point);
483 if (valueHandler.validate(value)){
484 bucket.addRight(point.y, value, defaultWeight);
491 for (
int j=0; j<height; ++j){
492 dst.putScaled(i,j, bucket.get(j));
map_t parameters
Parameters (name -> linked variable), typically linked to member variables of the derived class.
Definition BeanLike.h:313
LogSourc e is the means for a function or any program segment to "connect" to a Log.
Definition Log.h:326
Logger & warn(const TT &... args)
Possible error, but execution can continue.
Definition Log.h:440
Logger & debug(const TT &... args)
Debug information.
Definition Log.h:676
void append(ReferenceMap &rMap, bool replace=true)
Adopts the references of r. If replace==false, only new entries are appended.
Definition ReferenceMap.h:333
Image with static geometry.
Definition ImageChannel.h:58
Definition CoordinateHandler.h:74
void put(size_t i, T x)
Sets the intensity in location i to x.
Definition ImageFrame.h:191
T get(size_t i) const
Gets the intensity at location i. See address().
Definition ImageFrame.h:263
void setPhysicalRange(const Range< double > &range, bool rescale=false)
Sets the supported range for physical values and optionally adjusts the scaling for maximal resolutio...
Definition ImageFrame.h:105
const CoordinatePolicy & getCoordinatePolicy() const
Coord policy.
Definition ImageLike.h:179
Base class for image processing functions.
Definition ImageOp.h:49
void traverseChannelsSeparately(const ImageTray< const Channel > &src, ImageTray< Channel > &dst) const
Process each (src,dst) channel pair independently. Raise error if their counts differ.
Definition ImageOp.cpp:340
Container applicable for Channels and Images, with alpha support.
Definition ImageTray.h:266
Class for multi-channel digital images. Supports dynamic typing with base types (char,...
Definition Image.h:183
Definition ImpulseResponseOp.h:55
virtual double get(int i)=0
Return natural (not encoded) value at position i.
virtual void addRight(int i, double value, double weight)=0
When traversing down or right, add a encoded value to bucket in position i.
virtual void reset()=0
Clear statistics before traversing each row or column.
virtual double getWeight(int i)=0
Return weight at position i.
virtual void addLeft(int i, double value, double weight)=0
When traversing up or left, add a encoded value to bucket in position i.
virtual void addDown(int i, double value, double weight)=0
When traversing down or right, add a encoded value to bucket in position i.
virtual void init(const Channel &src, bool horizontal=true)
Adapt to input geometry, type, and scaling.
Definition ImpulseResponseOp.h:67
virtual void addUp(int i, double value, double weight)=0
When traversing up or left, add a encoded value to bucket in position i.
Definition ImpulseResponseOp.h:124
virtual const std::string & getName() const
Return the name of an instance.
Definition ImpulseResponseOp.h:148
virtual const std::string & getDescription() const
Return a brief description.
Definition ImpulseResponseOp.h:153
A fill operation for one color.
Definition ImpulseResponseOp.h:171
virtual void traverseChannel(const Channel &src, Channel &dst) const
Apply to single channel.
Definition ImpulseResponseOp.h:261
Definition ValueHandler.h:59