;+ ; NAME: ; PICKCOLORNAME ; ; PURPOSE: ; ; The purpose of this program is to provide a blocking ; or modal widget interface for selecting a color "name". ; The program uses colors familiar to the FSC_COLOR program, ; and is often used to select a color name for passing to FSC_COLOR. ; ; AUTHOR: ; ; FANNING SOFTWARE CONSULTING: ; David Fanning, Ph.D. ; 1645 Sheely Drive ; Fort Collins, CO 80526 USA ; Phone: 970-221-0438 ; E-mail: davidf@dfanning.com ; Coyote's Guide to IDL Programming: http://www.dfanning.com ; ; CATEGORY: ; ; Graphics, Color Specification. ; ; CALLING SEQUENCE: ; ; colorName = PickColorName(startColorName) ; ; OPTIONAL INPUT PARAMETERS: ; ; startColorName: A string with the "name" of the color. Colors available are these: ; ; Almond Antique White Aquamarine Beige Bisque Black ; Blue Blue Violet Brown Burlywood Cadet Blue Charcoal ; Chartreuse Chocolate Coral Cornflower Blue Cornsilk Crimson ; Cyan Dark Goldenrod Dark Gray Dark Green Dark Khaki Dark Orchid ; Dark Red Dark Salmon Dark Slate Blue Deep Pink Dodger Blue Firebrick ; Forest Green Gold Goldenrod Gray Green Green Yellow ; Honeydew Hot Pink Indian Red Ivory Khaki Lavender ; Lawn Green Light Coral Light Cyan Light Gray Light Salmon Light Sea Green ; Light Yellow Lime Green Linen Magenta Maroon Medium Gray ; Medium Orchid Moccasin Navy Olive Olive Drab Orange ; Orange Red Orchid Pale Goldenrod Pale Green Papaya Peru ; Pink Plum Powder Blue Purple Red Rose ; Rosy Brown Royal Blue Saddle Brown Salmon Sandy Brown Sea Green ; Seashell Sienna Sky Blue Slate Blue Slate Gray Snow ; Spring Green Steel Blue Tan Teal Thistle Tomato ; Turquoise Violet Violet Red Wheat White Yellow ; ; ; The color WHITE is used if this parameter is absent. ; ; If the BREWER keyword is set, you can use the Brewer Color names: ; ; WT1 WT2 WT3 WT4 WT5 WT6 WT7 WT8 ; TAN1 TAN2 TAN3 TAN4 TAN5 TAN6 TAN7 TAN8 ; BLK1 BLK2 BLK3 BLK4 BLK5 BLK6 BLK7 BLK8 ; GRN1 GRN2 GRN3 GRN4 GRN5 GRN6 GRN7 GRN8 ; BLU1 BLU2 BLU3 BLU4 BLU5 BLU6 BLU7 BLU8 ; ORG1 ORG2 ORG3 ORG4 ORG5 ORG6 ORG7 ORG8 ; RED1 RED2 RED3 RED4 RED5 RED6 RED7 RED8 ; PUR1 PUR2 PUR3 PUR4 PUR5 PUR6 PUR7 PUR8 ; PBG1 PBG2 PBG3 PBG4 PBG5 PBG6 PBG7 PBG8 ; YGB1 YGB2 YGB3 YGB4 YGB5 YGB6 YGB7 YGB8 ; RYB1 RYB2 RYB3 RYB4 RYB5 RYB6 RYB7 RYB8 ; TG1 TG2 TG3 TG4 TG5 TG6 TG7 TG8 ; ; INPUT KEYWORD PARAMETERS: ; ; BOTTOM: The colors used in the program must be loaded somewhere ; in the color table. This keyword indicates where the colors ; start loading. By default BOTTOM is set equal to !D.Table_Size-NCOLORS-1. ; ; BREWER: Set this keyword if you wish to use the Brewer Colors, as defined ; in this reference: ; ; http://www.personal.psu.edu/cab38/ColorBrewer/ColorBrewer_intro.html ; ; COLUMNS: Set this keyword to the number of columns the colors should ; be arranged in. ; ; FILENAME: The string name of an ASCII file that can be opened to read in ; color values and color names. There should be one color per row ; in the file. Please be sure there are no blank lines in the file. ; The format of each row should be: ; ; redValue greenValue blueValue colorName ; ; Color values should be between 0 and 255. Any kind of white-space ; separation (blank characters, commas, or tabs) are allowed. The color ; name should be a string, but it should NOT be in quotes. A typical ; entry into the file would look like this: ; ; 255 255 0 Yellow ; ; GROUP_LEADER: This identifies a group leader if the program is called ; from within a widget program. Note that this keyword MUST be provided ; if you want to guarantee modal widget functionality. (If you don't know ; what this means, believe me, you WANT to use this keyword, always.) ; ; INDEX: This keyword identifies a color table index where the selected color ; is to be loaded when the program exits. The default behavior is to restore ; the input color table and NOT load a color. ; ; TITLE: This keyword accepts a string value for the window title. The default ; is "Select a Color". ; ; OUTPUT KEYWORD PARAMETERS: ; ; CANCEL: On exit, this keyword value is set to 0 if the user selected ; the ACCEPT button. IF the user selected the CANCEL button, or ; closed the window in any other way, this keyword value is set to 1. ; COMMON BLOCKS: ; ; None. ; ; SIDE EFFECTS: ; ; Colors are loaded in the current color table. The input color table ; is restored when the program exits. This will only be noticable on ; 8-bit displays. The startColorName is returned if the user cancels ; or destroys the widget before a selection is made. Users should ; check the CANCEL flag before using the returned color. ; ; EXAMPLE: ; ; To call the program from the IDL comamnd line: ; ; IDL> color = PickColorName("red") & Print, color ; ; To call the program from within a widget program: ; ; color = PickColorName("red", Group_Leader=event.top) & Print, color ; ; MODIFICATION HISTORY: ; ; Written by: David W. Fanning, 31 August 2000. ; Modified program to read colors from a file and to use more ; colors on 24-bit platforms. 16 October 2000. DWF. ; Added the COLUMNS keyword. 16 October 2000. DWF. ; Fixed a small problem with mapping a modal widget. 2 Jan 2001. DWF ; Now drawing small box around each color. 13 March 2003. DWF. ; Added eight new colors. Total now of 104 colors. 11 August 2005. DWF. ; Modified GUI to display system colors. 13 Dec 2005. DWF. ; Added BREWER keyword to allow Brewer Colors. 15 May 2008. DWF. ;- ; ;########################################################################### ; ; LICENSE ; ; This software is OSI Certified Open Source Software. ; OSI Certified is a certification mark of the Open Source Initiative. ; ; Copyright2000-2008 Fanning Software Consulting. ; ; This software is provided "as-is", without any express or ; implied warranty. In no event will the authors be held liable ; for any damages arising from the use of this software. ; ; Permission is granted to anyone to use this software for any ; purpose, including commercial applications, and to alter it and ; redistribute it freely, subject to the following restrictions: ; ; 1. The origin of this software must not be misrepresented; you must ; not claim you wrote the original software. If you use this software ; in a product, an acknowledgment in the product documentation ; would be appreciated, but is not required. ; ; 2. Altered source versions must be plainly marked as such, and must ; not be misrepresented as being the original software. ; ; 3. This notice may not be removed or altered from any source distribution. ; ; For more information on Open Source Software, visit the Open Source ; web site: http://www.opensource.org. ; ;########################################################################### PRO PickColorName_CenterTLB, tlb ; Center the top-level base widget. screenSize = Get_Screen_Size() Device, Get_Screen_Size=screenSize IF screenSize[0] GT 2000 THEN screenSize[0] = screenSize[0]/2 xCenter = screenSize(0) / 2 yCenter = screenSize(1) / 2 geom = Widget_Info(tlb, /Geometry) xHalfSize = geom.Scr_XSize / 2 yHalfSize = geom.Scr_YSize / 2 Widget_Control, tlb, XOffset = xCenter-xHalfSize, $ YOffset = yCenter-yHalfSize END ;------------------------------------------------------------------------------- FUNCTION PickColorName_RGB_to_24Bit, number ; Convert RGB values to 24-bit number values. IF Size(number, /N_Dimensions) EQ 1 THEN BEGIN RETURN, number[0] + (number[1] * 2L^8) + (number[2] * 2L^16) ENDIF ELSE BEGIN RETURN, number[*,0] + (number[*,1] * 2L^8) + (number[*,2] * 2L^16) ENDELSE END ;------------------------------------------------------------------------------- FUNCTION PickColorName_Count_Rows, filename, MaxRows = maxrows ; This utility routine is used to count the number of ; rows in an ASCII data file. IF N_Elements(maxrows) EQ 0 THEN maxrows = 500L IF N_Elements(filename) EQ 0 THEN BEGIN filename = Dialog_Pickfile() IF filename EQ "" THEN RETURN, -1 ENDIF OpenR, lun, filename, /Get_Lun Catch, error IF error NE 0 THEN BEGIN count = count-1 Free_Lun, lun RETURN, count ENDIF RESTART: count = 1L line = '' FOR j=count, maxrows DO BEGIN ReadF, lun, line count = count + 1 ; Try again if you hit MAXROWS without encountering the ; end of the file. Double the MAXROWS parameter. IF j EQ maxrows THEN BEGIN maxrows = maxrows * 2 Point_Lun, lun, 0 GOTO, RESTART ENDIF ENDFOR RETURN, -1 END ;------------------------------------------------------------------------------- PRO PickColorName_Select_Color, event ; This event handler permits color selection by clicking on a color window. IF event.type NE 0 THEN RETURN Widget_Control, event.top, Get_UValue=info, /No_Copy ; Get the color names from the window you clicked on and set it. Widget_Control, event.id, Get_UValue=thisColorName Widget_Control, event.top, Update=0 Widget_Control, info.labelID, Set_Value=thisColorName Widget_Control, event.top, Update=1 ; Get the color value and load it as the current color. WSet, info.mixWID info.theName = thisColorName theIndex = Where(info.colorNames EQ StrUpCase(StrCompress(thisColorName, /Remove_All))) theIndex = theIndex[0] info.nameIndex = theIndex IF info.theDepth GT 8 THEN BEGIN Erase, Color=info.colors24[theIndex] PlotS, [0,0,59,59,0], [0,14,14,0,0], /Device, Color=info.black ENDIF ELSE BEGIN TVLCT, info.red[theIndex], info.green[theIndex], info.blue[theIndex], info.mixcolorIndex Erase, Color=info.mixcolorIndex PlotS, [0,0,59,59,0], [0,14,14,0,0], /Device, Color=info.black ENDELSE Widget_Control, event.top, Set_UValue=info, /No_Copy END ;--------------------------------------------------------------------------- PRO PickColorName_Buttons, event ; This event handler responds to CANCEL and ACCEPT buttons. Widget_Control, event.top, Get_UValue=info, /No_Copy ; Which button is this? Widget_Control, event.id, Get_Value=buttonValue ; Branch on button value. CASE buttonValue OF 'Cancel': BEGIN ; Simply destroy the widget. The pointer info is already ; set up for a CANCEL event. Widget_Control, event.top, /Destroy ENDCASE 'Accept': BEGIN ; Get the new color table after the color has been selected. TVLCT, r, g, b, /Get ; Save the new color and name in the pointer. *(info.ptr) = {cancel:0.0, r:info.red[info.nameIndex], g:info.green[info.nameIndex], $ b:info.blue[info.nameIndex], name:info.theName} ; Destoy the widget. Widget_Control, event.top, /Destroy ENDCASE ENDCASE END ;--------------------------------------------------------------------------- FUNCTION PickColorName, theName, $ ; The name of the starting color. Brewer=brewer, $ ; Select brewer colors. Bottom=bottom, $ ; The index number where the colors should be loaded. Cancel=cancelled, $ ; An output keyword set to 1 if the user cancelled or an error occurred. Columns = ncols, $ ; The number of columns to display the colors in. Filename=filename, $ ; The name of the file which contains color names and values. Group_Leader=group_leader, $ ; The group leader of the TLB. Required for modal operation. Index=index, $ ; The color index number where the final selected color should be loaded. Title=title ; The title of the top-level base widget. ; Error handling for this program module. Catch, theError IF theError NE 0 THEN BEGIN Catch, /Cancel ok = Error_Message(/Traceback) cancel = 1 IF N_Elements(theName) NE 0 THEN RETURN, theName ELSE RETURN, 'White' ENDIF ; Get depth of visual display. IF (!D.Flags AND 256) NE 0 THEN Device, Get_Visual_Depth=theDepth ELSE theDepth = 8 ; Is there a filename? If so, get colors from there. IF N_Elements(filename) NE 0 THEN BEGIN ; Count the number of rows in the file. NCOLORS = PickColorName_Count_Rows(filename) ; Read the data. OpenR, lun, filename, /Get_Lun red = BytArr(NCOLORS) green = BytArr(NCOLORS) blue = BytArr(NCOLORS) colors = StrArr(NCOLORS) redvalue = 0B greenvalue = 0B bluevalue = 0B namevalue = "" FOR j=0L, NCOLORS-1 DO BEGIN ReadF, lun, redvalue, greenvalue, bluevalue, namevalue colors[j] = namevalue red[j] = redvalue green[j] = greenvalue blue[j] = bluevalue ENDFOR ; Trim the colors array of blank characters. colors = StrTrim(colors, 2) ; Calculate the number of columns to display colors in. IF N_Elements(ncols) EQ 0 THEN ncols = Fix(Sqrt(ncolors)) Free_Lun, lun ENDIF ELSE BEGIN IF theDepth GT 8 THEN BEGIN ; The colors with their names. NCOLORS = 96 IF N_Elements(ncols) EQ 0 THEN ncols = 12 IF Keyword_Set(brewer) THEN BEGIN colors = [ 'WT1', 'WT2', 'WT3', 'WT4', 'WT5', 'WT6', 'WT7', 'WT8'] red = [ 255, 255, 255, 255, 255, 245, 255, 250 ] green = [ 255, 250, 255, 255, 248, 245, 245, 240 ] blue = [ 255, 250, 240, 224, 220, 220, 238, 230 ] colors = [ colors, 'TAN1', 'TAN2', 'TAN3', 'TAN4', 'TAN5', 'TAN6', 'TAN7', 'TAN8'] red = [ red, 250, 255, 255, 255, 255, 245, 222, 210 ] green = [ green, 235, 239, 235, 228, 228, 222, 184, 180 ] blue = [ blue, 215, 213, 205, 196, 181, 179, 135, 140 ] colors = [ colors, 'BLK1', 'BLK2', 'BLK3', 'BLK4', 'BLK5', 'BLK6', 'BLK7', 'BLK8'] red = [ red, 250, 230, 210, 190, 112, 110, 70, 0 ] green = [ green, 250, 230, 210, 190, 128, 110, 70, 0 ] blue = [ blue, 250, 230, 210, 190, 128, 110, 70, 0 ] colors = [ colors, 'GRN1', 'GRN2', 'GRN3', 'GRN4', 'GRN5', 'GRN6', 'GRN7', 'GRN8'] red = [ red, 250, 223, 173, 109, 53, 35, 0, 0 ] green = [ green, 253, 242, 221, 193, 156, 132, 97, 69 ] blue = [ blue, 202, 167, 142, 115, 83, 67, 52, 41 ] colors = [ colors, 'BLU1', 'BLU2', 'BLU3', 'BLU4', 'BLU5', 'BLU6', 'BLU7', 'BLU8'] red = [ red, 232, 202, 158, 99, 53, 33, 8, 8 ] green = [ green, 241, 222, 202, 168, 133, 113, 75, 48 ] blue = [ blue, 250, 240, 225, 211, 191, 181, 147, 107 ] colors = [ colors, 'ORG1', 'ORG2', 'ORG3', 'ORG4', 'ORG5', 'ORG6', 'ORG7', 'ORG8'] red = [ red, 254, 253, 253, 250, 231, 217, 159, 127 ] green = [ green, 236, 212, 174, 134, 92, 72, 51, 39 ] blue = [ blue, 217, 171, 107, 52, 12, 1, 3, 4 ] colors = [ colors, 'RED1', 'RED2', 'RED3', 'RED4', 'RED5', 'RED6', 'RED7', 'RED8'] red = [ red, 254, 252, 252, 248, 225, 203, 154, 103 ] green = [ green, 232, 194, 146, 97, 45, 24, 12, 0 ] blue = [ blue, 222, 171, 114, 68, 38, 29, 19, 13 ] colors = [ colors, 'PUR1', 'PUR2', 'PUR3', 'PUR4', 'PUR5', 'PUR6', 'PUR7', 'PUR8'] red = [ red, 244, 222, 188, 152, 119, 106, 80, 63 ] green = [ green, 242, 221, 189, 148, 108, 82, 32, 0 ] blue = [ blue, 248, 237, 220, 197, 177, 163, 139, 125 ] colors = [ colors, 'PBG1', 'PBG2', 'PBG3', 'PBG4', 'PBG5', 'PBG6', 'PBG7', 'PBG8'] red = [ red, 243, 213, 166, 94, 34, 3, 1, 1 ] green = [ green, 234, 212, 189, 164, 138, 129, 101, 70 ] blue = [ blue, 244, 232, 219, 204, 171, 139, 82, 54 ] colors = [ colors, 'YGB1', 'YGB2', 'YGB3', 'YGB4', 'YGB5', 'YGB6', 'YGB7', 'YGB8'] red = [ red, 244, 206, 127, 58, 30, 33, 32, 8 ] green = [ green, 250, 236, 205, 175, 125, 95, 48, 29 ] blue = [ blue, 193, 179, 186, 195, 182, 168, 137, 88 ] colors = [ colors, 'RYB1', 'RYB2', 'RYB3', 'RYB4', 'RYB5', 'RYB6', 'RYB7', 'RYB8'] red = [ red, 201, 245, 253, 251, 228, 193, 114, 59 ] green = [ green, 35, 121, 206, 253, 244, 228, 171, 85 ] blue = [ blue, 38, 72, 127, 197, 239, 239, 207, 164 ] colors = [ colors, 'TG1', 'TG2', 'TG3', 'TG4', 'TG5', 'TG6', 'TG7', 'TG8'] red = [ red, 84, 163, 197, 220, 105, 51, 13, 0 ] green = [ green, 48, 103, 141, 188, 188, 149, 113, 81 ] blue = [ blue, 5, 26, 60, 118, 177, 141, 105, 71 ] ENDIF ELSE BEGIN colors= ['White'] red = [ 255] green = [ 255] blue = [ 255] colors= [ colors, 'Snow', 'Ivory','Light Yellow', 'Cornsilk', 'Beige', 'Seashell' ] red = [ red, 255, 255, 255, 255, 245, 255 ] green = [ green, 250, 255, 255, 248, 245, 245 ] blue = [ blue, 250, 240, 224, 220, 220, 238 ] colors= [ colors, 'Linen','Antique White', 'Papaya', 'Almond', 'Bisque', 'Moccasin' ] red = [ red, 250, 250, 255, 255, 255, 255 ] green = [ green, 240, 235, 239, 235, 228, 228 ] blue = [ blue, 230, 215, 213, 205, 196, 181 ] colors= [ colors, 'Wheat', 'Burlywood', 'Tan', 'Light Gray', 'Lavender','Medium Gray' ] red = [ red, 245, 222, 210, 230, 230, 210 ] green = [ green, 222, 184, 180, 230, 230, 210 ] blue = [ blue, 179, 135, 140, 230, 250, 210 ] colors= [ colors, 'Gray', 'Slate Gray', 'Dark Gray', 'Charcoal', 'Black', 'Honeydew', 'Light Cyan' ] red = [ red, 190, 112, 110, 70, 0, 240, 224 ] green = [ green, 190, 128, 110, 70, 0, 255, 255 ] blue = [ blue, 190, 144, 110, 70, 0, 255, 240 ] colors= [ colors,'Powder Blue', 'Sky Blue', 'Cornflower Blue', 'Cadet Blue', 'Steel Blue','Dodger Blue', 'Royal Blue', 'Blue' ] red = [ red, 176, 135, 100, 95, 70, 30, 65, 0 ] green = [ green, 224, 206, 149, 158, 130, 144, 105, 0 ] blue = [ blue, 230, 235, 237, 160, 180, 255, 225, 255 ] colors= [ colors, 'Navy', 'Pale Green','Aquamarine','Spring Green', 'Cyan' ] red = [ red, 0, 152, 127, 0, 0 ] green = [ green, 0, 251, 255, 250, 255 ] blue = [ blue, 128, 152, 212, 154, 255 ] colors= [ colors, 'Turquoise', 'Light Sea Green', 'Sea Green','Forest Green', 'Teal','Green Yellow','Chartreuse', 'Lawn Green' ] red = [ red, 64, 143, 46, 34, 0, 173, 127, 124 ] green = [ green, 224, 188, 139, 139, 128, 255, 255, 252 ] blue = [ blue, 208, 143, 87, 34, 128, 47, 0, 0 ] colors= [ colors, 'Green', 'Lime Green', 'Olive Drab', 'Olive','Dark Green','Pale Goldenrod'] red = [ red, 0, 50, 107, 85, 0, 238 ] green = [ green, 255, 205, 142, 107, 100, 232 ] blue = [ blue, 0, 50, 35, 47, 0, 170 ] colors =[ colors, 'Khaki', 'Dark Khaki', 'Yellow', 'Gold','Goldenrod','Dark Goldenrod'] red = [ red, 240, 189, 255, 255, 218, 184 ] green = [ green, 230, 183, 255, 215, 165, 134 ] blue = [ blue, 140, 107, 0, 0, 32, 11 ] colors= [ colors,'Saddle Brown', 'Rose', 'Pink', 'Rosy Brown','Sandy Brown', 'Peru'] red = [ red, 139, 255, 255, 188, 244, 205 ] green = [ green, 69, 228, 192, 143, 164, 133 ] blue = [ blue, 19, 225, 203, 143, 96, 63 ] colors= [ colors,'Indian Red', 'Chocolate', 'Sienna','Dark Salmon', 'Salmon','Light Salmon' ] red = [ red, 205, 210, 160, 233, 250, 255 ] green = [ green, 92, 105, 82, 150, 128, 160 ] blue = [ blue, 92, 30, 45, 122, 114, 122 ] colors= [ colors, 'Orange', 'Coral', 'Light Coral', 'Firebrick', 'Dark Red', 'Brown', 'Hot Pink' ] red = [ red, 255, 255, 240, 178, 139, 165, 255 ] green = [ green, 165, 127, 128, 34, 0, 42, 105 ] blue = [ blue, 0, 80, 128, 34, 0, 42, 180 ] colors= [ colors, 'Deep Pink', 'Magenta', 'Tomato', 'Orange Red', 'Red', 'Crimson', 'Violet Red' ] red = [ red, 255, 255, 255, 255, 255, 220, 208 ] green = [ green, 20, 0, 99, 69, 0, 20, 32 ] blue = [ blue, 147, 255, 71, 0, 0, 60, 144 ] colors= [ colors, 'Maroon', 'Thistle', 'Plum', 'Violet', 'Orchid','Medium Orchid'] red = [ red, 176, 216, 221, 238, 218, 186 ] green = [ green, 48, 191, 160, 130, 112, 85 ] blue = [ blue, 96, 216, 221, 238, 214, 211 ] colors= [ colors,'Dark Orchid','Blue Violet', 'Purple'] red = [ red, 153, 138, 160] green = [ green, 50, 43, 32] blue = [ blue, 204, 226, 240] colors= [ colors, 'Slate Blue', 'Dark Slate Blue'] red = [ red, 106, 72] green = [ green, 90, 61] blue = [ blue, 205, 139] ENDELSE ENDIF ELSE BEGIN NCOLORS = 16 IF N_Elements(ncols) EQ 0 THEN ncols = 8 colors = ['Black', 'Magenta', 'Cyan', 'Yellow', 'Green'] red = [ 0, 255, 0, 255, 0 ] green = [ 0, 0, 255, 255, 255 ] blue = [ 0, 255, 255, 0, 0 ] colors = [colors, 'Red', 'Blue', 'Navy', 'Pink', 'Aqua'] red = [red, 255, 0, 0, 255, 112] green = [green, 0, 0, 0, 127, 219] blue = [blue, 0, 255, 115, 127, 147] colors = [colors, 'Orchid', 'Sky', 'Beige', 'Charcoal', 'Gray','White'] red = [red, 219, 0, 245, 80, 135, 255 ] green = [green, 112, 163, 245, 80, 135, 255 ] blue = [blue, 219, 255, 220, 80, 135, 255 ] ENDELSE ENDELSE ; Add system color names for IDL version 5.6 and higher. IF Float(!Version.Release) GE 5.6 THEN BEGIN tlb = Widget_Base() sc = Widget_Info(tlb, /System_Colors) Widget_Control, tlb, /Destroy frame = sc.window_frame text = sc.window_text active = sc.active_border shadow = sc.shadow_3d highlight = sc.light_3d edge = sc.light_edge_3d selected = sc.highlight face = sc.face_3d colors = [colors, 'Frame', 'Text', 'Active', 'Shadow'] red = [red, frame[0], text[0], active[0], shadow[0]] green = [green, frame[1], text[1], active[1], shadow[1]] blue = [blue, frame[2], text[2], active[2], shadow[2]] colors = [colors, 'Highlight', 'Edge', 'Selected', 'Face'] red = [red, highlight[0], edge[0], selected[0], face[0]] green = [green, highlight[1], edge[1], selected[1], face[1]] blue = [blue, highlight[2], edge[2], selected[2], face[2]] ENDIF ; Save decomposed state and restore it, if possible. IF Float(!Version.Release) GE 5.2 THEN BEGIN Device, Get_Decomposed=decomposedState ENDIF ELSE decomposedState = 0 ; Different color decomposition based on visual depth. IF theDepth GT 8 THEN BEGIN Device, Decomposed=1 colors24 = PickColorName_RGB_to_24Bit([[red], [green], [blue]]) ENDIF ELSE BEGIN IF NCOLORS GT !D.Table_Size THEN $ Message, /NoName, 'Number of colors exceeds color table size. Returning...' Device, Decomposed=0 colors24 = -1 ENDELSE ; Check argument values. All arguments are optional. IF N_Elements(theName) EQ 0 THEN IF Keyword_Set(brewer) THEN theName = 'WT1' ELSE theName = 'White' IF Size(theName, /TName) NE 'STRING' THEN $ Message, 'Color name argument must be STRING type.', /NoName theName = StrCompress(theName, /Remove_All) IF N_Elements(bottom) EQ 0 THEN bottom = 0 > (!D.Table_Size - (NCOLORS + 2)) mixcolorIndex = bottom IF N_Elements(title) EQ 0 THEN title='Select a Color' ; We will work with all uppercase names. colorNames = StrUpCase(StrCompress(colors, /Remove_All)) ; Get the current color table vectors before we change anything. ; This will allow us to restore the color table when we depart. TVLCT, r_old, g_old, b_old, /Get ; Load the colors if needed. The "bottom" index is reserved as the "mixing color" index. IF theDepth LE 8 THEN TVLCT, red, green, blue, bottom+1 ; Can you find the color name in the colors array? nameIndex = WHERE(colorNames EQ StrUpCase(theName), count) IF count EQ 0 THEN BEGIN Message, 'Unable to resolve color name: ' + StrUpCase(theName) + '. Replacing with WHITE.', /Informational theName = 'WT1' nameIndex = WHERE(colorNames EQ StrUpCase(theName), count) IF count EQ 0 THEN Message, /NoName, 'Unable to resolve color name: ' + StrUpCase(theName) + '. Returning...' ENDIF nameIndex = nameIndex[0] ; Who knows how the user spelled the color? Make it look nice. theName = colors[nameIndex] ; Load the mixing color in the mixcolorIndex. IF theDepth LE 8 THEN TVLCT, red[nameIndex], green[nameIndex], blue[nameIndex], mixcolorIndex ; Create the widgets. TLB is MODAL or BLOCKING, depending upon presence of ; Group_Leader variable. IF N_Elements(group_leader) EQ 0 THEN BEGIN tlb = Widget_Base(Title=title, Column=1, /Base_Align_Center) ENDIF ELSE BEGIN tlb = Widget_Base(Title=title, Column=1, /Base_Align_Center, /Modal, $ Group_Leader=group_leader) ENDELSE ; Draw widgets for the possible colors. Store the color name in the UVALUE. colorbaseID = Widget_Base(tlb, Column=ncols, Event_Pro='PickColorName_Select_Color') drawID = LonArr(NCOLORS) FOR j=0,NCOLORS-1 DO BEGIN drawID[j] = Widget_Draw(colorbaseID, XSize=20, YSize=15, $ UValue=colors[j], Button_Events=1) ENDFOR ; System colors. IF N_Elements(colors) GT NCOLORS THEN BEGIN systemColorbase = Widget_Base(tlb, Column=8, Event_Pro='PickColorName_Select_Color') drawID = [Temporary(drawID), LonArr(8)] FOR j=NCOLORS,N_Elements(colors)-1 DO BEGIN drawID[j] = Widget_Draw(systemColorbase, XSize=20, YSize=15, $ UValue=colors[j], Button_Events=1) ENDFOR ENDIF ; Set up the current or mixing color draw widget. currentID = Widget_Base(tlb, Column=1, Base_Align_Center=1) labelID = Widget_Label(currentID, Value=theName, /Dynamic_Resize) mixColorID = Widget_Draw(currentID, XSize=60, YSize=15) ; CANCEL and ACCEPT buttons. buttonbase = Widget_Base(tlb, ROW=1, Align_Center=1, Event_Pro='PickColorName_Buttons') cancelID = Widget_Button(buttonbase, VALUE='Cancel') acceptID = Widget_Button(buttonbase, VALUE='Accept') ; Center the TLB. PickColorName_CenterTLB, tlb Widget_Control, tlb, /Realize ; Load the drawing colors. wids = IntArr(NCOLORS) IF theDepth GT 8 THEN BEGIN FOR j=0,NCOLORS-1 DO BEGIN Widget_Control, drawID[j], Get_Value=thisWID wids[j] = thisWID WSet, thisWID PolyFill, [1,1,19,19,1], [0,13,13,0,0], /Device, Color=colors24[j] ENDFOR IF (N_Elements(colors) GT NCOLORS) THEN BEGIN wids = [Temporary(wids), Intarr(8)] FOR j=NCOLORS, N_Elements(colors)-1 DO BEGIN Widget_Control, drawID[j], Get_Value=thisWID wids[j] = thisWID WSet, thisWID PolyFill, [1,1,19,19,1], [0,13,13,0,0], /Device, Color=colors24[j] ENDFOR ENDIF ENDIF ELSE BEGIN FOR j=1,NCOLORS DO BEGIN Widget_Control, drawID[j-1], Get_Value=thisWID wids[j-1] = thisWID WSet, thisWID PolyFill, [1,1,19,19,1], [0,13,13,0,0], /Device, Color=bottom + black ENDFOR IF (N_Elements(colors) GT NCOLORS) THEN BEGIN wids = [Temporary(wids), Intarr(8)] FOR j=NCOLORS+1, N_Elements(colors) DO BEGIN Widget_Control, drawID[j-1], Get_Value=thisWID wids[j-1] = thisWID WSet, thisWID PolyFill, [1,1,19,19,1], [0,13,13,0,0], /Device, Color=bottom + j ENDFOR ENDIF ENDELSE ; Load the current or mixing color. Widget_Control, mixColorID, Get_Value=mixWID WSet, mixWID IF theDepth GT 8 THEN BEGIN Erase, Color=colors24[nameIndex] eraseColor = Keyword_Set(brewer) ? 'BLK8' : 'BLACK black = Where(colornames EQ eraseColor) black = black[0] PlotS, [0,0,59,59,0], [0,14,14,0,0], /Device, Color=colors24[black] ENDIF ELSE BEGIN eraseColor = Keyword_Set(brewer) ? 'BLK8' : 'BLACK black = Where(colornames EQ eraseColor) Erase, Color=mixcolorIndex PlotS, [0,0,59,59,0], [0,14,14,0,0], /Device, Color=black ENDELSE ; Pointer to hold the color form information. ptr = Ptr_New({cancel:1.0, r:0B, g:0B, b:0B, name:theName}) ; Info structure for program information. info = { ptr:ptr, $ ; The pointer to the form information. mixColorIndex:mixColorIndex, $ colorNames:colorNames, $ nameIndex:nameIndex, $ red:red, $ green:green, $ blue:blue, $ black:black, $ colors24:colors24, $ mixWid:mixWid, $ theDepth:theDepth, $ labelID:labelID, $ theName:theName $ } ; Store the info structure in the UVALUE of the TLB. Widget_Control, tlb, Set_UValue=info, /No_Copy ; Set up program event loop. This will be blocking widget ; if called from the IDL command line. Program operation ; will stop here until widget interface is destroyed. XManager, 'pickcolor', tlb ; Retrieve the color information from the pointer and free ; the pointer. colorInfo = *ptr Ptr_Free, ptr ; Set the Cancel flag. cancelled = colorInfo.cancel ; Restore color table, taking care to load the color index if required. IF N_Elements(index) NE 0 AND (NOT cancelled) THEN BEGIN r_old[index] = colorInfo.r g_old[index] = colorInfo.g b_old[index] = colorInfo.b ENDIF TVLCT, r_old, g_old, b_old ; Restore decomposed state if possible. IF Float(!Version.Release) GE 5.2 THEN Device, Decomposed=decomposedState ; Return the color name. RETURN, colorInfo.name END