* Add Style::HasTransparency() which just tells if any of the colors that the
style uses has an alpha value below 255. * Add support for intermediate rendering passes to IconRenderer. Normally, the whole icon is rendered in a single pass, which means shapes cannot overlap. With the change, intermediate rendering passes are inserted when a shape is encountered that contains transparency. This is an easy way to allow for more feature rich icons, with easy support for glossy/reflective surface effects or other such effects that require support for transparent shapes on top of other shapes. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@24490 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -26,7 +26,7 @@
|
||||
|
||||
using std::nothrow;
|
||||
|
||||
class StyleHandler {
|
||||
class IconRenderer::StyleHandler {
|
||||
struct StyleItem {
|
||||
Style* style;
|
||||
Transformation transformation;
|
||||
@@ -96,7 +96,7 @@ private:
|
||||
|
||||
// color
|
||||
const agg::rgba8&
|
||||
StyleHandler::color(unsigned styleIndex)
|
||||
IconRenderer::StyleHandler::color(unsigned styleIndex)
|
||||
{
|
||||
StyleItem* styleItem = (StyleItem*)fStyles.ItemAt(styleIndex);
|
||||
if (!styleItem) {
|
||||
@@ -115,8 +115,8 @@ StyleHandler::color(unsigned styleIndex)
|
||||
|
||||
// generate_span
|
||||
void
|
||||
StyleHandler::generate_span(agg::rgba8* span, int x, int y,
|
||||
unsigned len, unsigned styleIndex)
|
||||
IconRenderer::StyleHandler::generate_span(agg::rgba8* span, int x, int y,
|
||||
unsigned len, unsigned styleIndex)
|
||||
{
|
||||
StyleItem* styleItem = (StyleItem*)fStyles.ItemAt(styleIndex);
|
||||
if (!styleItem || !styleItem->style->Gradient()) {
|
||||
@@ -172,12 +172,9 @@ StyleHandler::generate_span(agg::rgba8* span, int x, int y,
|
||||
// _GenerateGradient
|
||||
template<class GradientFunction>
|
||||
void
|
||||
StyleHandler::_GenerateGradient(agg::rgba8* span, int x, int y, unsigned len,
|
||||
GradientFunction function,
|
||||
int32 start, int32 end,
|
||||
const agg::rgba8* gradientColors,
|
||||
Transformation& gradientTransform)
|
||||
|
||||
IconRenderer::StyleHandler::_GenerateGradient(agg::rgba8* span, int x, int y,
|
||||
unsigned len, GradientFunction function, int32 start, int32 end,
|
||||
const agg::rgba8* gradientColors, Transformation& gradientTransform)
|
||||
{
|
||||
typedef agg::pod_auto_array<agg::rgba8, 256> ColorArray;
|
||||
typedef agg::span_interpolator_linear<> Interpolator;
|
||||
@@ -393,6 +390,12 @@ IconRenderer::_Render(const BRect& r)
|
||||
printf("IconRenderer::_Render() - out of memory\n");
|
||||
break;
|
||||
}
|
||||
|
||||
// if this is not the first shape, and the style contains
|
||||
// transparency, commit a render pass of previous shapes
|
||||
if (i > 0 && style->HasTransparency())
|
||||
_CommitRenderPass(styleHandler);
|
||||
|
||||
fRasterizer.styles(styleIndex, -1);
|
||||
styleIndex++;
|
||||
|
||||
@@ -409,12 +412,7 @@ IconRenderer::_Render(const BRect& r)
|
||||
}
|
||||
}
|
||||
|
||||
agg::render_scanlines_compound(fRasterizer,
|
||||
fScanline,
|
||||
fBinaryScanline,
|
||||
fBaseRendererPre,
|
||||
fSpanAllocator,
|
||||
styleHandler);
|
||||
_CommitRenderPass(styleHandler, false);
|
||||
|
||||
if (fGammaTable.gamma() != 1.0)
|
||||
fPixelFormat.apply_gamma_inv(fGammaTable);
|
||||
@@ -423,6 +421,19 @@ IconRenderer::_Render(const BRect& r)
|
||||
//printf("rendering 64x64: %lld\n", system_time() - start);
|
||||
}
|
||||
|
||||
// _CommitRenderPass
|
||||
void
|
||||
IconRenderer::_CommitRenderPass(StyleHandler& styleHandler, bool reset)
|
||||
{
|
||||
agg::render_scanlines_compound(fRasterizer,
|
||||
fScanline,
|
||||
fBinaryScanline,
|
||||
fBaseRendererPre,
|
||||
fSpanAllocator,
|
||||
styleHandler);
|
||||
if (reset)
|
||||
fRasterizer.reset();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -72,7 +72,11 @@ class IconRenderer {
|
||||
void Demultiply();
|
||||
|
||||
private:
|
||||
class StyleHandler;
|
||||
|
||||
void _Render(const BRect& area);
|
||||
void _CommitRenderPass(StyleHandler& styleHandler,
|
||||
bool reset = true);
|
||||
|
||||
BBitmap* fBitmap;
|
||||
const BBitmap* fBackground;
|
||||
|
||||
@@ -162,6 +162,22 @@ Style::operator==(const Style& other) const
|
||||
|
||||
#endif // ICON_O_MATIC
|
||||
|
||||
// HasTransparency
|
||||
bool
|
||||
Style::HasTransparency() const
|
||||
{
|
||||
if (fGradient) {
|
||||
int32 count = fGradient->CountColors();
|
||||
for (int32 i = 0; i < count; i++) {
|
||||
color_step* step = fGradient->ColorAtFast(i);
|
||||
if (step->color.alpha < 255)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return fColor.alpha < 255;
|
||||
}
|
||||
|
||||
// SetColor
|
||||
void
|
||||
Style::SetColor(const rgb_color& color)
|
||||
|
||||
@@ -55,6 +55,8 @@ class Style {
|
||||
inline void Notify() {}
|
||||
#endif // ICON_O_MATIC
|
||||
|
||||
bool HasTransparency() const;
|
||||
|
||||
void SetColor(const rgb_color& color);
|
||||
inline rgb_color Color() const
|
||||
{ return fColor; }
|
||||
|
||||
Reference in New Issue
Block a user