Upstream version 5.34.104.0
[platform/framework/web/crosswalk.git] / src / third_party / trace-viewer / third_party / tvcm / src / tvcm / quad.js
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 'use strict';
6
7 tvcm.require('tvcm.gl_matrix');
8
9 tvcm.exportTo('tvcm', function() {
10   var tmpVec2s = [];
11   for (var i = 0; i < 8; i++)
12     tmpVec2s[i] = vec2.create();
13
14   var tmpVec2a = vec4.create();
15   var tmpVec4a = vec4.create();
16   var tmpVec4b = vec4.create();
17   var tmpMat4 = mat4.create();
18   var tmpMat4b = mat4.create();
19
20   var p00 = vec2.createXY(0, 0);
21   var p10 = vec2.createXY(1, 0);
22   var p01 = vec2.createXY(0, 1);
23   var p11 = vec2.createXY(1, 1);
24
25   var lerpingVecA = vec2.create();
26   var lerpingVecB = vec2.create();
27   function lerpVec2(out, a, b, amt) {
28     vec2.scale(lerpingVecA, a, amt);
29     vec2.scale(lerpingVecB, b, 1 - amt);
30     vec2.add(out, lerpingVecA, lerpingVecB);
31     vec2.normalize(out, out);
32     return out;
33   }
34
35   /**
36    * @constructor
37    */
38   function Quad() {
39     this.p1 = vec2.create();
40     this.p2 = vec2.create();
41     this.p3 = vec2.create();
42     this.p4 = vec2.create();
43   }
44
45   Quad.fromXYWH = function(x, y, w, h) {
46     var q = new Quad();
47     vec2.set(q.p1, x, y);
48     vec2.set(q.p2, x + w, y);
49     vec2.set(q.p3, x + w, y + h);
50     vec2.set(q.p4, x, y + h);
51     return q;
52   }
53
54   Quad.fromRect = function(r) {
55     return new Quad.fromXYWH(
56         r.x, r.y,
57         r.width, r.height);
58   }
59
60   Quad.from4Vecs = function(p1, p2, p3, p4) {
61     var q = new Quad();
62     vec2.set(q.p1, p1[0], p1[1]);
63     vec2.set(q.p2, p2[0], p2[1]);
64     vec2.set(q.p3, p3[0], p3[1]);
65     vec2.set(q.p4, p4[0], p4[1]);
66     return q;
67   }
68
69   Quad.from8Array = function(arr) {
70     if (arr.length != 8)
71       throw new Error('Array must be 8 long');
72     var q = new Quad();
73     q.p1[0] = arr[0];
74     q.p1[1] = arr[1];
75     q.p2[0] = arr[2];
76     q.p2[1] = arr[3];
77     q.p3[0] = arr[4];
78     q.p3[1] = arr[5];
79     q.p4[0] = arr[6];
80     q.p4[1] = arr[7];
81     return q;
82   };
83
84   Quad.prototype = {
85     pointInside: function(point) {
86       return pointInImplicitQuad(point,
87                                  this.p1, this.p2, this.p3, this.p4);
88     },
89
90     boundingRect: function() {
91       var x0 = Math.min(this.p1[0], this.p2[0], this.p3[0], this.p4[0]);
92       var y0 = Math.min(this.p1[1], this.p2[1], this.p3[1], this.p4[1]);
93
94       var x1 = Math.max(this.p1[0], this.p2[0], this.p3[0], this.p4[0]);
95       var y1 = Math.max(this.p1[1], this.p2[1], this.p3[1], this.p4[1]);
96
97       return new tvcm.Rect.fromXYWH(x0, y0, x1 - x0, y1 - y0);
98     },
99
100     clone: function() {
101       var q = new Quad();
102       vec2.copy(q.p1, this.p1);
103       vec2.copy(q.p2, this.p2);
104       vec2.copy(q.p3, this.p3);
105       vec2.copy(q.p4, this.p4);
106       return q;
107     },
108
109     scale: function(s) {
110       var q = new Quad();
111       this.scaleFast(q, s);
112       return q;
113     },
114
115     scaleFast: function(dstQuad, s) {
116       vec2.copy(dstQuad.p1, this.p1, s);
117       vec2.copy(dstQuad.p2, this.p2, s);
118       vec2.copy(dstQuad.p3, this.p3, s);
119       vec2.copy(dstQuad.p3, this.p3, s);
120     },
121
122     isRectangle: function() {
123       // Simple rectangle check. Note: will not handle out-of-order components.
124       var bounds = this.boundingRect();
125       return (
126           bounds.x == this.p1[0] &&
127           bounds.y == this.p1[1] &&
128           bounds.width == this.p2[0] - this.p1[0] &&
129           bounds.y == this.p2[1] &&
130           bounds.width == this.p3[0] - this.p1[0] &&
131           bounds.height == this.p3[1] - this.p2[1] &&
132           bounds.x == this.p4[0] &&
133           bounds.height == this.p4[1] - this.p2[1]
134       );
135     },
136
137     projectUnitRect: function(rect) {
138       var q = new Quad();
139       this.projectUnitRectFast(q, rect);
140       return q;
141     },
142
143     projectUnitRectFast: function(dstQuad, rect) {
144       var v12 = tmpVec2s[0];
145       var v14 = tmpVec2s[1];
146       var v23 = tmpVec2s[2];
147       var v43 = tmpVec2s[3];
148       var l12, l14, l23, l43;
149
150       vec2.sub(v12, this.p2, this.p1);
151       l12 = vec2.length(v12);
152       vec2.scale(v12, v12, 1 / l12);
153
154       vec2.sub(v14, this.p4, this.p1);
155       l14 = vec2.length(v14);
156       vec2.scale(v14, v14, 1 / l14);
157
158       vec2.sub(v23, this.p3, this.p2);
159       l23 = vec2.length(v23);
160       vec2.scale(v23, v23, 1 / l23);
161
162       vec2.sub(v43, this.p3, this.p4);
163       l43 = vec2.length(v43);
164       vec2.scale(v43, v43, 1 / l43);
165
166       var b12 = tmpVec2s[0];
167       var b14 = tmpVec2s[1];
168       var b23 = tmpVec2s[2];
169       var b43 = tmpVec2s[3];
170       lerpVec2(b12, v12, v43, rect.y);
171       lerpVec2(b43, v12, v43, 1 - rect.bottom);
172       lerpVec2(b14, v14, v23, rect.x);
173       lerpVec2(b23, v14, v23, 1 - rect.right);
174
175       vec2.addTwoScaledUnitVectors(tmpVec2a,
176                                    b12, l12 * rect.x,
177                                    b14, l14 * rect.y);
178       vec2.add(dstQuad.p1, this.p1, tmpVec2a);
179
180       vec2.addTwoScaledUnitVectors(tmpVec2a,
181                                    b12, l12 * -(1.0 - rect.right),
182                                    b23, l23 * rect.y);
183       vec2.add(dstQuad.p2, this.p2, tmpVec2a);
184
185
186       vec2.addTwoScaledUnitVectors(tmpVec2a,
187                                    b43, l43 * -(1.0 - rect.right),
188                                    b23, l23 * -(1.0 - rect.bottom));
189       vec2.add(dstQuad.p3, this.p3, tmpVec2a);
190
191       vec2.addTwoScaledUnitVectors(tmpVec2a,
192                                    b43, l43 * rect.left,
193                                    b14, l14 * -(1.0 - rect.bottom));
194       vec2.add(dstQuad.p4, this.p4, tmpVec2a);
195     },
196
197     toString: function() {
198       return 'Quad(' +
199           vec2.toString(this.p1) + ', ' +
200           vec2.toString(this.p2) + ', ' +
201           vec2.toString(this.p3) + ', ' +
202           vec2.toString(this.p4) + ')';
203     }
204   };
205
206   function sign(p1, p2, p3) {
207     return (p1[0] - p3[0]) * (p2[1] - p3[1]) -
208         (p2[0] - p3[0]) * (p1[1] - p3[1]);
209   }
210
211   function pointInTriangle2(pt, p1, p2, p3) {
212     var b1 = sign(pt, p1, p2) < 0.0;
213     var b2 = sign(pt, p2, p3) < 0.0;
214     var b3 = sign(pt, p3, p1) < 0.0;
215     return ((b1 == b2) && (b2 == b3));
216   }
217
218   function pointInImplicitQuad(point, p1, p2, p3, p4) {
219     return pointInTriangle2(point, p1, p2, p3) ||
220         pointInTriangle2(point, p1, p3, p4);
221   }
222
223   return {
224     pointInTriangle2: pointInTriangle2,
225     pointInImplicitQuad: pointInImplicitQuad,
226     Quad: Quad
227   };
228 });