summaryrefslogtreecommitdiffstats
path: root/tksao
diff options
context:
space:
mode:
authorWilliam Joye <wjoye@cfa.harvard.edu>2019-09-25 18:49:21 (GMT)
committerWilliam Joye <wjoye@cfa.harvard.edu>2019-09-25 18:49:21 (GMT)
commit336c8740b21f24fed26559b5e5d1d347aa49a819 (patch)
tree02779a5f07f92b1a371a9594df19ce98dc041111 /tksao
parentf9b8d12a4f5df44aabc2385045956e00e0eae5df (diff)
downloadblt-336c8740b21f24fed26559b5e5d1d347aa49a819.zip
blt-336c8740b21f24fed26559b5e5d1d347aa49a819.tar.gz
blt-336c8740b21f24fed26559b5e5d1d347aa49a819.tar.bz2
backout colormapPM changes
Diffstat (limited to 'tksao')
-rw-r--r--tksao/frame/frame.C223
-rw-r--r--tksao/frame/framebase.C15
-rw-r--r--tksao/frame/framebase.h4
-rw-r--r--tksao/frame/framergb.C262
4 files changed, 503 insertions, 1 deletions
diff --git a/tksao/frame/frame.C b/tksao/frame/frame.C
index dc6a146..1225f09 100644
--- a/tksao/frame/frame.C
+++ b/tksao/frame/frame.C
@@ -555,7 +555,132 @@ void Frame::colormapCmd(int id, float b, float c, int i,
update(BASE);
}
-void Frame::colormapBeginCmd() {}
+#ifndef MAC_OSX_TK
+
+void Frame::colormapBeginCmd()
+{
+ // we need a colorScale before we can render
+ if (!validColorScale())
+ return;
+
+ // we need some fits data
+ // we assume the colorScale length will not change during motion calls
+ if (!context->cfits)
+ return;
+
+ int width = options->width;
+ int height = options->height;
+
+ // Create XImage
+ if (!(colormapXM = XGetImage(display, pixmap, 0, 0,
+ width, height, AllPlanes, ZPixmap))) {
+ internalError("Unable to Create Colormap XImage");
+ return;
+ }
+
+ // Create Pixmap
+ colormapPM =
+ Tk_GetPixmap(display, Tk_WindowId(tkwin), width, height, depth);
+ if (!colormapPM) {
+ internalError("Unable to Create Colormap Pixmap");
+ return;
+ }
+
+ // colormapGCXOR
+ colormapGCXOR = XCreateGC(display, Tk_WindowId(tkwin), 0, NULL);
+
+ // Create table index array
+ if (colormapData)
+ delete [] colormapData;
+ colormapData = new long[width*height];
+ if (!colormapData) {
+ internalError("Unable to alloc tmp data array");
+ return;
+ }
+
+ // fill data array
+ // basics
+ int bytesPerPixel = colormapXM->bits_per_pixel/8;
+
+ int length = colorScale->size() - 1;
+ int last = length * bytesPerPixel;
+
+ FitsImage* sptr = context->cfits;
+ int mosaic = isMosaic();
+
+ long* dest = colormapData;
+
+ // variable
+ double* mm = sptr->matrixToData(Coord::WIDGET).mm();
+ FitsBound* params = sptr->getDataParams(context->secMode());
+ int srcw = sptr->width();
+
+ double ll = sptr->low();
+ double hh = sptr->high();
+ double diff = hh - ll;
+
+ // main loop
+
+ SETSIGBUS
+ for (long jj=0; jj<height; jj++) {
+ for (long ii=0; ii<width; ii++, dest++) {
+ // default is bg
+ *dest = -2;
+
+ if (mosaic) {
+ sptr = context->cfits;
+
+ mm = sptr->matrixToData(Coord::WIDGET).mm();
+ params = sptr->getDataParams(context->secMode());
+ srcw = sptr->width();
+
+ ll = sptr->low();
+ hh = sptr->high();
+ diff = hh - ll;
+ }
+
+ do {
+ double xx = ii*mm[0] + jj*mm[3] + mm[6];
+ double yy = ii*mm[1] + jj*mm[4] + mm[7];
+
+ if (xx>=params->xmin && xx<params->xmax &&
+ yy>=params->ymin && yy<params->ymax) {
+ double value = sptr->getValueDouble(long(yy)*srcw + long(xx));
+
+ if (isfinite(diff) && isfinite(value)) {
+ if (value <= ll)
+ *dest = 0;
+ else if (value >= hh)
+ *dest = last;
+ else
+ *dest = (int)(((value - ll)/diff * length) + .5)*bytesPerPixel;
+ }
+ else
+ *dest = -1;
+
+ break;
+ }
+ else {
+ if (mosaic) {
+ sptr = sptr->nextMosaic();
+
+ if (sptr) {
+ mm = sptr->matrixToData(Coord::WIDGET).mm();
+ params = sptr->getDataParams(context->secMode());
+ srcw = sptr->width();
+
+ ll = sptr->low();
+ hh = sptr->high();
+ diff = hh - ll;
+ }
+ }
+ }
+ }
+ while (mosaic && sptr);
+ }
+ }
+ CLEARSIGBUS
+}
void Frame::colormapMotionCmd(int id, float b, float c, int i,
unsigned char* cells, int cnt)
@@ -577,6 +702,100 @@ void Frame::colormapMotionCmd(int id, float b, float c, int i,
updateColorCells(cells, cnt);
updateColorScale();
+ // if we have no data, stop now
+ if (!context->cfits)
+ return;
+
+ // clear ximage
+ int& width = colormapXM->width;
+ int& height = colormapXM->height;
+ char* data = colormapXM->data;
+ int bytesPerPixel = colormapXM->bits_per_pixel/8;
+ int& bytesPerLine = colormapXM->bytes_per_line;
+
+ const unsigned char* table = colorScale->colors();
+
+ long* src = colormapData;
+ for (long jj=0; jj<height; jj++) {
+ // line may be padded at end
+ char* dest = data + jj*bytesPerLine;
+
+ for (long ii=0; ii<width; ii++, src++, dest+=bytesPerPixel)
+ switch (*src) {
+ case -1:
+ memcpy(dest, nanTrueColor_, bytesPerPixel);
+ break;
+ case -2:
+ memcpy(dest, bgTrueColor_, bytesPerPixel);
+ break;
+ default:
+ memcpy(dest, table+(*src), bytesPerPixel);
+ break;
+ }
+ }
+
+ // XImage to Pixmap
+ TkPutImage(NULL, 0, display, colormapPM, widgetGC, colormapXM,
+ 0, 0, 0, 0, width, height);
+
+ // Display Pixmap
+ Vector dd = Vector() * widgetToWindow;
+ XCopyArea(display, colormapPM, Tk_WindowId(tkwin), colormapGCXOR, 0, 0,
+ width, height, dd[0], dd[1]);
+
+ // update panner
+ updatePanner();
+}
+
+void Frame::colormapEndCmd()
+{
+ if (colormapXM) {
+ XDestroyImage(colormapXM);
+ colormapXM = NULL;
+ }
+
+ if (colormapPM) {
+ Tk_FreePixmap(display, colormapPM);
+ colormapPM = 0;
+ }
+
+ if (colormapGCXOR) {
+ XFreeGC(display, colormapGCXOR);
+ colormapGCXOR = 0;
+ }
+
+ if (colormapData) {
+ delete [] colormapData;
+ colormapData = NULL;
+ }
+
+ update(BASE); // always update
+}
+
+#else
+
+void Frame::colormapBeginCmd() {}
+
+void Frame::colormapMotionCmd(int id, float b, float c, int i,
+ unsigned char* cells, int cnt)
+{
+ // we need a colorScale before we can render
+ if (!validColorScale())
+ return;
+
+ // first check for change
+ if (cmapID == id && bias == b && contrast == c && invert == i && colorCells)
+ return;
+
+ // we got a change
+ cmapID = id;
+ bias = b;
+ contrast = c;
+ invert = i;
+
+ updateColorCells(cells, cnt);
+ updateColorScale();
+
update(BASE);
updatePanner();
}
@@ -586,6 +805,8 @@ void Frame::colormapEndCmd()
update(BASE);
}
+#endif
+
void Frame::getColorbarCmd()
{
ostringstream str;
diff --git a/tksao/frame/framebase.C b/tksao/frame/framebase.C
index dafaa60..86aa528 100644
--- a/tksao/frame/framebase.C
+++ b/tksao/frame/framebase.C
@@ -16,10 +16,25 @@
FrameBase::FrameBase(Tcl_Interp* i, Tk_Canvas c, Tk_Item* item)
: Base(i, c, item)
{
+#ifndef MAC_OSX_TK
+ colormapXM = NULL;
+ colormapPM = 0;
+ colormapGCXOR = 0;
+#endif
}
FrameBase::~FrameBase()
{
+#ifndef MAC_OSX_TK
+ if (colormapXM)
+ XDestroyImage(colormapXM);
+
+ if (colormapPM)
+ Tk_FreePixmap(display, colormapPM);
+
+ if (colormapGCXOR)
+ XFreeGC(display, colormapGCXOR);
+#endif
}
void FrameBase::getInfoCmd(const Vector& vv, Coord::InternalSystem ref,
diff --git a/tksao/frame/framebase.h b/tksao/frame/framebase.h
index 457b5e3..70a1bd7 100644
--- a/tksao/frame/framebase.h
+++ b/tksao/frame/framebase.h
@@ -9,6 +9,10 @@
class FrameBase : public Base {
protected:
+ XImage* colormapXM; // colormap dest ximage
+ Pixmap colormapPM; // colormap pixmap
+ GC colormapGCXOR; // GC for interactive colormap
+
Vector iisLastCursor; // iis cursor state info
private:
diff --git a/tksao/frame/framergb.C b/tksao/frame/framergb.C
index 50ed145..7e77bb8 100644
--- a/tksao/frame/framergb.C
+++ b/tksao/frame/framergb.C
@@ -500,6 +500,266 @@ void FrameRGB::colormapCmd(float rb, float gb, float bb,
update(BASE);
}
+#ifndef MAC_OSX_TK
+
+void FrameRGB::colormapBeginCmd()
+{
+ // we need a colorScale before we can render
+ if (!validColorScale())
+ return;
+
+ // we need some fits data
+ // we assume the colorScale length will not change during motion calls
+ if (!context[0].fits && !context[1].fits && !context[2].fits)
+ return;
+
+ int width = options->width;
+ int height = options->height;
+
+ // Create XImage
+ if (!(colormapXM = XGetImage(display, pixmap, 0, 0,
+ width, height, AllPlanes, ZPixmap))) {
+ internalError("Unable to Create Colormap XImage");
+ return;
+ }
+
+ // Create Pixmap
+ colormapPM =
+ Tk_GetPixmap(display, Tk_WindowId(tkwin), width, height, depth);
+ if (!colormapPM) {
+ internalError("Unable to Create Colormap Pixmap");
+ return;
+ }
+
+ // colormapGCXOR
+ colormapGCXOR = XCreateGC(display, Tk_WindowId(tkwin), 0, NULL);
+
+ // Create table index array
+ for (int kk=0; kk<3; kk++) {
+ if (colormapData[kk])
+ delete [] colormapData[kk];
+ colormapData[kk] = new long[width*height];
+
+ if (!colormapData[kk]) {
+ internalError("Unable to alloc tmp data array");
+ return;
+ }
+ }
+
+ SETSIGBUS
+
+ // fill data array
+ for (int kk=0; kk<3; kk++) {
+ if (!view[kk] || !context[kk].fits)
+ continue;
+
+ // basics
+ int length = colorScale[kk]->size() - 1;
+
+ FitsImage* sptr = context[kk].cfits;
+ int mosaic = context[kk].isMosaic();
+
+ // variable
+ double* mm = sptr->matrixToData(Coord::WIDGET).mm();
+ FitsBound* params = sptr->getDataParams(context[kk].secMode());
+ int srcw = sptr->width();
+
+ double ll = sptr->low();
+ double hh = sptr->high();
+ double diff = hh - ll;
+
+ // main loop
+ long* dest = colormapData[kk];
+
+ for (long jj=0; jj<height; jj++) {
+ for (long ii=0; ii<width; ii++, dest++) {
+ *dest = -2; // bg
+
+ if (mosaic) {
+ sptr = context[kk].cfits;
+
+ mm = sptr->matrixToData(Coord::WIDGET).mm();
+ params = sptr->getDataParams(context[kk].secMode());
+ srcw = sptr->width();
+
+ ll = sptr->low();
+ hh = sptr->high();
+ diff = hh - ll;
+ }
+
+ do {
+ double xx = ii*mm[0] + jj*mm[3] + mm[6];
+ double yy = ii*mm[1] + jj*mm[4] + mm[7];
+
+ if (xx>=params->xmin && xx<params->xmax &&
+ yy>=params->ymin && yy<params->ymax) {
+ double value = sptr->getValueDouble(long(yy)*srcw + long(xx));
+
+ if (isfinite(diff) && isfinite(value)) {
+ if (value <= ll)
+ *dest = 0;
+ else if (value >= hh)
+ *dest = length;
+ else
+ *dest = (int)(((value - ll)/diff * length) + .5);
+ }
+ else
+ *dest = -1; // nan
+
+ break;
+ }
+ else {
+ if (mosaic) {
+ sptr = sptr->nextMosaic();
+
+ if (sptr) {
+ mm = sptr->matrixToData(Coord::WIDGET).mm();
+ params = sptr->getDataParams(context[kk].secMode());
+ srcw = sptr->width();
+
+ ll = sptr->low();
+ hh = sptr->high();
+ diff = hh - ll;
+ }
+ }
+ }
+ }
+ while (mosaic && sptr);
+ }
+ }
+ }
+ CLEARSIGBUS
+}
+
+void FrameRGB::colormapMotionCmd(float rb, float gb, float bb,
+ float rc, float gc, float bc, int i,
+ unsigned char* cells, int cnt)
+{
+ // we need a colorScale before we can render
+ if (!validColorScale())
+ return;
+
+ // first check for change
+ if (bias[0] == rb && bias[1] == gb && bias[2] == bb &&
+ contrast[0] == rc && contrast[1] == gc && contrast[2] == bc &&
+ invert == i && colorCells)
+ return;
+
+ // we got a change
+ bias[0] = rb;
+ bias[1] = gb;
+ bias[2] = bb;
+ contrast[0] = rc;
+ contrast[1] = gc;
+ contrast[2] = bc;
+ invert = i;
+
+ updateColorCells(cells, cnt);
+ updateColorScale();
+
+ // special case
+ if ((!view[0] || !context[0].fits) &&
+ (!view[1] || !context[1].fits) &&
+ (!view[2] || !context[2].fits))
+ return;
+
+ int& width = colormapXM->width;
+ int& height = colormapXM->height;
+
+ // create img
+ unsigned char* img = new unsigned char[width*height*3];
+ memset(img, 0, width*height*3);
+ char* mk = new char[width*height];
+ memset(mk, 0, width*height);
+
+ for (int kk=0; kk<3; kk++) {
+ if (!view[kk] || !context[kk].fits)
+ continue;
+
+ const unsigned char* table = colorScale[kk]->psColors();
+ long* src = colormapData[kk];
+ unsigned char* dest = img;
+ char* mptr = mk;
+ for (long jj=0; jj<height; jj++)
+ for (long ii=0; ii<width; ii++, src++, dest+=3, mptr++)
+ if (*src >= 0) {
+ memcpy(dest+kk, table+(*src), 1);
+ *mptr = 2;
+ }
+ else if (*src == -1 && *mptr < 2)
+ *mptr = 1;
+ }
+
+ // set remainder to bg
+ {
+ unsigned char* dest = img;
+ char* mptr = mk;
+ for (long jj=0; jj<height; jj++)
+ for (long ii=0; ii<width; ii++, dest+=3, mptr++)
+ if (*mptr == 2) // good value
+ ;
+ else if (*mptr == 1) { // nan
+ *(dest ) = (unsigned char)nanColor->red;
+ *(dest+1) = (unsigned char)nanColor->green;
+ *(dest+2) = (unsigned char)nanColor->blue;
+ }
+ else { // bg
+ *(dest ) = (unsigned char)bgColor->red;
+ *(dest+1) = (unsigned char)bgColor->green;
+ *(dest+2) = (unsigned char)bgColor->blue;
+ }
+ }
+
+ // build colormapXM
+ encodeTrueColor((unsigned char*)img, colormapXM);
+
+ // clean up
+ if (img)
+ delete [] img;
+ if (mk)
+ delete [] mk;
+
+ // XImage to Pixmap
+ TkPutImage(NULL, 0, display, colormapPM, widgetGC, colormapXM,
+ 0, 0, 0, 0, width, height);
+
+ // Display Pixmap
+ Vector dd = Vector() * widgetToWindow;
+ XCopyArea(display, colormapPM, Tk_WindowId(tkwin), colormapGCXOR, 0, 0,
+ width, height, dd[0], dd[1]);
+
+ // update panner
+ updatePanner();
+}
+
+void FrameRGB::colormapEndCmd()
+{
+ if (colormapXM) {
+ XDestroyImage(colormapXM);
+ colormapXM = NULL;
+ }
+
+ if (colormapPM) {
+ Tk_FreePixmap(display, colormapPM);
+ colormapPM = 0;
+ }
+
+ if (colormapGCXOR) {
+ XFreeGC(display, colormapGCXOR);
+ colormapGCXOR = 0;
+ }
+
+ for (int kk=0; kk<3; kk++)
+ if (colormapData[kk]) {
+ delete [] colormapData[kk];
+ colormapData[kk] = NULL;
+ }
+
+ update(BASE); // always update
+}
+
+#else
+
void FrameRGB::colormapBeginCmd() {}
void FrameRGB::colormapMotionCmd(float rb, float gb, float bb,
@@ -537,6 +797,8 @@ void FrameRGB::colormapEndCmd()
update(BASE);
}
+#endif
+
void FrameRGB::getColorbarCmd()
{
ostringstream str;