* 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:
Stephan Aßmus
2008-03-20 11:35:51 +00:00
parent a886f802fc
commit 112d61551e
4 changed files with 49 additions and 16 deletions
+27 -16
View File
@@ -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();
}
+4
View File
@@ -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;
+16
View File
@@ -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)
+2
View File
@@ -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; }