void TAlertView::GetPreferredSize(float* _width, float* _height) { int32 scale = icon_layout_scale(); if (_width != NULL) { if (fIconBitmap != NULL) *_width = 18 * scale + fIconBitmap->Bounds().Width(); else *_width = 0; } if (_height != NULL) { if (fIconBitmap != NULL) *_height = 6 * scale + fIconBitmap->Bounds().Height(); else *_height = 0; } }
void TAlertView::Draw(BRect updateRect) { if (fIconBitmap == NULL) return; // Here's the fun stuff BRect stripeRect = Bounds(); int32 iconLayoutScale = icon_layout_scale(); stripeRect.right = kIconStripeWidth * iconLayoutScale; SetHighColor(tint_color(ViewColor(), B_DARKEN_1_TINT)); FillRect(stripeRect); SetDrawingMode(B_OP_ALPHA); SetBlendingMode(B_PIXEL_ALPHA, B_ALPHA_OVERLAY); DrawBitmapAsync(fIconBitmap, BPoint(18 * iconLayoutScale, 6 * iconLayoutScale)); }
BBitmap* BAlert::_InitIcon() { // Save the desired alert type and set it to "empty" until // loading the icon was successful alert_type alertType = fMsgType; fMsgType = B_EMPTY_ALERT; // After a bit of a search, I found the icons in app_server. =P BBitmap* icon = NULL; BPath path; status_t status = find_directory(B_BEOS_SERVERS_DIRECTORY, &path); if (status < B_OK) { FTRACE((stderr, "BAlert::_InitIcon() - find_directory failed: %s\n", strerror(status))); return NULL; } path.Append("app_server"); BFile file; status = file.SetTo(path.Path(), B_READ_ONLY); if (status < B_OK) { FTRACE((stderr, "BAlert::_InitIcon() - BFile init failed: %s\n", strerror(status))); return NULL; } BResources resources; status = resources.SetTo(&file); if (status < B_OK) { FTRACE((stderr, "BAlert::_InitIcon() - BResources init failed: %s\n", strerror(status))); return NULL; } // Which icon are we trying to load? const char* iconName = ""; // Don't want any seg faults switch (alertType) { case B_INFO_ALERT: iconName = "info"; break; case B_IDEA_ALERT: iconName = "idea"; break; case B_WARNING_ALERT: iconName = "warn"; break; case B_STOP_ALERT: iconName = "stop"; break; default: // Alert type is either invalid or B_EMPTY_ALERT; // either way, we're not going to load an icon return NULL; } int32 iconSize = 32 * icon_layout_scale(); // Allocate the icon bitmap icon = new(std::nothrow) BBitmap(BRect(0, 0, iconSize - 1, iconSize - 1), 0, B_RGBA32); if (icon == NULL || icon->InitCheck() < B_OK) { FTRACE((stderr, "BAlert::_InitIcon() - No memory for bitmap\n")); delete icon; return NULL; } // Load the raw icon data size_t size = 0; const uint8* rawIcon; #ifdef __ANTARES__ // Try to load vector icon rawIcon = (const uint8*)resources.LoadResource(B_VECTOR_ICON_TYPE, iconName, &size); if (rawIcon != NULL && BIconUtils::GetVectorIcon(rawIcon, size, icon) == B_OK) { // We have an icon, restore the saved alert type fMsgType = alertType; return icon; } #endif // Fall back to bitmap icon rawIcon = (const uint8*)resources.LoadResource(B_LARGE_ICON_TYPE, iconName, &size); if (rawIcon == NULL) { FTRACE((stderr, "BAlert::_InitIcon() - Icon resource not found\n")); delete icon; return NULL; } // Handle color space conversion #ifdef __ANTARES__ if (icon->ColorSpace() != B_CMAP8) { BIconUtils::ConvertFromCMAP8(rawIcon, iconSize, iconSize, iconSize, icon); } #else icon->SetBits(rawIcon, iconSize, 0, B_CMAP8); #endif // We have an icon, restore the saved alert type fMsgType = alertType; return icon; }
void BAlert::_InitObject(const char* text, const char* button0, const char* button1, const char* button2, button_width buttonWidth, button_spacing spacing, alert_type type) { fInvoker = NULL; fAlertSem = -1; fAlertValue = -1; fButtons[0] = fButtons[1] = fButtons[2] = NULL; fTextView = NULL; fKeys[0] = fKeys[1] = fKeys[2] = 0; fMsgType = type; fButtonWidth = buttonWidth; // Set up the "_master_" view TAlertView* view = new(std::nothrow) TAlertView(Bounds()); if (view == NULL) return; AddChild(view); view->SetBitmap(_InitIcon()); // Must have at least one button if (button0 == NULL) { debugger("BAlerts must have at least one button."); button0 = ""; } // Set up the buttons int32 buttonCount = 1; view->AddChild(fButtons[0] = _CreateButton(0, button0)); if (button1 != NULL) { view->AddChild(fButtons[1] = _CreateButton(1, button1)); buttonCount++; } if (button2 != NULL) { view->AddChild(fButtons[2] = _CreateButton(2, button2)); buttonCount++; } // Find the widest button only if the widest value needs to be known. if (fButtonWidth == B_WIDTH_FROM_WIDEST) { float maxWidth = 0; for (int i = 0; i < buttonCount; i++) { float width = fButtons[i]->Bounds().Width(); if (width > maxWidth) maxWidth = width; } // resize buttons for (int i = 0; i < buttonCount; i++) { fButtons[i]->ResizeTo(maxWidth, fButtons[i]->Bounds().Height()); } } float defaultButtonFrameWidth = -fButtons[buttonCount - 1]->Bounds().Width() / 2.0f; SetDefaultButton(fButtons[buttonCount - 1]); defaultButtonFrameWidth += fButtons[buttonCount - 1]->Bounds().Width() / 2.0f; // Layout buttons float fontFactor = be_plain_font->Size() / 11.0f; for (int i = buttonCount - 1; i >= 0; --i) { float x = -fButtons[i]->Bounds().Width(); if (i + 1 == buttonCount) x += Bounds().right - kRightOffset + defaultButtonFrameWidth; else x += fButtons[i + 1]->Frame().left - kButtonSpacing; if (buttonCount > 1 && i == 0 && spacing == B_OFFSET_SPACING) x -= kButtonOffsetSpacing * fontFactor; fButtons[i]->MoveTo(x, fButtons[i]->Frame().top); } // Adjust the window's width, if necessary int32 iconLayoutScale = icon_layout_scale(); float totalWidth = kRightOffset + fButtons[buttonCount - 1]->Frame().right - defaultButtonFrameWidth - fButtons[0]->Frame().left; if (view->Bitmap()) { totalWidth += (kIconStripeWidth + kWindowIconOffset) * iconLayoutScale; } else totalWidth += kWindowMinOffset; float width = (spacing == B_OFFSET_SPACING ? kWindowOffsetMinWidth : kWindowMinWidth) * fontFactor; ResizeTo(max_c(totalWidth, width), Bounds().Height()); // Set up the text view BRect textViewRect(kLeftOffset, kTopOffset, Bounds().right - kRightOffset, fButtons[0]->Frame().top - kTextButtonOffset); if (view->Bitmap()) textViewRect.left = (kWindowIconOffset + kIconStripeWidth) * iconLayoutScale - 2; fTextView = new(std::nothrow) BTextView(textViewRect, "_tv_", textViewRect.OffsetByCopy(B_ORIGIN), B_FOLLOW_LEFT | B_FOLLOW_TOP, B_WILL_DRAW); if (fTextView == NULL) return; fTextView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); rgb_color textColor = ui_color(B_PANEL_TEXT_COLOR); fTextView->SetFontAndColor(be_plain_font, B_FONT_ALL, &textColor); fTextView->SetText(text, strlen(text)); fTextView->MakeEditable(false); fTextView->MakeSelectable(false); fTextView->SetWordWrap(true); view->AddChild(fTextView); // Now resize the TextView vertically so that all the text is visible float textHeight = fTextView->TextHeight(0, fTextView->CountLines()); textViewRect.OffsetTo(0, 0); textHeight -= textViewRect.Height(); ResizeBy(0, textHeight); fTextView->ResizeBy(0, textHeight); textViewRect.bottom += textHeight; fTextView->SetTextRect(textViewRect); AddCommonFilter(new(std::nothrow) _BAlertFilter_(this)); MoveTo(AlertPosition(Frame().Width(), Frame().Height())); }
BBitmap* BAlert::_CreateTypeIcon() { if (Type() == B_EMPTY_ALERT) return NULL; // The icons are in the app_server resources BBitmap* icon = NULL; BPath path; status_t status = find_directory(B_BEOS_SERVERS_DIRECTORY, &path); if (status != B_OK) { FTRACE((stderr, "BAlert::_CreateTypeIcon() - find_directory " "failed: %s\n", strerror(status))); return NULL; } path.Append("app_server"); BFile file; status = file.SetTo(path.Path(), B_READ_ONLY); if (status != B_OK) { FTRACE((stderr, "BAlert::_CreateTypeIcon() - BFile init failed: %s\n", strerror(status))); return NULL; } BResources resources; status = resources.SetTo(&file); if (status != B_OK) { FTRACE((stderr, "BAlert::_CreateTypeIcon() - BResources init " "failed: %s\n", strerror(status))); return NULL; } // Which icon are we trying to load? const char* iconName; switch (fType) { case B_INFO_ALERT: iconName = "info"; break; case B_IDEA_ALERT: iconName = "idea"; break; case B_WARNING_ALERT: iconName = "warn"; break; case B_STOP_ALERT: iconName = "stop"; break; default: // Alert type is either invalid or B_EMPTY_ALERT; // either way, we're not going to load an icon return NULL; } int32 iconSize = 32 * icon_layout_scale(); // Allocate the icon bitmap icon = new(std::nothrow) BBitmap(BRect(0, 0, iconSize - 1, iconSize - 1), 0, B_RGBA32); if (icon == NULL || icon->InitCheck() < B_OK) { FTRACE((stderr, "BAlert::_CreateTypeIcon() - No memory for bitmap\n")); delete icon; return NULL; } // Load the raw icon data size_t size = 0; const uint8* rawIcon; // Try to load vector icon rawIcon = (const uint8*)resources.LoadResource(B_VECTOR_ICON_TYPE, iconName, &size); if (rawIcon != NULL && BIconUtils::GetVectorIcon(rawIcon, size, icon) == B_OK) { return icon; } // Fall back to bitmap icon rawIcon = (const uint8*)resources.LoadResource(B_LARGE_ICON_TYPE, iconName, &size); if (rawIcon == NULL) { FTRACE((stderr, "BAlert::_CreateTypeIcon() - Icon resource not found\n")); delete icon; return NULL; } // Handle color space conversion if (icon->ColorSpace() != B_CMAP8) { BIconUtils::ConvertFromCMAP8(rawIcon, iconSize, iconSize, iconSize, icon); } return icon; }