1 //////////////////////////////////////////////////////////////////////////////// 2 // 3 // File: GIFView.cpp 4 // 5 // Date: December 1999 6 // 7 // Author: Daniel Switkin 8 // 9 // Copyright 2003 (c) by Daniel Switkin. This file is made publically available 10 // under the BSD license, with the stipulations that this complete header must 11 // remain at the top of the file indefinitely, and credit must be given to the 12 // original author in any about box using this software. 13 // 14 //////////////////////////////////////////////////////////////////////////////// 15 16 // Additional authors: Stephan Aßmus, <superstippi@gmx.de> 17 // Maxime Simon, <maxime.simon@gmail.com> 18 19 #include <stdio.h> 20 #include <stdlib.h> 21 22 #include <Catalog.h> 23 #include <InterfaceKit.h> 24 #include <LayoutBuilder.h> 25 #include <String.h> 26 27 #include "Prefs.h" 28 #include "SavePalette.h" 29 30 #include "GIFView.h" 31 32 #undef B_TRANSLATION_CONTEXT 33 #define B_TRANSLATION_CONTEXT "GIFView" 34 35 36 extern int32 translatorVersion; 37 extern char translatorName[]; 38 39 // constructor 40 GIFView::GIFView(const char *name) 41 : BView(name, B_WILL_DRAW) 42 { 43 SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); 44 45 BStringView *title = new BStringView("Title", B_TRANSLATE("GIF image translator")); 46 title->SetFont(be_bold_font); 47 48 char version_string[100]; 49 sprintf(version_string, "v%d.%d.%d %s", (int)(translatorVersion >> 8), 50 (int)((translatorVersion >> 4) & 0xf), (int)(translatorVersion & 0xf), 51 __DATE__); 52 BStringView *version = new BStringView("Version", version_string); 53 54 const char *copyrightString = "©2003 Daniel Switkin, software@switkin.com"; 55 BStringView *copyright = new BStringView("Copyright", copyrightString); 56 57 // menu fields (Palette & Colors) 58 fWebSafeMI = new BMenuItem(B_TRANSLATE("Websafe"), 59 new BMessage(GV_WEB_SAFE), 0, 0); 60 fBeOSSystemMI = new BMenuItem(B_TRANSLATE("BeOS system"), 61 new BMessage(GV_BEOS_SYSTEM), 0, 0); 62 fGreyScaleMI = new BMenuItem(B_TRANSLATE("Greyscale"), 63 new BMessage(GV_GREYSCALE), 0, 0); 64 fOptimalMI = new BMenuItem(B_TRANSLATE("Optimal"), 65 new BMessage(GV_OPTIMAL), 0, 0); 66 fPaletteM = new BPopUpMenu("PalettePopUpMenu", true, true, B_ITEMS_IN_COLUMN); 67 fPaletteM->AddItem(fWebSafeMI); 68 fPaletteM->AddItem(fBeOSSystemMI); 69 fPaletteM->AddItem(fGreyScaleMI); 70 fPaletteM->AddItem(fOptimalMI); 71 72 fColorCountM = new BPopUpMenu("ColorCountPopUpMenu", true, true, 73 B_ITEMS_IN_COLUMN); 74 int32 count = 2; 75 for (int32 i = 0; i < 8; i++) { 76 BMessage* message = new BMessage(GV_SET_COLOR_COUNT); 77 message->AddInt32("size in bits", i + 1); 78 BString label; 79 label << count; 80 fColorCountMI[i] = new BMenuItem(label.String(), message, 0, 0); 81 fColorCountM->AddItem(fColorCountMI[i]); 82 count *= 2; 83 } 84 fColorCount256MI = fColorCountMI[7]; 85 86 fPaletteMF = new BMenuField(B_TRANSLATE("Palette"), fPaletteM); 87 fColorCountMF = new BMenuField(B_TRANSLATE("Colors"), fColorCountM); 88 89 // check boxes 90 fUseDitheringCB = new BCheckBox(B_TRANSLATE("Use dithering"), 91 new BMessage(GV_USE_DITHERING)); 92 93 fInterlacedCB = new BCheckBox(B_TRANSLATE("Write interlaced images"), 94 new BMessage(GV_INTERLACED)); 95 96 fUseTransparentCB = new BCheckBox(B_TRANSLATE("Write transparent images"), 97 new BMessage(GV_USE_TRANSPARENT)); 98 99 // radio buttons 100 fUseTransparentAutoRB = new BRadioButton( 101 B_TRANSLATE("Automatic (from alpha channel)"), 102 new BMessage(GV_USE_TRANSPARENT_AUTO)); 103 104 fUseTransparentColorRB = new BRadioButton(B_TRANSLATE("Use RGB color"), 105 new BMessage(GV_USE_TRANSPARENT_COLOR)); 106 107 fTransparentRedTC = new BTextControl("", "0", new BMessage(GV_TRANSPARENT_RED)); 108 109 fTransparentGreenTC = new BTextControl("", "0", new BMessage(GV_TRANSPARENT_GREEN)); 110 111 fTransparentBlueTC = new BTextControl("", "0", new BMessage(GV_TRANSPARENT_BLUE)); 112 113 BTextView *tr = fTransparentRedTC->TextView(); 114 BTextView *tg = fTransparentGreenTC->TextView(); 115 BTextView *tb = fTransparentBlueTC->TextView(); 116 117 for (uint32 x = 0; x < 256; x++) { 118 if (x < '0' || x > '9') { 119 tr->DisallowChar(x); 120 tg->DisallowChar(x); 121 tb->DisallowChar(x); 122 } 123 } 124 125 BLayoutBuilder::Group<>(this, B_VERTICAL, 7) 126 .SetInsets(5) 127 .AddGrid(10, 10) 128 .Add(title, 0, 0) 129 .Add(version, 1, 0) 130 .End() 131 .Add(copyright) 132 .AddGlue() 133 134 .AddGrid(10, 10) 135 .Add(fPaletteMF->CreateLabelLayoutItem(), 0, 0) 136 .Add(fPaletteMF->CreateMenuBarLayoutItem(), 1, 0) 137 138 .Add(fColorCountMF->CreateLabelLayoutItem(), 0, 1) 139 .Add(fColorCountMF->CreateMenuBarLayoutItem(), 1, 1) 140 .End() 141 .AddGlue() 142 143 .Add(fUseDitheringCB) 144 .Add(fInterlacedCB) 145 .Add(fUseTransparentCB) 146 147 .Add(fUseTransparentAutoRB) 148 .AddGrid(10, 10) 149 .Add(fUseTransparentColorRB, 0, 0) 150 .Add(fTransparentRedTC, 1, 0) 151 .Add(fTransparentGreenTC, 2, 0) 152 .Add(fTransparentBlueTC, 3, 0) 153 .End() 154 .AddGlue(); 155 156 BFont font; 157 GetFont(&font); 158 SetExplicitPreferredSize(BSize((font.Size() * 400)/12, (font.Size() * 300)/12)); 159 160 RestorePrefs(); 161 } 162 163 164 GIFView::~GIFView() 165 { 166 delete fPrefs; 167 } 168 169 170 void 171 GIFView::RestorePrefs() 172 { 173 fPrefs = new Prefs(); 174 175 fColorCountMF->SetEnabled(false); 176 fUseDitheringCB->SetEnabled(true); 177 178 switch (fPrefs->palettemode) { 179 case WEB_SAFE_PALETTE: 180 fWebSafeMI->SetMarked(true); 181 break; 182 case BEOS_SYSTEM_PALETTE: 183 fBeOSSystemMI->SetMarked(true); 184 break; 185 case GREYSCALE_PALETTE: 186 fGreyScaleMI->SetMarked(true); 187 fUseDitheringCB->SetEnabled(false); 188 break; 189 case OPTIMAL_PALETTE: 190 fOptimalMI->SetMarked(true); 191 fColorCountMF->SetEnabled(true); 192 break; 193 default: 194 fPrefs->palettemode = WEB_SAFE_PALETTE; 195 fWebSafeMI->SetMarked(true); 196 break; 197 } 198 199 if (fColorCountMF->IsEnabled() && 200 fPrefs->palette_size_in_bits > 0 && 201 fPrefs->palette_size_in_bits <= 8) { 202 // display the stored color count 203 fColorCountMI[fPrefs->palette_size_in_bits - 1]->SetMarked(true); 204 } else { 205 // display 256 colors 206 fColorCount256MI->SetMarked(true); 207 fPrefs->palette_size_in_bits = 8; 208 } 209 210 fInterlacedCB->SetValue(fPrefs->interlaced); 211 212 if (fGreyScaleMI->IsMarked()) fUseDitheringCB->SetValue(false); 213 else fUseDitheringCB->SetValue(fPrefs->usedithering); 214 fUseTransparentCB->SetValue(fPrefs->usetransparent); 215 fUseTransparentAutoRB->SetValue(fPrefs->usetransparentauto); 216 fUseTransparentColorRB->SetValue(!fPrefs->usetransparentauto); 217 if (fPrefs->usetransparent) { 218 fUseTransparentAutoRB->SetEnabled(true); 219 fUseTransparentColorRB->SetEnabled(true); 220 fTransparentRedTC->SetEnabled(!fPrefs->usetransparentauto); 221 fTransparentGreenTC->SetEnabled(!fPrefs->usetransparentauto); 222 fTransparentBlueTC->SetEnabled(!fPrefs->usetransparentauto); 223 } else { 224 fUseTransparentAutoRB->SetEnabled(false); 225 fUseTransparentColorRB->SetEnabled(false); 226 fTransparentRedTC->SetEnabled(false); 227 fTransparentGreenTC->SetEnabled(false); 228 fTransparentBlueTC->SetEnabled(false); 229 } 230 231 char temp[4]; 232 sprintf(temp, "%d", fPrefs->transparentred); 233 fTransparentRedTC->SetText(temp); 234 sprintf(temp, "%d", fPrefs->transparentgreen); 235 fTransparentGreenTC->SetText(temp); 236 sprintf(temp, "%d", fPrefs->transparentblue); 237 fTransparentBlueTC->SetText(temp); 238 } 239 240 // AllAttached 241 void 242 GIFView::AllAttached() 243 { 244 BView::AllAttached(); 245 BMessenger msgr(this); 246 fInterlacedCB->SetTarget(msgr); 247 fUseDitheringCB->SetTarget(msgr); 248 fUseTransparentCB->SetTarget(msgr); 249 fUseTransparentAutoRB->SetTarget(msgr); 250 fUseTransparentColorRB->SetTarget(msgr); 251 fTransparentRedTC->SetTarget(msgr); 252 fTransparentGreenTC->SetTarget(msgr); 253 fTransparentBlueTC->SetTarget(msgr); 254 fPaletteM->SetTargetForItems(msgr); 255 fColorCountM->SetTargetForItems(msgr); 256 } 257 258 // MessageReceived 259 void 260 GIFView::MessageReceived(BMessage *message) 261 { 262 switch (message->what) { 263 case GV_WEB_SAFE: 264 fPrefs->palettemode = WEB_SAFE_PALETTE; 265 fUseDitheringCB->SetEnabled(true); 266 fColorCountMF->SetEnabled(false); 267 fColorCount256MI->SetMarked(true); 268 break; 269 case GV_BEOS_SYSTEM: 270 fPrefs->palettemode = BEOS_SYSTEM_PALETTE; 271 fUseDitheringCB->SetEnabled(true); 272 fColorCountMF->SetEnabled(false); 273 fColorCount256MI->SetMarked(true); 274 break; 275 case GV_GREYSCALE: 276 fPrefs->palettemode = GREYSCALE_PALETTE; 277 fUseDitheringCB->SetEnabled(false); 278 fUseDitheringCB->SetValue(false); 279 fColorCountMF->SetEnabled(false); 280 fColorCount256MI->SetMarked(true); 281 fPrefs->usedithering = false; 282 break; 283 case GV_OPTIMAL: 284 fPrefs->palettemode = OPTIMAL_PALETTE; 285 fUseDitheringCB->SetEnabled(true); 286 fColorCountMF->SetEnabled(true); 287 fColorCountMI[fPrefs->palette_size_in_bits - 1]->SetMarked(true); 288 break; 289 case GV_SET_COLOR_COUNT: 290 if (fColorCountMF->IsEnabled()) { 291 int32 sizeInBits; 292 if (message->FindInt32("size in bits", &sizeInBits) >= B_OK) { 293 if (sizeInBits > 0 && sizeInBits <= 8) 294 fPrefs->palette_size_in_bits = sizeInBits; 295 } 296 } 297 break; 298 case GV_INTERLACED: 299 fPrefs->interlaced = fInterlacedCB->Value(); 300 break; 301 case GV_USE_DITHERING: 302 fPrefs->usedithering = fUseDitheringCB->Value(); 303 break; 304 case GV_USE_TRANSPARENT: 305 fPrefs->usetransparent = fUseTransparentCB->Value(); 306 if (fPrefs->usetransparent) { 307 fUseTransparentAutoRB->SetEnabled(true); 308 fUseTransparentColorRB->SetEnabled(true); 309 fTransparentRedTC->SetEnabled(fUseTransparentColorRB->Value()); 310 fTransparentGreenTC->SetEnabled(fUseTransparentColorRB->Value()); 311 fTransparentBlueTC->SetEnabled(fUseTransparentColorRB->Value()); 312 } else { 313 fUseTransparentAutoRB->SetEnabled(false); 314 fUseTransparentColorRB->SetEnabled(false); 315 fTransparentRedTC->SetEnabled(false); 316 fTransparentGreenTC->SetEnabled(false); 317 fTransparentBlueTC->SetEnabled(false); 318 } 319 break; 320 case GV_USE_TRANSPARENT_AUTO: 321 fPrefs->usetransparentauto = true; 322 fTransparentRedTC->SetEnabled(false); 323 fTransparentGreenTC->SetEnabled(false); 324 fTransparentBlueTC->SetEnabled(false); 325 break; 326 case GV_USE_TRANSPARENT_COLOR: 327 fPrefs->usetransparentauto = false; 328 fTransparentRedTC->SetEnabled(true); 329 fTransparentGreenTC->SetEnabled(true); 330 fTransparentBlueTC->SetEnabled(true); 331 break; 332 case GV_TRANSPARENT_RED: 333 fPrefs->transparentred = CheckInput(fTransparentRedTC); 334 break; 335 case GV_TRANSPARENT_GREEN: 336 fPrefs->transparentgreen = CheckInput(fTransparentGreenTC); 337 break; 338 case GV_TRANSPARENT_BLUE: 339 fPrefs->transparentblue = CheckInput(fTransparentBlueTC); 340 break; 341 default: 342 BView::MessageReceived(message); 343 break; 344 } 345 fPrefs->Save(); 346 } 347 348 int GIFView::CheckInput(BTextControl *control) { 349 int value = atoi(control->Text()); 350 if (value < 0 || value > 255) { 351 value = (value < 0) ? 0 : 255; 352 char temp[4]; 353 sprintf(temp, "%d", value); 354 control->SetText(temp); 355 } 356 return value; 357 } 358 359