[gtk+/wip/alexl/broadway4: 85/96] broadway: Add linear gradient node
- From: Alexander Larsson <alexl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk+/wip/alexl/broadway4: 85/96] broadway: Add linear gradient node
- Date: Thu, 23 Nov 2017 09:53:24 +0000 (UTC)
commit 278370c8e5b74b9b1f6e63b1b4b508a2d76f8bc4
Author: Alexander Larsson <alexl redhat com>
Date: Wed Nov 22 12:31:36 2017 +0100
broadway: Add linear gradient node
gdk/broadway/broadway-protocol.h | 1 +
gdk/broadway/broadway.js | 84 ++++++++++++++++++++++++++++++++++----
gdk/broadway/broadwayd.c | 8 +++-
gsk/gskbroadwayrenderer.c | 22 ++++++++++
4 files changed, 106 insertions(+), 9 deletions(-)
---
diff --git a/gdk/broadway/broadway-protocol.h b/gdk/broadway/broadway-protocol.h
index bc772d9..e4ce21e 100644
--- a/gdk/broadway/broadway-protocol.h
+++ b/gdk/broadway/broadway-protocol.h
@@ -16,6 +16,7 @@ typedef enum { /* Sync changes with broadway.js */
BROADWAY_NODE_OUTSET_SHADOW = 4,
BROADWAY_NODE_INSET_SHADOW = 5,
BROADWAY_NODE_ROUNDED_CLIP = 6,
+ BROADWAY_NODE_LINEAR_GRADIENT = 7,
} BroadwayNodeType;
typedef enum {
diff --git a/gdk/broadway/broadway.js b/gdk/broadway/broadway.js
index 68f7b8a..45dae02 100644
--- a/gdk/broadway/broadway.js
+++ b/gdk/broadway/broadway.js
@@ -331,15 +331,16 @@ SwapNodes.prototype.decode_int32 = function() {
SwapNodes.prototype.decode_color = function() {
var rgba = this.decode_uint32();
- a = (rgba >> 24) & 0xff;
- r = (rgba >> 16) & 0xff;
- g = (rgba >> 8) & 0xff;
- b = (rgba >> 0) & 0xff;
+ var a = (rgba >> 24) & 0xff;
+ var r = (rgba >> 16) & 0xff;
+ var g = (rgba >> 8) & 0xff;
+ var b = (rgba >> 0) & 0xff;
+ var c;
if (a == 0)
c = "rgb(" + r + "," + g + "," + b + ")";
else
c = "rgba(" + r + "," + g + "," + b + "," + (a / 255.0) + ")";
- return c
+ return c;
}
SwapNodes.prototype.decode_float = function() {
@@ -350,7 +351,14 @@ SwapNodes.prototype.decode_size = function() {
var s = new Object();
s.width = this.decode_float ();
s.height = this.decode_float ();
- return s
+ return s;
+}
+
+SwapNodes.prototype.decode_point = function() {
+ var p = new Object();
+ p.x = this.decode_float ();
+ p.y = this.decode_float ();
+ return p;
}
SwapNodes.prototype.decode_rect = function() {
@@ -374,10 +382,25 @@ SwapNodes.prototype.decode_irect = function() {
SwapNodes.prototype.decode_rounded_rect = function() {
var r = new Object();
r.bounds = this.decode_rect();
- r.sizes = []
+ r.sizes = [];
for (var i = 0; i < 4; i++)
r.sizes[i] = this.decode_size();
- return r
+ return r;
+}
+
+SwapNodes.prototype.decode_color_stop = function() {
+ var s = new Object();
+ s.offset = this.decode_float ();
+ s.color = this.decode_color ();
+ return s;
+}
+
+SwapNodes.prototype.decode_color_stops = function() {
+ var stops = [];
+ var len = this.decode_uint32();
+ for (var i = 0; i < len; i++)
+ stops[i] = this.decode_color_stop();
+ return stops;
}
function args() {
@@ -524,6 +547,51 @@ SwapNodes.prototype.handle_node = function(parent, offset_x, offset_y)
}
break;
+ case 7: // LINEAR_GRADIENT
+ {
+ var rect = this.decode_rect();
+ var start = this.decode_point ();
+ var end = this.decode_point ();
+ var stops = this.decode_color_stops ();
+ var div = document.createElement('div');
+ div.style["position"] = "absolute";
+ set_rect_style(div, rect, offset_x, offset_y);
+
+ // direction:
+ var dx = end.x - start.x;
+ var dy = end.y - start.y;
+
+ // Angle in css coords (clockwise degrees, up = 0), note that y goes downwards so we have to
invert
+ var angle = Math.atan2(dx, -dy) * 180.0 / Math.PI;
+
+ // Figure out which corner has offset == 0 in css
+ var start_corner_x, start_corner_y;
+ if (dx >= 0) // going right
+ start_corner_x = rect.x;
+ else
+ start_corner_x = rect.x + rect.width;
+ if (dy >= 0) // going down
+ start_corner_y = rect.y;
+ else
+ start_corner_y = rect.y + rect.height;
+
+ /* project start corner on the line */
+ var l2 = dx*dx + dy*dy;
+ var l = Math.sqrt(l2);
+ var offset = ((start_corner_x - start.x) * dx + (start_corner_y - start.y) * dy) / l2;
+
+ var gradient = "linear-gradient(" + angle + "deg";
+ for (var i = 0; i < stops.length; i++) {
+ var stop = stops[i];
+ gradient = gradient + ", " + stop.color + " " + px(stop.offset * l - offset);
+ }
+ gradient = gradient + ")";
+
+ div.style["background-image"] = gradient;
+ parent.appendChild(div);
+ }
+ break;
+
default:
alert("Unexpected node type " + type);
}
diff --git a/gdk/broadway/broadwayd.c b/gdk/broadway/broadwayd.c
index b3ebd4b..693e76c 100644
--- a/gdk/broadway/broadwayd.c
+++ b/gdk/broadway/broadwayd.c
@@ -221,13 +221,14 @@ get_client_serial (BroadwayClient *client, guint32 daemon_serial)
#define NODE_SIZE_SIZE 2
#define NODE_SIZE_RECT (NODE_SIZE_POINT + NODE_SIZE_SIZE)
#define NODE_SIZE_RRECT (NODE_SIZE_RECT + 4 * NODE_SIZE_SIZE)
+#define NODE_SIZE_COLOR_STOP (NODE_SIZE_FLOAT + NODE_SIZE_COLOR)
static int
rewrite_node_textures (BroadwayClient *client,
int len, guint32 data[], int pos)
{
guint32 type;
- guint32 i, n_children;
+ guint32 i, n_children, n_stops;
g_assert (pos < len);
@@ -257,6 +258,11 @@ rewrite_node_textures (BroadwayClient *client,
pos += NODE_SIZE_RRECT;
pos = rewrite_node_textures (client, len, data, pos);
break;
+ case BROADWAY_NODE_LINEAR_GRADIENT:
+ pos += NODE_SIZE_RECT + 2 * NODE_SIZE_POINT;
+ n_stops = data[pos++];
+ pos += n_stops * NODE_SIZE_COLOR_STOP;
+ break;
default:
g_assert_not_reached ();
}
diff --git a/gsk/gskbroadwayrenderer.c b/gsk/gskbroadwayrenderer.c
index 0720369..b2ead65 100644
--- a/gsk/gskbroadwayrenderer.c
+++ b/gsk/gskbroadwayrenderer.c
@@ -146,6 +146,13 @@ add_rounded_rect (GArray *nodes, const GskRoundedRect *rrect)
}
static void
+add_color_stop (GArray *nodes, const GskColorStop *stop)
+{
+ add_float (nodes, stop->offset);
+ add_rgba (nodes, &stop->color);
+}
+
+static void
gsk_broadway_renderer_add_node (GskRenderer *self,
GArray *nodes,
GPtrArray *node_textures,
@@ -228,6 +235,21 @@ gsk_broadway_renderer_add_node (GskRenderer *self,
}
return;
+ case GSK_LINEAR_GRADIENT_NODE:
+ {
+ guint i, n;
+
+ add_uint32 (nodes, BROADWAY_NODE_LINEAR_GRADIENT);
+ add_rect (nodes, &node->bounds);
+ add_point (nodes, gsk_linear_gradient_node_peek_start (node));
+ add_point (nodes, gsk_linear_gradient_node_peek_end (node));
+ n = gsk_linear_gradient_node_get_n_color_stops (node);
+ add_uint32 (nodes, n);
+ for (i = 0; i < n; i++)
+ add_color_stop (nodes, &gsk_linear_gradient_node_peek_color_stops (node)[i]);
+ }
+ return;
+
default:
{
cairo_surface_t *surface;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]