void wxRenderer_DrawScrollbar(wxWindow* WXUNUSED(window), wxDC& dc, const wxRect& rect, wxOrientation orient, int current, wxScrollbarPart focusPart, wxScrollbarPart hoverPart, int max, int step, int flags) { const wxCoord x = rect.x; const wxCoord y = rect.y; const wxCoord w = rect.width; const wxCoord h = rect.height; dc.SetBrush( *wxWHITE_BRUSH ); dc.SetPen( *wxTRANSPARENT_PEN ); dc.DrawRectangle(rect); dc.SetBrush( *wxTRANSPARENT_BRUSH ); HIRect hiRect = CGRectMake( x, y, w, h ); CGContextRef cgContext = NULL; wxGraphicsContext* gc = NULL; #if wxCHECK_VERSION(2,9,0) wxGCDCImpl *impl = dynamic_cast<wxGCDCImpl*> (dc.GetImpl()); if (impl) gc = impl->GetGraphicsContext(); #else gc = dc.GetGraphicsContext(); #endif if (gc) cgContext = (CGContextRef) gc->GetNativeContext(); if (cgContext) { HIThemeTrackDrawInfo trackInfo; trackInfo.version = 0; trackInfo.kind = kThemeMediumScrollBar; trackInfo.bounds = hiRect; trackInfo.min = 0; trackInfo.max = max; trackInfo.value = current; trackInfo.trackInfo.scrollbar.viewsize = step; trackInfo.attributes = 0; if (orient == wxHORIZONTAL) trackInfo.attributes |= kThemeTrackHorizontal; trackInfo.enableState = (flags & wxCONTROL_FOCUSED) ? kThemeTrackActive : kThemeTrackInactive; trackInfo.trackInfo.scrollbar.pressState = wxScrollbarPartToHIPressedState(focusPart); trackInfo.attributes |= kThemeTrackShowThumb; if (flags & wxCONTROL_DISABLED) trackInfo.enableState = kThemeTrackDisabled; HIThemeDrawTrack(&trackInfo, 0, cgContext, kHIThemeOrientationNormal); } }
BOOL MacWidgetPainter::DrawSlider(const OpRect& rect, BOOL horizontal, double min, double max, double pos, BOOL highlighted, BOOL pressed_knob, OpRect& out_knob_position, OpPoint& out_start_track, OpPoint& out_end_track) { // Opera 11.50: We are going to use special skinned (non-toolkit) sliders for zoom sliders // so we are not drawing with our painter in that case if (!widget || widget->GetType() == OpTypedObject::WIDGET_TYPE_ZOOM_SLIDER) return FALSE; OpSkinElement *border_skin = widget->GetBorderSkin()->GetSkinElement(); if(!g_skin_manager->GetCurrentSkin() || (border_skin && !border_skin->IsNative())) { return IndpWidgetPainter::DrawSlider(rect, horizontal, min, max, pos, highlighted, pressed_knob, out_knob_position, out_start_track, out_end_track); } CGRect r = {{0, 0}, {rect.width, rect.height}}; CGContextRef context; OpBitmap* bitmap = NULL; int bmpwidth = rect.width; int bmpheight = rect.height; #ifdef PIXEL_SCALE_RENDERING_SUPPORT const PixelScaler& scaler = vd->GetVPScale(); bmpwidth = TO_DEVICE_PIXEL(scaler, bmpwidth); bmpheight = TO_DEVICE_PIXEL(scaler, bmpheight); #endif // PIXEL_SCALE_RENDERING_SUPPORT if(OpStatus::IsSuccess(OpBitmap::Create(&bitmap, bmpwidth, bmpheight, FALSE, TRUE, 0, 0, TRUE))) { int w = bitmap->Width(); int h = bitmap->Height(); int bpl = bitmap->GetBytesPerLine(); void *image_data = bitmap->GetPointer(OpBitmap::ACCESS_WRITEONLY); if (!image_data) { delete bitmap; return FALSE; } memset(image_data, 0, bpl*h); CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); CGBitmapInfo alpha = kCGBitmapByteOrderVegaInternal; context = CGBitmapContextCreate(image_data, w, h, 8, bpl, colorSpace, alpha); CGColorSpaceRelease(colorSpace); int win_height = rect.height; float scale = 1.0f; #ifdef PIXEL_SCALE_RENDERING_SUPPORT scale = TO_DEVICE_PIXEL(scaler, scale); #endif // PIXEL_SCALE_RENDERING_SUPPORT CGContextScaleCTM(context, scale, -scale); CGContextTranslateCTM(context, 0.0, -win_height); HIThemeTrackDrawInfo drawInfo; SInt32 thickness = 0; SInt32 shadow = 0; if (noErr == GetThemeMetric(kThemeMetricLargeProgressBarThickness, &thickness) && (noErr == GetThemeMetric(kThemeMetricProgressBarShadowOutset, &shadow))) { SInt32 progressHeight = thickness + shadow; if (horizontal) { if((r.size.height) > progressHeight) { float f = (r.size.height - progressHeight); r.origin.y += f / 2; r.size.height -= f; } } else { if((r.size.width) > progressHeight) { float f = (r.size.width - progressHeight); r.origin.x += f / 2; r.size.width -= f; } } } else { if (horizontal) { float f = (r.size.height / 4) - 1; r.origin.y += f / 2; r.size.height -= f; } else { float f = (r.size.width / 4) - 1; r.origin.x += f / 2; r.size.width -= f; } } drawInfo.version = 0; drawInfo.kind = kThemeSliderSmall; drawInfo.bounds = r; drawInfo.min = 0; drawInfo.max = NUMBER_OF_STEPS; if (widget->GetRTL()) drawInfo.value = (max - pos) / (max - min) * NUMBER_OF_STEPS; else drawInfo.value = (pos - min) / (max - min) * NUMBER_OF_STEPS; drawInfo.attributes = kThemeTrackShowThumb; if (horizontal) { drawInfo.attributes |= kThemeTrackHorizontal; } else { drawInfo.attributes |= kThemeTrackRightToLeft; } drawInfo.enableState = widget->IsEnabled() ? kThemeTrackActive : kThemeTrackInactive; drawInfo.trackInfo.slider.thumbDir = kThemeThumbPlain; drawInfo.trackInfo.slider.pressState = 0; if (highlighted) drawInfo.attributes |= kThemeTrackHasFocus; HIThemeDrawTrack(&drawInfo, NULL, context, kHIThemeOrientationNormal); HIShapeRef thumb_shape; HIRect thumb_bounds, track_bounds; HIThemeGetTrackThumbShape(&drawInfo, &thumb_shape); HIShapeGetBounds(thumb_shape, &thumb_bounds); HIThemeGetTrackBounds(&drawInfo, &track_bounds); CFRelease(thumb_shape); out_knob_position.Set(thumb_bounds.origin.x, thumb_bounds.origin.y, thumb_bounds.size.width, thumb_bounds.size.height); out_start_track.Set(track_bounds.origin.x, track_bounds.origin.y); out_end_track.Set(track_bounds.origin.x+track_bounds.size.width, track_bounds.origin.y+track_bounds.size.height); CGContextRelease(context); bitmap->ReleasePointer(); vd->BitmapOut(bitmap, OpRect(0, 0, bitmap->Width(), bitmap->Height()), rect); delete bitmap; } return TRUE; }
BOOL MacWidgetPainter::DrawScrollbar(const OpRect &drawrect) { HIThemeTrackDrawInfo drawInfo; ThemeTrackPressState pressState = 0; OpScrollbar *scroll = (OpScrollbar*)widget; HIShapeRef thumbRgn; OpRect opBounds = scroll->GetBounds(); CGRect bounds = {{-drawrect.x, -drawrect.y}, {opBounds.width, opBounds.height}}; pressState = (ThemeTrackPressState)scroll->GetHitPart(); // hack to draw correctly, for some reason DrawThemeTrack needs this. if(pressState == kThemeTopInsideArrowPressed) pressState = kThemeBottomInsideArrowPressed; else if(pressState == kThemeBottomInsideArrowPressed) pressState = kThemeTopInsideArrowPressed; if(scroll->horizontal) { bounds.size.width++; } else { bounds.size.height++; } OpWindow *rootWindow; BOOL inActiveWindow = FALSE; if (vd->GetView()) { rootWindow = vd->GetView()->GetContainer()->GetOpView()->GetRootWindow(); inActiveWindow = rootWindow->IsActiveTopmostWindow() || rootWindow->GetStyle() == OpWindow::STYLE_POPUP; } drawInfo.version = 0; drawInfo.kind = kThemeMediumScrollBar; drawInfo.enableState = (scroll->IsEnabled() && inActiveWindow) ? kThemeTrackActive : kThemeTrackInactive; drawInfo.attributes = kThemeTrackShowThumb | (scroll->horizontal ? kThemeTrackHorizontal : 0); drawInfo.bounds = bounds; drawInfo.min = scroll->limit_min; drawInfo.max = scroll->limit_max; drawInfo.value = scroll->value; drawInfo.trackInfo.scrollbar.viewsize = scroll->limit_visible; drawInfo.trackInfo.scrollbar.pressState = pressState; int minSize = g_op_ui_info->GetHorizontalScrollbarHeight(); if (GetOSVersion() >= 0x1070) { minSize = 0; } else if (GetInfo()->GetScrollbarArrowStyle() == ARROWS_AT_BOTTOM_AND_TOP) { minSize *= 6; minSize -= 4; } else { minSize *= 4; } // Bail out if smaller than minSize if(scroll->horizontal) { if((bounds.size.width) < minSize) { return FALSE; } } else { if((bounds.size.height) < minSize) { return FALSE; } } // Ok, the thumb(knob) could have been changed, let's update if(noErr == HIThemeGetTrackThumbShape(&drawInfo, &thumbRgn)) { HIRect thumbRect; OpRect thumbOpRect; HIShapeGetBounds(thumbRgn, &thumbRect); CFRelease(thumbRgn); thumbOpRect.x = thumbRect.origin.x - bounds.origin.x; thumbOpRect.y = thumbRect.origin.y - bounds.origin.y; thumbOpRect.width = thumbRect.size.width; thumbOpRect.height = thumbRect.size.height; scroll->SetKnobRect(thumbOpRect); } if (OpStatus::IsError(MacCachedObjectFactory<MacWidgetBitmap, MacWidgetBitmapTraits>::Init())) return FALSE; int bmpwidth = drawrect.width; int bmpheight = drawrect.height; #ifdef PIXEL_SCALE_RENDERING_SUPPORT const PixelScaler& scaler = vd->GetVPScale(); bmpwidth = TO_DEVICE_PIXEL(scaler, bmpwidth); bmpheight = TO_DEVICE_PIXEL(scaler, bmpheight); #endif // PIXEL_SCALE_RENDERING_SUPPORT MacWidgetBitmap* bitmap = MacCachedObjectFactory<MacWidgetBitmap, MacWidgetBitmapTraits>::CreateObject(MacWidgetBitmapTraits::CreateParam(bmpwidth, bmpheight)); if (!bitmap) return FALSE; // Set clip and draw widget->SetClipRect(drawrect); OpBitmap* bmp = bitmap->GetOpBitmap(); void* image_data = bmp->GetPointer(OpBitmap::ACCESS_WRITEONLY); if (!image_data) { bitmap->DecRef(); widget->RemoveClipRect(); return FALSE; } bitmap->Lock(); const int bpl = bmp->GetBytesPerLine(); memset(image_data, 0, bpl * bmp->Height()); CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); CGBitmapInfo alpha = kCGBitmapByteOrderVegaInternal; // create the context at size of drawrect instead of bitmap itself. // we cache the bitmap to prevent create-destroy cycle and reallocation. // since we need the bitmap's memory only, we can create a much smaller context within that buffer. CGContextRef context = CGBitmapContextCreate(image_data, bmpwidth, bmpheight, 8, bpl, colorSpace, alpha); CGColorSpaceRelease(colorSpace); if (!context) { bitmap->DecRef(); bmp->ReleasePointer(FALSE); widget->RemoveClipRect(); bitmap->Unlock(); return FALSE; } const int win_height = drawrect.height; CGFloat scale = 1.0f; #ifdef PIXEL_SCALE_RENDERING_SUPPORT scale = CGFloat(scaler.GetScale()) / 100.0f; #endif // PIXEL_SCALE_RENDERING_SUPPORT CGContextScaleCTM(context, scale, -scale); CGContextTranslateCTM(context, 0.0f, -win_height); HIThemeDrawTrack(&drawInfo, NULL, context, kHIThemeOrientationNormal); bmp->ReleasePointer(); vd->BitmapOut(bmp, OpRect(0, 0, bmp->Width(), bmp->Height()), drawrect); CGContextRelease(context); widget->RemoveClipRect(); bitmap->Unlock(); bitmap->DecRef(); return TRUE; }
BOOL MacWidgetPainter::DrawProgressbar(const OpRect &drawrect, double percent, INT32 progress_when_total_unknown, OpWidgetString* string, const char *skin_empty, const char *skin_full) { const char *full_skin = skin_full && *skin_full ? skin_full : "Progress Full Skin"; OpSkinElement *border_skin = g_skin_manager->GetSkinElement(full_skin); if(!g_skin_manager->GetCurrentSkin() || !border_skin || !border_skin->IsNative()) { return IndpWidgetPainter::DrawProgressbar(drawrect, percent, progress_when_total_unknown, string, skin_empty, skin_full); } UINT32 full_color = g_op_ui_info->GetUICSSColor(CSS_VALUE_HighlightText); g_skin_manager->GetTextColor(full_skin, &full_color); CGRect r = {{0, 0}, {drawrect.width, drawrect.height}}; CGContextRef context; OpBitmap* bitmap = NULL; int bmpwidth = drawrect.width; int bmpheight = drawrect.height; #ifdef PIXEL_SCALE_RENDERING_SUPPORT const PixelScaler& scaler = vd->GetVPScale(); bmpwidth = TO_DEVICE_PIXEL(scaler, bmpwidth); bmpheight = TO_DEVICE_PIXEL(scaler, bmpheight); #endif // PIXEL_SCALE_RENDERING_SUPPORT if(OpStatus::IsSuccess(OpBitmap::Create(&bitmap, bmpwidth, bmpheight, FALSE, TRUE, 0, 0, TRUE))) { int w = bitmap->Width(); int h = bitmap->Height(); int bpl = bitmap->GetBytesPerLine(); void *image_data = bitmap->GetPointer(OpBitmap::ACCESS_WRITEONLY); if (!image_data) { delete bitmap; return FALSE; } memset(image_data, 0, bpl*h); CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); CGBitmapInfo alpha = kCGBitmapByteOrderVegaInternal; context = CGBitmapContextCreate(image_data, w, h, 8, bpl, colorSpace, alpha); CGColorSpaceRelease(colorSpace); int win_height = drawrect.height; float scale = 1.0f; #ifdef PIXEL_SCALE_RENDERING_SUPPORT scale = TO_DEVICE_PIXEL(scaler, scale); #endif // PIXEL_SCALE_RENDERING_SUPPORT CGContextScaleCTM(context, scale, -scale); CGContextTranslateCTM(context, 0.0, -win_height); if (percent == 0 && progress_when_total_unknown) { HIThemeTrackDrawInfo drawInfo; SInt32 thickness = 0; SInt32 shadow = 0; if (noErr == GetThemeMetric(kThemeMetricLargeProgressBarThickness, &thickness) && (noErr == GetThemeMetric(kThemeMetricProgressBarShadowOutset, &shadow))) { SInt32 progressHeight = thickness + shadow; if((r.size.height) > progressHeight) { float f = (r.size.height - progressHeight); // / 2; r.origin.y += f; r.size.height -= f; } } else { float f = (r.size.height / 4) - 1; r.origin.y += f; r.size.height -= f; } drawInfo.version = 0; drawInfo.kind = kThemeIndeterminateBarLarge; drawInfo.bounds = r; drawInfo.min = 0; drawInfo.max = 100; drawInfo.value = 0; drawInfo.attributes = kThemeTrackHorizontal; drawInfo.enableState = widget->IsEnabled() ? kThemeTrackActive : kThemeTrackInactive; drawInfo.trackInfo.progress.phase = progress_when_total_unknown; HIThemeDrawTrack(&drawInfo, NULL, context, kHIThemeOrientationNormal); } else { HIThemeTrackDrawInfo drawInfo; SInt32 thickness = 0; SInt32 shadow = 0; if (noErr == GetThemeMetric(kThemeMetricLargeProgressBarThickness, &thickness) && (noErr == GetThemeMetric(kThemeMetricProgressBarShadowOutset, &shadow))) { SInt32 progressHeight = thickness + shadow; if((r.size.height) > progressHeight) { float f = (r.size.height - progressHeight); // / 2; r.origin.y += f; r.size.height -= f; } } else { float f = (r.size.height / 4) - 1; r.origin.y += f; r.size.height -= f; } drawInfo.version = 0; drawInfo.kind = kThemeProgressBarLarge; drawInfo.bounds = r; drawInfo.min = 0; drawInfo.max = 100; drawInfo.value = (SInt32)(percent); drawInfo.attributes = kThemeTrackHorizontal; drawInfo.enableState = widget->IsEnabled() ? kThemeTrackActive : kThemeTrackInactive; drawInfo.trackInfo.progress.phase = floorf(GetCurrentEventTime()*16); HIThemeDrawTrack(&drawInfo, NULL, context, kHIThemeOrientationNormal); } CGContextRelease(context); bitmap->ReleasePointer(); vd->BitmapOut(bitmap, OpRect(0, 0, bitmap->Width(), bitmap->Height()), drawrect); delete bitmap; } if (string) { widget->SetClipRect(drawrect); OpRect textRect = drawrect; textRect.y -= 1; string->Draw(textRect, vd, full_color); widget->RemoveClipRect(); } return TRUE; }