00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #ifndef DIMOOPXT_H
00031 #define DIMOOPXT_H
00032
00033 #include "dcmtk/config/osconfig.h"
00034
00035 #include "dcmtk/ofstd/ofcast.h"
00036 #include "dcmtk/ofstd/ofbmanip.h"
00037
00038 #include "dcmtk/dcmimgle/dimoopx.h"
00039 #include "dcmtk/dcmimgle/dimopx.h"
00040 #include "dcmtk/dcmimgle/diluptab.h"
00041 #include "dcmtk/dcmimgle/diovlay.h"
00042 #include "dcmtk/dcmimgle/dipxrept.h"
00043 #include "dcmtk/dcmimgle/didispfn.h"
00044 #include "dcmtk/dcmimgle/didislut.h"
00045
00046 #ifdef PASTEL_COLOR_OUTPUT
00047 #include "dimcopxt.h"
00048 #endif
00049
00050 #define INCLUDE_CMATH
00051 #include "dcmtk/ofstd/ofstdinc.h"
00052
00053
00054
00055
00056
00057
00060 template<class T1, class T2, class T3>
00061 class DiMonoOutputPixelTemplate
00062 : public DiMonoOutputPixel,
00063 public DiPixelRepresentationTemplate<T3>
00064 {
00065
00066 public:
00067
00087 DiMonoOutputPixelTemplate(void *buffer,
00088 const DiMonoPixel *pixel,
00089 DiOverlay *overlays[2],
00090 const DiLookupTable *vlut,
00091 const DiLookupTable *plut,
00092 DiDisplayFunction *disp,
00093 const EF_VoiLutFunction vfunc,
00094 const double center,
00095 const double width,
00096 const Uint32 low,
00097 const Uint32 high,
00098 const Uint16 columns,
00099 const Uint16 rows,
00100 const unsigned long frame,
00101 #ifdef PASTEL_COLOR_OUTPUT
00102 const unsigned long frames,
00103 #else
00104 const unsigned long ,
00105 #endif
00106 const int pastel = 0)
00107 : DiMonoOutputPixel(pixel, OFstatic_cast(unsigned long, columns) * OFstatic_cast(unsigned long, rows), frame,
00108 OFstatic_cast(unsigned long, fabs(OFstatic_cast(double, high - low)))),
00109 Data(NULL),
00110 DeleteData(buffer == NULL),
00111 ColorData(NULL)
00112 {
00113 if ((pixel != NULL) && (Count > 0) && (FrameSize >= Count))
00114 {
00115 if (pastel)
00116 #ifdef PASTEL_COLOR_OUTPUT
00117 color(buffer, pixel, frame, frames);
00118 #else
00119 DCMIMGLE_ERROR("pastel color output not supported");
00120 #endif
00121 else
00122 {
00123 DCMIMGLE_TRACE("monochrome output image - columns: " << columns << ", rows: " << rows << ", frame: " << frame);
00124 DCMIMGLE_TRACE("monochrome output values - low: " << OFstatic_cast(unsigned long, low) << ", high: "
00125 << OFstatic_cast(unsigned long, high) << ((low > high) ? " (inverted)" : ""));
00126 Data = OFstatic_cast(T3 *, buffer);
00127 if ((vlut != NULL) && (vlut->isValid()))
00128 voilut(pixel, frame * FrameSize, vlut, plut, disp, OFstatic_cast(T3, low), OFstatic_cast(T3, high));
00129 else
00130 {
00131 if (width < 1)
00132 nowindow(pixel, frame * FrameSize, plut, disp, OFstatic_cast(T3, low), OFstatic_cast(T3, high));
00133 else if (vfunc == EFV_Sigmoid)
00134 sigmoid(pixel, frame * FrameSize, plut, disp, center, width, OFstatic_cast(T3, low), OFstatic_cast(T3, high));
00135 else
00136 window(pixel, frame * FrameSize, plut, disp, center, width, OFstatic_cast(T3, low), OFstatic_cast(T3, high));
00137 }
00138 overlay(overlays, disp, columns, rows, frame);
00139 }
00140 }
00141 }
00142
00145 virtual ~DiMonoOutputPixelTemplate()
00146 {
00147 if (DeleteData)
00148 delete[] Data;
00149 delete ColorData;
00150 }
00151
00156 inline EP_Representation getRepresentation() const
00157 {
00158 return DiPixelRepresentationTemplate<T3>::getRepresentation();
00159 }
00160
00165 inline size_t getItemSize() const
00166 {
00167 return (ColorData != NULL) ? ColorData->getItemSize() : sizeof(T3);
00168 }
00169
00174 inline const void *getData() const
00175 {
00176 return (ColorData != NULL) ? ColorData->getData() : OFstatic_cast(const void *, Data);
00177 }
00178
00183 virtual void *getDataPtr()
00184 {
00185 return (ColorData != NULL) ? ColorData->getDataPtr() : OFstatic_cast(void *, Data);
00186 }
00187
00190 inline void removeDataReference()
00191 {
00192 Data = NULL;
00193 DeleteData = 0;
00194 }
00195
00202 inline int writePPM(STD_NAMESPACE ostream& stream) const
00203 {
00204 if (Data != NULL)
00205 {
00206 register unsigned long i;
00207 for (i = 0; i < FrameSize; ++i)
00208 stream << OFstatic_cast(unsigned long, Data[i]) << " ";
00209 return 1;
00210 }
00211 if (ColorData != NULL)
00212 return ColorData->writePPM(stream);
00213 return 0;
00214 }
00215
00222 inline int writePPM(FILE *stream) const
00223 {
00224 if (Data != NULL)
00225 {
00226 register unsigned long i;
00227 for (i = 0; i < FrameSize; ++i)
00228 fprintf(stream, "%lu ", OFstatic_cast(unsigned long, Data[i]));
00229 return 1;
00230 }
00231 if (ColorData != NULL)
00232 return ColorData->writePPM(stream);
00233 return 0;
00234 }
00235
00236
00237 protected:
00238
00241 inline void determineUsedValues()
00242 {
00243 if ((UsedValues == NULL) && (MaxValue > 0) && (MaxValue < MAX_TABLE_ENTRY_COUNT))
00244 {
00245 UsedValues = new Uint8[MaxValue + 1];
00246 if (UsedValues != NULL)
00247 {
00248 OFBitmanipTemplate<Uint8>::zeroMem(UsedValues, MaxValue + 1);
00249 register const T3 *p = Data;
00250 register Uint8 *q = UsedValues;
00251 register unsigned long i;
00252 for (i = Count; i != 0; --i)
00253 *(q + *(p++)) = 1;
00254 }
00255 }
00256 }
00257
00258
00259 private:
00260
00267 inline void createDisplayLUT(const DiDisplayLUT *&dlut,
00268 DiDisplayFunction *disp,
00269 const int bits)
00270 {
00271 if ((disp != NULL) && (disp->isValid()))
00272 {
00273 dlut = disp->getLookupTable(bits);
00274 if ((dlut != NULL) && (dlut->isValid()))
00275 {
00276 DCMIMGLE_DEBUG("using display transformation");
00277 } else {
00278 DCMIMGLE_WARN("can't create display LUT ... ignoring display transformation");
00279 dlut = NULL;
00280 }
00281 }
00282 }
00283
00289 inline int initOptimizationLUT(T3 *&lut,
00290 const unsigned long ocnt)
00291 {
00292 int result = 0;
00293 if ((sizeof(T1) <= 2) && (Count > 3 * ocnt))
00294 {
00295 lut = new T3[ocnt];
00296 if (lut != NULL)
00297 {
00298 DCMIMGLE_DEBUG("using optimized routine with additional LUT (" << ocnt << " entries)");
00299 result = 1;
00300 }
00301 }
00302 return result;
00303 }
00304
00305 #ifdef PASTEL_COLOR_OUTPUT
00306 void color(void *buffer,
00307 const DiMonoPixel *inter,
00308 const unsigned long frame,
00309 const unsigned long frames)
00310 {
00311 ColorData = new DiMonoColorOutputPixelTemplate<T1, T3>(buffer, inter, frame, frames);
00312 if (ColorData != NULL)
00313 DCMIMGLE_DEBUG(">>> COLOR <<<");
00314 }
00315 #endif
00316
00327 void voilut(const DiMonoPixel *inter,
00328 const Uint32 start,
00329 const DiLookupTable *vlut,
00330 const DiLookupTable *plut,
00331 DiDisplayFunction *disp,
00332 const T3 low,
00333 const T3 high)
00334 {
00335 const T1 *pixel = OFstatic_cast(const T1 *, inter->getData());
00336 if ((pixel != NULL) && (vlut != NULL))
00337 {
00338 if (Data == NULL)
00339 Data = new T3[FrameSize];
00340 if (Data != NULL)
00341 {
00342 DCMIMGLE_DEBUG("applying VOI transformation with LUT (" << vlut->getCount() << " entries)");
00343 const DiDisplayLUT *dlut = NULL;
00344 const double minvalue = vlut->getMinValue();
00345 const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low) + 1;
00346 register unsigned long i;
00347 if (minvalue == vlut->getMaxValue())
00348 {
00349 T3 value;
00350 if ((plut != NULL) && (plut->isValid()))
00351 {
00352 DCMIMGLE_DEBUG("applying presentation LUT transformation");
00353 createDisplayLUT(dlut, disp, plut->getBits());
00354 const Uint32 value2 = OFstatic_cast(Uint32, (minvalue / OFstatic_cast(double, vlut->getAbsMaxRange())) * plut->getCount());
00355 if (dlut != NULL)
00356 {
00357 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #1 - UNTESTED");
00358 if (low > high)
00359 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, plut->getAbsMaxRange() - plut->getValue(value2) - 1)));
00360 else
00361 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, plut->getValue(value2))));
00362 } else {
00363 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #2");
00364 value = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * outrange / OFstatic_cast(double, plut->getAbsMaxRange()));
00365 }
00366 } else {
00367 createDisplayLUT(dlut, disp, vlut->getBits());
00368 if (dlut != NULL)
00369 {
00370 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #3 - UNTESTED");
00371 if (low > high)
00372 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, vlut->getAbsMaxRange() - minvalue - 1)));
00373 else
00374 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, minvalue)));
00375 } else {
00376 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #4");
00377 value = OFstatic_cast(T3, OFstatic_cast(double, low) + (minvalue / OFstatic_cast(double, vlut->getAbsMaxRange())) * outrange);
00378 }
00379 }
00380 OFBitmanipTemplate<T3>::setMem(Data, value, Count);
00381 } else {
00382 register T2 value = 0;
00383 const T2 absmin = OFstatic_cast(T2, inter->getAbsMinimum());
00384 const T2 firstentry = vlut->getFirstEntry(value);
00385 const T2 lastentry = vlut->getLastEntry(value);
00386 const unsigned long ocnt = OFstatic_cast(unsigned long, inter->getAbsMaxRange());
00387 register const T1 *p = pixel + start;
00388 register T3 *q = Data;
00389 T3 *lut = NULL;
00390 if ((plut != NULL) && (plut->isValid()))
00391 {
00392 DCMIMGLE_DEBUG("applying presentation LUT transformation");
00393 createDisplayLUT(dlut, disp, plut->getBits());
00394 register Uint32 value2;
00395 const Uint32 pcnt = plut->getCount();
00396 const double gradient1 = OFstatic_cast(double, pcnt) / OFstatic_cast(double, vlut->getAbsMaxRange());
00397 const Uint32 firstvalue = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getFirstValue()) * gradient1);
00398 const Uint32 lastvalue = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getLastValue()) * gradient1);
00399 if (initOptimizationLUT(lut, ocnt))
00400 {
00401 q = lut;
00402 if (dlut != NULL)
00403 {
00404 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #5");
00405 if (low > high)
00406 {
00407 const Uint16 maxvalue = OFstatic_cast(Uint16, plut->getAbsMaxRange() - 1);
00408 for (i = 0; i < ocnt; ++i)
00409 {
00410 value = OFstatic_cast(T2, i) + absmin;
00411 if (value <= firstentry)
00412 value2 = firstvalue;
00413 else if (value >= lastentry)
00414 value2 = lastvalue;
00415 else
00416 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00417 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - plut->getValue(value2))));
00418 }
00419 } else {
00420 for (i = 0; i < ocnt; ++i)
00421 {
00422 value = OFstatic_cast(T2, i) + absmin;
00423 if (value <= firstentry)
00424 value2 = firstvalue;
00425 else if (value >= lastentry)
00426 value2 = lastvalue;
00427 else
00428 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00429 *(q++) = OFstatic_cast(T3, dlut->getValue(plut->getValue(value2)));
00430 }
00431 }
00432 } else {
00433 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #6");
00434 const double gradient2 = outrange / OFstatic_cast(double, plut->getAbsMaxRange());
00435 for (i = 0; i < ocnt; ++i)
00436 {
00437 value = OFstatic_cast(T2, i) + absmin;
00438 if (value <= firstentry)
00439 value2 = firstvalue;
00440 else if (value >= lastentry)
00441 value2 = lastvalue;
00442 else
00443 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00444 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
00445 }
00446 }
00447 const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());
00448 q = Data;
00449 for (i = Count; i != 0; --i)
00450 *(q++) = *(lut0 + (*(p++)));
00451 }
00452 if (lut == NULL)
00453 {
00454 if (dlut != NULL)
00455 {
00456 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #7");
00457 if (low > high)
00458 {
00459 const Uint16 maxvalue = OFstatic_cast(Uint16, vlut->getAbsMaxRange() - 1);
00460 for (i = Count; i != 0; --i)
00461 {
00462 value = OFstatic_cast(T2, *(p++));
00463 if (value <= firstentry)
00464 value2 = firstvalue;
00465 else if (value >= lastentry)
00466 value2 = lastvalue;
00467 else
00468 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00469 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - plut->getValue(value2))));
00470 }
00471 } else {
00472 for (i = Count; i != 0; --i)
00473 {
00474 value = OFstatic_cast(T2, *(p++));
00475 if (value <= firstentry)
00476 value2 = firstvalue;
00477 else if (value >= lastentry)
00478 value2 = lastvalue;
00479 else
00480 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00481 *(q++) = OFstatic_cast(T3, dlut->getValue(plut->getValue(value2)));
00482 }
00483 }
00484 } else {
00485 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #8");
00486 const double gradient2 = outrange / OFstatic_cast(double, plut->getAbsMaxRange());
00487 for (i = Count; i != 0; --i)
00488 {
00489 value = OFstatic_cast(T2, *(p++));
00490 if (value <= firstentry)
00491 value2 = firstvalue;
00492 else if (value >= lastentry)
00493 value2 = lastvalue;
00494 else
00495 value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
00496 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
00497 }
00498 }
00499 }
00500 } else {
00501 createDisplayLUT(dlut, disp, vlut->getBits());
00502 const double gradient = outrange / OFstatic_cast(double, vlut->getAbsMaxRange());
00503 const T3 firstvalue = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getFirstValue()) * gradient);
00504 const T3 lastvalue = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getLastValue()) * gradient);
00505 if (initOptimizationLUT(lut, ocnt))
00506 {
00507 q = lut;
00508 if (dlut != NULL)
00509 {
00510 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #9");
00511 if (low > high)
00512 {
00513 const Uint16 maxvalue = OFstatic_cast(Uint16, vlut->getAbsMaxRange() - 1);
00514 for (i = 0; i < ocnt; ++i)
00515 {
00516 value = OFstatic_cast(T2, i) + absmin;
00517 if (value < firstentry)
00518 value = firstentry;
00519 else if (value > lastentry)
00520 value = lastentry;
00521 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - vlut->getValue(value))));
00522 }
00523 } else {
00524 for (i = 0; i < ocnt; ++i)
00525 {
00526 value = OFstatic_cast(T2, i) + absmin;
00527 if (value < firstentry)
00528 value = firstentry;
00529 else if (value > lastentry)
00530 value = lastentry;
00531 *(q++) = OFstatic_cast(T3, dlut->getValue(vlut->getValue(value)));
00532 }
00533 }
00534 } else {
00535 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #10");
00536 for (i = 0; i < ocnt; ++i)
00537 {
00538 value = OFstatic_cast(T2, i) + absmin;
00539 if (value <= firstentry)
00540 *(q++) = firstvalue;
00541 else if (value >= lastentry)
00542 *(q++) = lastvalue;
00543 else
00544 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getValue(value)) * gradient);
00545 }
00546 }
00547 const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());
00548 q = Data;
00549 for (i = Count; i != 0; --i)
00550 *(q++) = *(lut0 + (*(p++)));
00551 }
00552 if (lut == NULL)
00553 {
00554 if (dlut != NULL)
00555 {
00556 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #11");
00557 if (low > high)
00558 {
00559 const Uint16 maxvalue = OFstatic_cast(Uint16, vlut->getAbsMaxRange() - 1);
00560 for (i = Count; i != 0; --i)
00561 {
00562 value = OFstatic_cast(T2, *(p++));
00563 if (value < firstentry)
00564 value = firstentry;
00565 else if (value > lastentry)
00566 value = lastentry;
00567 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - vlut->getValue(value))));
00568 }
00569 } else {
00570 for (i = Count; i != 0; --i)
00571 {
00572 value = OFstatic_cast(T2, *(p++));
00573 if (value < firstentry)
00574 value = firstentry;
00575 else if (value > lastentry)
00576 value = lastentry;
00577 *(q++) = OFstatic_cast(T3, dlut->getValue(vlut->getValue(value)));
00578 }
00579 }
00580 } else {
00581 DCMIMGLE_TRACE("monochrome rendering: VOI LUT #12");
00582 for (i = 0; i < Count; ++i)
00583 {
00584 value = OFstatic_cast(T2, *(p++));
00585 if (value <= firstentry)
00586 *(q++) = firstvalue;
00587 else if (value >= lastentry)
00588 *(q++) = lastvalue;
00589 else
00590 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getValue(value)) * gradient);
00591 }
00592 }
00593 }
00594 }
00595 delete[] lut;
00596 }
00597 if (Count < FrameSize)
00598 OFBitmanipTemplate<T3>::zeroMem(Data + Count, FrameSize - Count);
00599 }
00600 } else
00601 Data = NULL;
00602 }
00603
00613 void nowindow(const DiMonoPixel *inter,
00614 const Uint32 start,
00615 const DiLookupTable *plut,
00616 DiDisplayFunction *disp,
00617 const T3 low,
00618 const T3 high)
00619 {
00620 const DiDisplayLUT *dlut = NULL;
00621 const T1 *pixel = OFstatic_cast(const T1 *, inter->getData());
00622 if (pixel != NULL)
00623 {
00624 if (Data == NULL)
00625 Data = new T3[FrameSize];
00626 if (Data != NULL)
00627 {
00628 DCMIMGLE_DEBUG("applying no VOI transformation (linear scaling)");
00629 const double absmin = inter->getAbsMinimum();
00630 const double absmax = inter->getAbsMaximum();
00631 const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low) + 1;
00632 const unsigned long ocnt = OFstatic_cast(unsigned long, inter->getAbsMaxRange());
00633 register const T1 *p = pixel + start;
00634 register T3 *q = Data;
00635 register unsigned long i;
00636 T3 *lut = NULL;
00637 if ((plut != NULL) && (plut->isValid()))
00638 {
00639 DCMIMGLE_DEBUG("applying presentation LUT transformation");
00640 createDisplayLUT(dlut, disp, plut->getBits());
00641 register Uint32 value;
00642 const double gradient1 = OFstatic_cast(double, plut->getCount()) / inter->getAbsMaxRange();
00643 const double gradient2 = outrange / OFstatic_cast(double, plut->getAbsMaxRange());
00644 if (initOptimizationLUT(lut, ocnt))
00645 {
00646 q = lut;
00647 if (dlut != NULL)
00648 {
00649 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #1");
00650 if (low > high)
00651 {
00652 const Uint16 maxvalue = OFstatic_cast(Uint16, plut->getAbsMaxRange() - 1);
00653 for (i = 0; i < ocnt; ++i)
00654 {
00655 value = OFstatic_cast(Uint32, OFstatic_cast(double, i) * gradient1);
00656 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - plut->getValue(value))));
00657 }
00658 } else {
00659 for (i = 0; i < ocnt; ++i)
00660 {
00661 value = OFstatic_cast(Uint32, OFstatic_cast(double, i) * gradient1);
00662 *(q++) = OFstatic_cast(T3, dlut->getValue(plut->getValue(value)));
00663 }
00664 }
00665 } else {
00666 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #2");
00667 for (i = 0; i < ocnt; ++i)
00668 {
00669 value = OFstatic_cast(Uint32, OFstatic_cast(double, i) * gradient1);
00670 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value)) * gradient2);
00671 }
00672 }
00673 const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());
00674 q = Data;
00675 for (i = Count; i != 0; --i)
00676 *(q++) = *(lut0 + (*(p++)));
00677 }
00678 if (lut == NULL)
00679 {
00680 if (dlut != NULL)
00681 {
00682 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #3");
00683 if (low > high)
00684 {
00685 const Uint16 maxvalue = OFstatic_cast(Uint16, plut->getAbsMaxRange() - 1);
00686 for (i = Count; i != 0; --i)
00687 {
00688 value = OFstatic_cast(Uint32, (OFstatic_cast(double, *(p++)) - absmin) * gradient1);
00689 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, maxvalue - plut->getValue(value))));
00690 }
00691 } else {
00692 for (i = Count; i != 0; --i)
00693 {
00694 value = OFstatic_cast(Uint32, (OFstatic_cast(double, *(p++)) - absmin) * gradient1);
00695 *(q++) = OFstatic_cast(T3, dlut->getValue(plut->getValue(value)));
00696 }
00697 }
00698 } else {
00699 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #4");
00700 for (i = Count; i != 0; --i)
00701 {
00702 value = OFstatic_cast(Uint32, (OFstatic_cast(double, *(p++)) - absmin) * gradient1);
00703 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value)) * gradient2);
00704 }
00705 }
00706 }
00707 } else {
00708 createDisplayLUT(dlut, disp, inter->getBits());
00709 register const double gradient = outrange / (inter->getAbsMaxRange());
00710 if (initOptimizationLUT(lut, ocnt))
00711 {
00712 q = lut;
00713 if (dlut != NULL)
00714 {
00715 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #5");
00716 if (low > high)
00717 {
00718 for (i = ocnt; i != 0; --i)
00719 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, i - 1)));
00720 } else {
00721 for (i = 0; i < ocnt; ++i)
00722 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, i)));
00723 }
00724 } else {
00725 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #6");
00726 for (i = 0; i < ocnt; ++i)
00727 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, i) * gradient);
00728 }
00729 const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());
00730 q = Data;
00731 for (i = Count; i != 0; --i)
00732 *(q++) = *(lut0 + (*(p++)));
00733 }
00734 if (lut == NULL)
00735 {
00736 if (dlut != NULL)
00737 {
00738 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #7");
00739 if (low > high)
00740 {
00741 for (i = Count; i != 0; --i)
00742 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, absmax - (OFstatic_cast(double, *(p++)) - absmin))));
00743 } else {
00744 for (i = Count; i != 0; --i)
00745 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, OFstatic_cast(double, *(p++)) - absmin)));
00746 }
00747 } else {
00748 DCMIMGLE_TRACE("monochrome rendering: VOI NONE #8");
00749 for (i = Count; i != 0; --i)
00750 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + (OFstatic_cast(double, *(p++)) - absmin) * gradient);
00751 }
00752 }
00753 }
00754 delete[] lut;
00755 if (Count < FrameSize)
00756 OFBitmanipTemplate<T3>::zeroMem(Data + Count, FrameSize - Count);
00757 }
00758 } else
00759 Data = NULL;
00760 }
00761
00773 void sigmoid(const DiMonoPixel *inter,
00774 const Uint32 start,
00775 const DiLookupTable *plut,
00776 DiDisplayFunction *disp,
00777 const double center,
00778 const double width,
00779 const T3 low,
00780 const T3 high)
00781 {
00782 const T1 *pixel = OFstatic_cast(const T1 *, inter->getData());
00783 if (pixel != NULL)
00784 {
00785 if (Data == NULL)
00786 Data = new T3[FrameSize];
00787 if (Data != NULL)
00788 {
00789 DCMIMGLE_DEBUG("applying sigmoid VOI transformation with window center = " << center << ", width = " << width);
00790 const DiDisplayLUT *dlut = NULL;
00791 const double absmin = inter->getAbsMinimum();
00792 const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low);
00793 const unsigned long ocnt = OFstatic_cast(unsigned long, inter->getAbsMaxRange());
00794 register const T1 *p = pixel + start;
00795 register T3 *q = Data;
00796 register unsigned long i;
00797 register double value;
00798 T3 *lut = NULL;
00799 if ((plut != NULL) && (plut->isValid()))
00800 {
00801 DCMIMGLE_DEBUG("applying presentation LUT transformation");
00802 createDisplayLUT(dlut, disp, plut->getBits());
00803 register Uint32 value2;
00804 const double plutcnt_1 = OFstatic_cast(double, plut->getCount() - 1);
00805 const double plutmax_1 = OFstatic_cast(double, plut->getAbsMaxRange() - 1);
00806 if (initOptimizationLUT(lut, ocnt))
00807 {
00808 q = lut;
00809 if (dlut != NULL)
00810 {
00811 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #1");
00812 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
00813 const double offset = (low > high) ? maxvalue : 0;
00814 const double gradient = (low > high) ? (-maxvalue / plutmax_1) : (maxvalue / plutmax_1);
00815 for (i = 0; i < ocnt; ++i)
00816 {
00817 value = OFstatic_cast(double, i) + absmin;
00818 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
00819 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + OFstatic_cast(double, plut->getValue(value2)) * gradient)));
00820 }
00821 } else {
00822 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #2");
00823 const double gradient = outrange / plutmax_1;
00824 for (i = 0; i < ocnt; ++i)
00825 {
00826 value = OFstatic_cast(double, i) + absmin;
00827 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
00828 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient);
00829 }
00830 }
00831 const T3 *lut0 = lut - OFstatic_cast(T2, absmin);
00832 q = Data;
00833 for (i = Count; i != 0; --i)
00834 *(q++) = *(lut0 + (*(p++)));
00835 }
00836 if (lut == NULL)
00837 {
00838 if (dlut != NULL)
00839 {
00840 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #3");
00841 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
00842 const double offset = (low > high) ? maxvalue : 0;
00843 const double gradient = (low > high) ? (-maxvalue / plutmax_1) : (maxvalue / plutmax_1);
00844 for (i = Count; i != 0; --i)
00845 {
00846 value = OFstatic_cast(double, *(p++));
00847 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
00848 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + OFstatic_cast(double, plut->getValue(value2)) * gradient)));
00849 }
00850 } else {
00851 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #4");
00852 const double gradient = outrange / plutmax_1;
00853 for (i = Count; i != 0; --i)
00854 {
00855 value = OFstatic_cast(double, *(p++));
00856 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
00857 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient);
00858 }
00859 }
00860 }
00861 } else {
00862 createDisplayLUT(dlut, disp, bitsof(T1));
00863 if (initOptimizationLUT(lut, ocnt))
00864 {
00865 q = lut;
00866 if (dlut != NULL)
00867 {
00868 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #5");
00869 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
00870 const double outrange2 = (low > high) ? -maxvalue : maxvalue;
00871 const double offset = (low > high) ? maxvalue : 0;
00872 for (i = 0; i < ocnt; ++i)
00873 {
00874 value = OFstatic_cast(double, i) + absmin;
00875 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + outrange2 / (1 + exp(-4 * (value - center) / width)))));
00876 }
00877 } else {
00878 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #6");
00879 for (i = 0; i < ocnt; ++i)
00880 {
00881 value = OFstatic_cast(double, i) + absmin;
00882 *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)));
00883 }
00884 }
00885 const T3 *lut0 = lut - OFstatic_cast(T2, absmin);
00886 q = Data;
00887 for (i = Count; i != 0; --i)
00888 *(q++) = *(lut0 + (*(p++)));
00889 }
00890 if (lut == NULL)
00891 {
00892 if (dlut != NULL)
00893 {
00894 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #7");
00895 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
00896 const double outrange2 = (low > high) ? -maxvalue : maxvalue;
00897 const double offset = (low > high) ? maxvalue : 0;
00898 for (i = Count; i != 0; --i)
00899 {
00900 value = OFstatic_cast(double, *(p++));
00901 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + outrange2 / (1 + exp(-4 * (value - center) / width)))));
00902 }
00903 } else {
00904 DCMIMGLE_TRACE("monochrome rendering: VOI SIGMOID #8");
00905 for (i = Count; i != 0; --i)
00906 {
00907 value = OFstatic_cast(double, *(p++));
00908 *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)));
00909 }
00910 }
00911 }
00912 }
00913 delete[] lut;
00914 if (Count < FrameSize)
00915 OFBitmanipTemplate<T3>::zeroMem(Data + Count, FrameSize - Count);
00916 }
00917 } else
00918 Data = NULL;
00919 }
00920
00932 void window(const DiMonoPixel *inter,
00933 const Uint32 start,
00934 const DiLookupTable *plut,
00935 DiDisplayFunction *disp,
00936 const double center,
00937 const double width,
00938 const T3 low,
00939 const T3 high)
00940 {
00941 const T1 *pixel = OFstatic_cast(const T1 *, inter->getData());
00942 if (pixel != NULL)
00943 {
00944 if (Data == NULL)
00945 Data = new T3[FrameSize];
00946 if (Data != NULL)
00947 {
00948 DCMIMGLE_DEBUG("applying linear VOI transformation with window center = " << center << ", width = " << width);
00949 const DiDisplayLUT *dlut = NULL;
00950 const double absmin = inter->getAbsMinimum();
00951 const double width_1 = width - 1;
00952 const double leftBorder = center - 0.5 - width_1 / 2;
00953 const double rightBorder = center - 0.5 + width_1 / 2;
00954 const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low);
00955 const unsigned long ocnt = OFstatic_cast(unsigned long, inter->getAbsMaxRange());
00956 register const T1 *p = pixel + start;
00957 register T3 *q = Data;
00958 register unsigned long i;
00959 register double value;
00960 T3 *lut = NULL;
00961 if ((plut != NULL) && (plut->isValid()))
00962 {
00963 DCMIMGLE_DEBUG("applying presentation LUT transformation");
00964 createDisplayLUT(dlut, disp, plut->getBits());
00965 register Uint32 value2;
00966 const Uint32 pcnt = plut->getCount();
00967 const double plutmax_1 = OFstatic_cast(double, plut->getAbsMaxRange()) - 1;
00968 const double gradient1 = (width_1 == 0) ? 0 : OFstatic_cast(double, pcnt - 1) / width_1;
00969 if (initOptimizationLUT(lut, ocnt))
00970 {
00971 q = lut;
00972 if (dlut != NULL)
00973 {
00974 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #1");
00975 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
00976 const double offset = (low > high) ? maxvalue : 0;
00977 const double gradient2 = (low > high) ? (-maxvalue / plutmax_1) : (maxvalue / plutmax_1);
00978 for (i = 0; i < ocnt; ++i)
00979 {
00980 value = OFstatic_cast(double, i) + absmin;
00981 if (value <= leftBorder)
00982 value2 = 0;
00983 else if (value > rightBorder)
00984 value2 = pcnt - 1;
00985 else
00986 value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
00987 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + OFstatic_cast(double, plut->getValue(value2)) * gradient2)));
00988 }
00989 } else {
00990 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #2");
00991 const double gradient2 = outrange / plutmax_1;
00992 for (i = 0; i < ocnt; ++i)
00993 {
00994 value = OFstatic_cast(double, i) + absmin;
00995 if (value <= leftBorder)
00996 value2 = 0;
00997 else if (value > rightBorder)
00998 value2 = pcnt - 1;
00999 else
01000 value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
01001 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
01002 }
01003 }
01004 const T3 *lut0 = lut - OFstatic_cast(T2, absmin);
01005 q = Data;
01006 for (i = Count; i != 0; --i)
01007 *(q++) = *(lut0 + (*(p++)));
01008 }
01009 if (lut == NULL)
01010 {
01011 if (dlut != NULL)
01012 {
01013 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #3");
01014 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
01015 const double offset = (low > high) ? maxvalue : 0;
01016 const double gradient2 = (low > high) ? (-maxvalue / plutmax_1) : (maxvalue / plutmax_1);
01017 for (i = Count; i != 0; --i)
01018 {
01019 value = OFstatic_cast(double, *(p++));
01020 if (value <= leftBorder)
01021 value2 = 0;
01022 else if (value > rightBorder)
01023 value2 = pcnt - 1;
01024 else
01025 value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
01026 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + OFstatic_cast(double, plut->getValue(value2)) * gradient2)));
01027 }
01028 } else {
01029 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #4");
01030 const double gradient2 = outrange / plutmax_1;
01031 for (i = Count; i != 0; --i)
01032 {
01033 value = OFstatic_cast(double, *(p++));
01034 if (value <= leftBorder)
01035 value2 = 0;
01036 else if (value > rightBorder)
01037 value2 = pcnt - 1;
01038 else
01039 value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
01040 *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
01041 }
01042 }
01043 }
01044 } else {
01045 createDisplayLUT(dlut, disp, bitsof(T1));
01046 if (initOptimizationLUT(lut, ocnt))
01047 {
01048 q = lut;
01049 if (dlut != NULL)
01050 {
01051 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #5");
01052 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
01053 const double offset = (low > high) ? maxvalue : 0;
01054 const double gradient = (width_1 == 0) ? 0 : ((low > high) ? (-maxvalue / width_1) : (maxvalue / width_1));
01055 for (i = 0; i < ocnt; ++i)
01056 {
01057 value = OFstatic_cast(double, i) + absmin - leftBorder;
01058 if (value < 0)
01059 value = 0;
01060 else if (value > width_1)
01061 value = width_1;
01062 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + value * gradient)));
01063 }
01064 } else {
01065 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #6");
01066 const double offset = (width_1 == 0) ? 0 : (high - ((center - 0.5) / width_1 + 0.5) * outrange);
01067 const double gradient = (width_1 == 0) ? 0 : outrange / width_1;
01068 for (i = 0; i < ocnt; ++i)
01069 {
01070 value = OFstatic_cast(double, i) + absmin;
01071 if (value <= leftBorder)
01072 *(q++) = low;
01073 else if (value > rightBorder)
01074 *(q++) = high;
01075 else
01076 *(q++) = OFstatic_cast(T3, offset + value * gradient);
01077 }
01078 }
01079 const T3 *lut0 = lut - OFstatic_cast(T2, absmin);
01080 q = Data;
01081 for (i = Count; i != 0; --i)
01082 *(q++) = *(lut0 + (*(p++)));
01083 }
01084 if (lut == NULL)
01085 {
01086 if (dlut != NULL)
01087 {
01088 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #7");
01089 const double maxvalue = OFstatic_cast(double, dlut->getCount() - 1);
01090 const double offset = (low > high) ? maxvalue : 0;
01091 const double gradient = (width_1 == 0) ? 0 : ((low > high) ? (-maxvalue / width_1) : (maxvalue / width_1));
01092 for (i = Count; i != 0; --i)
01093 {
01094 value = OFstatic_cast(double, *(p++)) - leftBorder;
01095 if (value < 0)
01096 value = 0;
01097 else if (value > width_1)
01098 value = width_1;
01099 *(q++) = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, offset + value * gradient)));
01100 }
01101 } else {
01102 DCMIMGLE_TRACE("monochrome rendering: VOI LINEAR #8");
01103 const double offset = (width_1 == 0) ? 0 : (high - ((center - 0.5) / width_1 + 0.5) * outrange);
01104 const double gradient = (width_1 == 0) ? 0 : outrange / width_1;
01105 for (i = Count; i != 0; --i)
01106 {
01107 value = OFstatic_cast(double, *(p++));
01108 if (value <= leftBorder)
01109 *(q++) = low;
01110 else if (value > rightBorder)
01111 *(q++) = high;
01112 else
01113 *(q++) = OFstatic_cast(T3, offset + value * gradient);
01114 }
01115 }
01116 }
01117 }
01118 delete[] lut;
01119 if (Count < FrameSize)
01120 OFBitmanipTemplate<T3>::zeroMem(Data + Count, FrameSize - Count);
01121 }
01122 } else
01123 Data = NULL;
01124 }
01125
01126
01135 void overlay(DiOverlay *overlays[2],
01136 DiDisplayFunction *disp,
01137 const Uint16 columns,
01138 const Uint16 rows,
01139 const unsigned long frame)
01140 {
01141 if ((Data != NULL) && (overlays != NULL))
01142 {
01143 for (unsigned int j = 0; j < 2; ++j)
01144 {
01145 if (overlays[j] != NULL)
01146 {
01147 if (overlays[j]->getCount() > 0)
01148 DCMIMGLE_DEBUG("applying " << ((j == 0) ? "built-in" : "additional") << " overlay planes");
01149 const signed long left_pos = overlays[j]->getLeft();
01150 const signed long top_pos = overlays[j]->getTop();
01151 register DiOverlayPlane *plane;
01152 for (unsigned int i = 0; i < overlays[j]->getCount(); ++i)
01153 {
01154 plane = overlays[j]->getPlane(i);
01155 if ((plane != NULL) && plane->isVisible() && plane->reset(frame))
01156 {
01157 register T3 *q;
01158 register Uint16 x;
01159 register Uint16 y;
01160 const Uint16 xmin = (plane->getLeft(left_pos) > 0) ? plane->getLeft(left_pos) : 0;
01161 const Uint16 ymin = (plane->getTop(top_pos) > 0) ? plane->getTop(top_pos) : 0;
01162 const Uint16 xmax = (plane->getRight(left_pos) < columns) ? plane->getRight(left_pos) : columns;
01163 const Uint16 ymax = (plane->getBottom(top_pos) < rows) ? plane->getBottom(top_pos) : rows;
01164 const T3 maxvalue = OFstatic_cast(T3, DicomImageClass::maxval(bitsof(T3)));
01165 switch (plane->getMode())
01166 {
01167 case EMO_Replace:
01168 {
01169 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'replace' mode");
01170 const T3 fore = OFstatic_cast(T3, plane->getForeground() * maxvalue);
01171 for (y = ymin; y < ymax; ++y)
01172 {
01173 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01174 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01175 for (x = xmin; x < xmax; ++x, ++q)
01176 {
01177 if (plane->getNextBit())
01178 *q = fore;
01179 }
01180 }
01181 break;
01182 }
01183 case EMO_ThresholdReplace:
01184 {
01185 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'threshold replace' mode");
01186 const T3 fore = OFstatic_cast(T3, plane->getForeground() * maxvalue);
01187 const T3 thresh = OFstatic_cast(T3, plane->getThreshold() * maxvalue);
01188 for (y = ymin; y < ymax; ++y)
01189 {
01190 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01191 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01192 for (x = xmin; x < xmax; ++x, ++q)
01193 {
01194 if (plane->getNextBit())
01195 *q = (*q <= thresh) ? fore : 1;
01196 }
01197 }
01198 break;
01199 }
01200 case EMO_Complement:
01201 {
01202 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'complement' mode");
01203 const T3 thresh = OFstatic_cast(T3, DicomImageClass::maxval(bitsof(T3) / 2));
01204 for (y = ymin; y < ymax; ++y)
01205 {
01206 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01207 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01208 for (x = xmin; x < xmax; ++x, ++q)
01209 {
01210 if (plane->getNextBit())
01211 *q = (*q <= thresh) ? maxvalue : 0;
01212 }
01213 }
01214 break;
01215 }
01216 case EMO_InvertBitmap:
01217 {
01218 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'invert bitmap' mode");
01219 const T3 fore = OFstatic_cast(T3, plane->getForeground() * maxvalue);
01220 for (y = ymin; y < ymax; ++y)
01221 {
01222 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01223 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01224 for (x = xmin; x < xmax; ++x, ++q)
01225 {
01226 if (!plane->getNextBit())
01227 *q = fore;
01228 }
01229 }
01230 break;
01231 }
01232 case EMO_RegionOfInterest:
01233 {
01234 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'region of interest' mode");
01235 const int dim = bitsof(T3) / 2;
01236 for (y = ymin; y < ymax; ++y)
01237 {
01238 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01239 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01240 for (x = xmin; x < xmax; ++x, ++q)
01241 {
01242 if (!plane->getNextBit())
01243 *q = *q >> dim;
01244 }
01245 }
01246 break;
01247 }
01248 case EMO_BitmapShutter:
01249 {
01250 DCMIMGLE_DEBUG("applying overlay plane " << (i + 1) << " with 'bitmap shutter' mode");
01251 register T3 fore = OFstatic_cast(T3, OFstatic_cast(double, maxvalue) * OFstatic_cast(double, plane->getPValue()) / OFstatic_cast(double, DicomImageClass::maxval(WIDTH_OF_PVALUES)));
01252 if ((disp != NULL) && (disp->isValid()))
01253 {
01254 const DiDisplayLUT *dlut = disp->getLookupTable(WIDTH_OF_PVALUES);
01255 if ((dlut != NULL) && (dlut->isValid()))
01256 fore = OFstatic_cast(T3, dlut->getValue(plane->getPValue()));
01257 }
01258 for (y = ymin; y < ymax; ++y)
01259 {
01260 plane->setStart(OFstatic_cast(Uint16, left_pos + xmin), OFstatic_cast(Uint16, top_pos + y));
01261 q = Data + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, columns) + OFstatic_cast(unsigned long, xmin);
01262 for (x = xmin; x < xmax; ++x, ++q)
01263 {
01264 if (plane->getNextBit())
01265 *q = fore;
01266 }
01267 }
01268 break;
01269 }
01270 default:
01271 DCMIMGLE_WARN("unhandled overlay mode (" << OFstatic_cast(int, plane->getMode()) << ")");
01272 }
01273 }
01274 }
01275 }
01276 }
01277 }
01278 }
01279
01280
01282 T3 *Data;
01284 int DeleteData;
01285
01286 #ifdef PASTEL_COLOR_OUTPUT
01287 DiMonoColorOutputPixelTemplate<T1, T3> *ColorData;
01288 #else
01289
01290 DiMonoOutputPixel *ColorData;
01291 #endif
01292
01293
01294
01295 DiMonoOutputPixelTemplate(const DiMonoOutputPixelTemplate<T1,T2,T3> &);
01296 DiMonoOutputPixelTemplate<T1,T2,T3> &operator=(const DiMonoOutputPixelTemplate<T1,T2,T3> &);
01297 };
01298
01299
01300 #endif
01301
01302
01303
01304
01305
01306
01307
01308
01309
01310
01311
01312
01313
01314
01315
01316
01317
01318
01319
01320
01321
01322
01323
01324
01325
01326
01327
01328
01329
01330
01331
01332
01333
01334
01335
01336
01337
01338
01339
01340
01341
01342
01343
01344
01345
01346
01347
01348
01349
01350
01351
01352
01353
01354
01355
01356
01357
01358
01359
01360
01361
01362
01363
01364
01365
01366
01367
01368
01369
01370
01371
01372
01373
01374
01375
01376
01377
01378
01379
01380
01381
01382
01383
01384
01385
01386
01387
01388
01389
01390
01391
01392
01393
01394
01395
01396
01397
01398
01399
01400
01401
01402
01403
01404
01405
01406
01407
01408
01409
01410
01411
01412
01413
01414
01415
01416
01417
01418
01419
01420
01421
01422
01423
01424
01425
01426
01427
01428
01429
01430
01431
01432
01433
01434
01435
01436
01437
01438
01439
01440
01441
01442
01443
01444
01445
01446
01447
01448
01449
01450
01451
01452
01453
01454
01455
01456
01457
01458
01459
01460
01461
01462
01463
01464
01465
01466
01467
01468
01469
01470
01471
01472
01473
01474
01475
01476
01477
01478
01479
01480
01481
01482
01483
01484
01485
01486
01487
01488
01489
01490
01491
01492
01493
01494
01495
01496
01497
01498
01499
01500
01501
01502
01503
01504
01505
01506
01507
01508
01509
01510
01511
01512