aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rwxr-xr-xexperimental/Intersection/ActiveEdge_Test.cpp67
-rw-r--r--experimental/Intersection/BezierClip.cpp83
-rw-r--r--experimental/Intersection/BezierClip_Test.cpp24
-rw-r--r--experimental/Intersection/CubicIntersection.h5
-rw-r--r--experimental/Intersection/CubicIntersectionT.cpp154
-rw-r--r--experimental/Intersection/CubicParameterization_TestUtility.cpp53
-rw-r--r--experimental/Intersection/CubicRoots.cpp64
-rw-r--r--experimental/Intersection/CurveIntersection.h5
-rw-r--r--experimental/Intersection/DataTypes.h19
-rw-r--r--experimental/Intersection/EdgeApp.cpp176
-rw-r--r--experimental/Intersection/EdgeDemoApp-Info.plist32
-rw-r--r--experimental/Intersection/EdgeDemoApp.mm116
-rw-r--r--experimental/Intersection/EdgeDemoApp.xib3115
-rw-r--r--experimental/Intersection/EdgeMain.cpp11
-rw-r--r--experimental/Intersection/EdgeMain.h6
-rw-r--r--experimental/Intersection/EdgeWalker.cpp105
-rwxr-xr-xexperimental/Intersection/EdgeWalkerPolygon4x4_Test.cpp306
-rw-r--r--experimental/Intersection/EdgeWalkerPolygons_Test.cpp198
-rw-r--r--experimental/Intersection/EdgeWalkerQuadralaterals_Test.cpp74
-rw-r--r--experimental/Intersection/EdgeWalker_Test.h4
-rw-r--r--experimental/Intersection/EdgeWalker_TestUtility.cpp8
-rw-r--r--experimental/Intersection/IntersectionUtilities.cpp4
-rw-r--r--experimental/Intersection/Intersection_Tests.cpp6
-rw-r--r--experimental/Intersection/Intersection_Tests.h4
-rw-r--r--experimental/Intersection/LineIntersection.h4
-rw-r--r--experimental/Intersection/QuadraticParameterization_TestUtility.cpp17
-rw-r--r--experimental/Intersection/QuadraticUtilities.cpp1
-rw-r--r--experimental/Intersection/ReduceOrder.cpp238
-rw-r--r--experimental/Intersection/ReduceOrder_Test.cpp138
-rw-r--r--experimental/Intersection/ShapeOps.h6
-rw-r--r--experimental/Intersection/ShapeOpsDemo-Info.plist32
-rw-r--r--experimental/Intersection/ShapeOpsDemo.cpp110
-rw-r--r--experimental/Intersection/TSearch.h5
-rw-r--r--experimental/Intersection/edge.xcodeproj/project.pbxproj121
-rw-r--r--experimental/Intersection/op.htm58
35 files changed, 4122 insertions, 1247 deletions
diff --git a/experimental/Intersection/ActiveEdge_Test.cpp b/experimental/Intersection/ActiveEdge_Test.cpp
new file mode 100755
index 0000000000..2ee408921e
--- /dev/null
+++ b/experimental/Intersection/ActiveEdge_Test.cpp
@@ -0,0 +1,67 @@
+#include "CurveIntersection.h"
+#include "LineIntersection.h"
+#include "SkPath.h"
+#include "SkRect.h"
+#include "SkTArray.h"
+#include "SkTDArray.h"
+#include "TSearch.h"
+
+namespace UnitTest {
+
+#include "EdgeWalker.cpp"
+
+} // end of UnitTest namespace
+
+#include "Intersection_Tests.h"
+
+SkPoint leftRight[][4] = {
+// equal length
+ {{10, 10}, {10, 50}, {20, 10}, {20, 50}},
+ {{10, 10}, {10, 50}, {10, 10}, {20, 50}},
+ {{10, 10}, {10, 50}, {20, 10}, {10, 50}},
+// left top higher
+ {{10, 0}, {10, 50}, {20, 10}, {20, 50}},
+ {{10, 0}, {10, 50}, {10, 10}, {20, 50}},
+ {{10, 0}, {10, 50}, {20, 10}, {10, 50}},
+ {{10, 0}, {10, 50}, {20, 10}, {10 + 0.000001, 40}},
+// left top lower
+ {{10, 20}, {10, 50}, {20, 10}, {20, 50}},
+ {{10, 20}, {10, 50}, {10, 10}, {20, 50}},
+ {{10, 20}, {10, 50}, {20, 10}, {10, 50}},
+ {{10, 20}, {10, 50}, {20, 10}, {10 + 0.000001, 40}},
+ {{10, 20}, {10, 50}, { 0, 0}, {50, 50}},
+// left bottom higher
+ {{10, 10}, {10, 40}, {20, 10}, {20, 50}},
+ {{10, 10}, {10, 40}, {10, 10}, {20, 50}},
+ {{10, 10}, {10, 40}, {20, 10}, {10, 50}},
+ {{10, 10}, {10, 40}, {20, 10}, { 0 + 0.000001, 70}},
+// left bottom lower
+ {{10, 10}, {10, 60}, {20, 10}, {20, 50}},
+ {{10, 10}, {10, 60}, {10, 10}, {20, 50}},
+ {{10, 10}, {10, 60}, {20, 10}, {10 + 0.000001, 50}},
+ {{10, 10}, {10, 60}, {20, 10}, {10 + 0.000001, 40}},
+ {{10, 10}, {10, 60}, { 0, 0}, {20 + 0.000001, 20}},
+};
+
+size_t leftRightCount = sizeof(leftRight) / sizeof(leftRight[0]);
+
+void ActiveEdge_Test() {
+ UnitTest::InEdge leftIn, rightIn;
+ UnitTest::ActiveEdge left, right;
+ left.fWorkEdge.fEdge = &leftIn;
+ right.fWorkEdge.fEdge = &rightIn;
+ for (size_t x = 0; x < leftRightCount; ++x) {
+ left.fAbove = leftRight[x][0];
+ left.fBelow = leftRight[x][1];
+ right.fAbove = leftRight[x][2];
+ right.fBelow = leftRight[x][3];
+ SkASSERT(left < right);
+ SkASSERT(left.operator_less_than(right));
+ SkASSERT(!(right < left));
+ SkASSERT(!right.operator_less_than(left));
+ }
+}
+
+
+
+
diff --git a/experimental/Intersection/BezierClip.cpp b/experimental/Intersection/BezierClip.cpp
deleted file mode 100644
index 1b5c60c182..0000000000
--- a/experimental/Intersection/BezierClip.cpp
+++ /dev/null
@@ -1,83 +0,0 @@
-#include "CubicIntersection.h"
-#include "LineParameters.h"
-#include <algorithm> // used for std::swap
-
-// return false if unable to clip (e.g., unable to create implicit line)
-// caller should subdivide, or create degenerate if the values are too small
-bool bezier_clip(const Cubic& cubic1, const Cubic& cubic2, double& minT, double& maxT) {
- minT = 1;
- maxT = 0;
- // determine normalized implicit line equation for pt[0] to pt[3]
- // of the form ax + by + c = 0, where a*a + b*b == 1
-
- // find the implicit line equation parameters
- LineParameters endLine;
- endLine.cubicEndPoints(cubic1);
- if (!endLine.normalize()) {
- printf("line cannot be normalized: need more code here\n");
- return false;
- }
-
- double distance[2];
- endLine.controlPtDistance(cubic1, distance);
-
- // find fat line
- double top = distance[0];
- double bottom = distance[1];
- if (top > bottom) {
- std::swap(top, bottom);
- }
- if (top * bottom >= 0) {
- const double scale = 3/4.0; // http://cagd.cs.byu.edu/~tom/papers/bezclip.pdf (13)
- if (top < 0) {
- top *= scale;
- bottom = 0;
- } else {
- top = 0;
- bottom *= scale;
- }
- } else {
- const double scale = 4/9.0; // http://cagd.cs.byu.edu/~tom/papers/bezclip.pdf (15)
- top *= scale;
- bottom *= scale;
- }
-
- // compute intersecting candidate distance
- Cubic distance2y; // points with X of (0, 1/3, 2/3, 1)
- endLine.cubicDistanceY(cubic2, distance2y);
-
- int flags = 0;
- if (approximately_lesser(distance2y[0].y, top)) {
- flags |= kFindTopMin;
- } else if (approximately_greater(distance2y[0].y, bottom)) {
- flags |= kFindBottomMin;
- } else {
- minT = 0;
- }
-
- if (approximately_lesser(distance2y[3].y, top)) {
- flags |= kFindTopMax;
- } else if (approximately_greater(distance2y[3].y, bottom)) {
- flags |= kFindBottomMax;
- } else {
- maxT = 1;
- }
- // Find the intersection of distance convex hull and fat line.
- char to_0[2];
- char to_3[2];
- bool do_1_2_edge = convex_x_hull(distance2y, to_0, to_3);
- x_at(distance2y[0], distance2y[to_0[0]], top, bottom, flags, minT, maxT);
- if (to_0[0] != to_0[1]) {
- x_at(distance2y[0], distance2y[to_0[1]], top, bottom, flags, minT, maxT);
- }
- x_at(distance2y[to_3[0]], distance2y[3], top, bottom, flags, minT, maxT);
- if (to_3[0] != to_3[1]) {
- x_at(distance2y[to_3[1]], distance2y[3], top, bottom, flags, minT, maxT);
- }
- if (do_1_2_edge) {
- x_at(distance2y[1], distance2y[2], top, bottom, flags, minT, maxT);
- }
-
- return minT < maxT; // returns false if distance shows no intersection
-}
-
diff --git a/experimental/Intersection/BezierClip_Test.cpp b/experimental/Intersection/BezierClip_Test.cpp
deleted file mode 100644
index 3228d89779..0000000000
--- a/experimental/Intersection/BezierClip_Test.cpp
+++ /dev/null
@@ -1,24 +0,0 @@
-#include "CubicIntersection.h"
-#include "CubicIntersection_TestData.h"
-#include "CubicIntersection_Tests.h"
-
-void BezierClip_Test() {
- for (size_t index = 0; index < tests_count; ++index) {
- const Cubic& cubic1 = tests[index][0];
- const Cubic& cubic2 = tests[index][1];
- Cubic reduce1, reduce2;
- int order1 = reduceOrder(cubic1, reduce1, kReduceOrder_NoQuadraticsAllowed);
- int order2 = reduceOrder(cubic2, reduce2, kReduceOrder_NoQuadraticsAllowed);
- if (order1 < 4) {
- printf("%s [%d] cubic1 order=%d\n", __FUNCTION__, (int) index, order1);
- }
- if (order2 < 4) {
- printf("%s [%d] cubic2 order=%d\n", __FUNCTION__, (int) index, order2);
- }
- if (order1 == 4 && order2 == 4) {
- double minT = 0;
- double maxT = 1;
- bezier_clip(reduce1, reduce2, minT, maxT);
- }
- }
-}
diff --git a/experimental/Intersection/CubicIntersection.h b/experimental/Intersection/CubicIntersection.h
index e5d74c0a2b..b918400d88 100644
--- a/experimental/Intersection/CubicIntersection.h
+++ b/experimental/Intersection/CubicIntersection.h
@@ -1,3 +1,6 @@
+#ifndef CubicIntersection_DEFINE
+#define CubicIntersection_DEFINE
+
#include "DataTypes.h"
class Intersections;
@@ -33,3 +36,5 @@ bool intersectStartT(const Cubic& cubic1, const Cubic& cubic2, Intersections& );
bool intersectStart(const Cubic& cubic, const _Line& line, Intersections& );
bool intersectStart(const Quadratic& q1, const Quadratic& q2, Intersections& );
bool intersectStart(const Quadratic& quad, const _Line& line, Intersections& );
+
+#endif
diff --git a/experimental/Intersection/CubicIntersectionT.cpp b/experimental/Intersection/CubicIntersectionT.cpp
deleted file mode 100644
index 615c3a785c..0000000000
--- a/experimental/Intersection/CubicIntersectionT.cpp
+++ /dev/null
@@ -1,154 +0,0 @@
-#include "CubicIntersection.h"
-#include "Intersections.h"
-#include "IntersectionUtilities.h"
-#include "LineIntersection.h"
-
-class CubicIntersections : public Intersections {
-public:
-
-CubicIntersections(const Cubic& c1, const Cubic& c2, Intersections& i)
- : cubic1(c1)
- , cubic2(c2)
- , intersections(i)
- , depth(0)
- , splits(0) {
-}
-
-bool intersect() {
- double minT1, minT2, maxT1, maxT2;
- if (!bezier_clip(cubic2, cubic1, minT1, maxT1)) {
- return false;
- }
- if (!bezier_clip(cubic1, cubic2, minT2, maxT2)) {
- return false;
- }
- int split;
- if (maxT1 - minT1 < maxT2 - minT2) {
- intersections.swap();
- minT2 = 0;
- maxT2 = 1;
- split = maxT1 - minT1 > tClipLimit;
- } else {
- minT1 = 0;
- maxT1 = 1;
- split = (maxT2 - minT2 > tClipLimit) << 1;
- }
- return chop(minT1, maxT1, minT2, maxT2, split);
-}
-
-protected:
-
-bool intersect(double minT1, double maxT1, double minT2, double maxT2) {
- Cubic smaller, larger;
- // FIXME: carry last subdivide and reduceOrder result with cubic
- sub_divide(cubic1, minT1, maxT1, intersections.swapped() ? larger : smaller);
- sub_divide(cubic2, minT2, maxT2, intersections.swapped() ? smaller : larger);
- Cubic smallResult;
- if (reduceOrder(smaller, smallResult,
- kReduceOrder_NoQuadraticsAllowed) <= 2) {
- Cubic largeResult;
- if (reduceOrder(larger, largeResult,
- kReduceOrder_NoQuadraticsAllowed) <= 2) {
- _Point pt;
- const _Line& smallLine = (const _Line&) smallResult;
- const _Line& largeLine = (const _Line&) largeResult;
- if (!lineIntersect(smallLine, largeLine, &pt)) {
- return false;
- }
- double smallT = t_at(smallLine, pt);
- double largeT = t_at(largeLine, pt);
- if (intersections.swapped()) {
- smallT = interp(minT2, maxT2, smallT);
- largeT = interp(minT1, maxT1, largeT);
- } else {
- smallT = interp(minT1, maxT1, smallT);
- largeT = interp(minT2, maxT2, largeT);
- }
- intersections.add(smallT, largeT);
- return true;
- }
- }
- double minT, maxT;
- if (!bezier_clip(smaller, larger, minT, maxT)) {
- if (minT == maxT) {
- if (intersections.swapped()) {
- minT1 = (minT1 + maxT1) / 2;
- minT2 = interp(minT2, maxT2, minT);
- } else {
- minT1 = interp(minT1, maxT1, minT);
- minT2 = (minT2 + maxT2) / 2;
- }
- intersections.add(minT1, minT2);
- return true;
- }
- return false;
- }
-
- int split;
- if (intersections.swapped()) {
- double newMinT1 = interp(minT1, maxT1, minT);
- double newMaxT1 = interp(minT1, maxT1, maxT);
- split = (newMaxT1 - newMinT1 > (maxT1 - minT1) * tClipLimit) << 1;
-#define VERBOSE 0
-#if VERBOSE
- printf("%s d=%d s=%d new1=(%g,%g) old1=(%g,%g) split=%d\n",
- __FUNCTION__, depth, splits, newMinT1, newMaxT1, minT1, maxT1,
- split);
-#endif
- minT1 = newMinT1;
- maxT1 = newMaxT1;
- } else {
- double newMinT2 = interp(minT2, maxT2, minT);
- double newMaxT2 = interp(minT2, maxT2, maxT);
- split = newMaxT2 - newMinT2 > (maxT2 - minT2) * tClipLimit;
-#if VERBOSE
- printf("%s d=%d s=%d new2=(%g,%g) old2=(%g,%g) split=%d\n",
- __FUNCTION__, depth, splits, newMinT2, newMaxT2, minT2, maxT2,
- split);
-#endif
- minT2 = newMinT2;
- maxT2 = newMaxT2;
- }
- return chop(minT1, maxT1, minT2, maxT2, split);
-}
-
-bool chop(double minT1, double maxT1, double minT2, double maxT2, int split) {
- ++depth;
- intersections.swap();
- if (split) {
- ++splits;
- if (split & 2) {
- double middle1 = (maxT1 + minT1) / 2;
- intersect(minT1, middle1, minT2, maxT2);
- intersect(middle1, maxT1, minT2, maxT2);
- } else {
- double middle2 = (maxT2 + minT2) / 2;
- intersect(minT1, maxT1, minT2, middle2);
- intersect(minT1, maxT1, middle2, maxT2);
- }
- --splits;
- intersections.swap();
- --depth;
- return intersections.intersected();
- }
- bool result = intersect(minT1, maxT1, minT2, maxT2);
- intersections.swap();
- --depth;
- return result;
-}
-
-private:
-
-static const double tClipLimit = 0.8; // http://cagd.cs.byu.edu/~tom/papers/bezclip.pdf see Multiple intersections
-const Cubic& cubic1;
-const Cubic& cubic2;
-Intersections& intersections;
-int depth;
-int splits;
-};
-
-bool intersectStartT(const Cubic& c1, const Cubic& c2, Intersections& i) {
- CubicIntersections c(c1, c2, i);
- return c.intersect();
-}
-
diff --git a/experimental/Intersection/CubicParameterization_TestUtility.cpp b/experimental/Intersection/CubicParameterization_TestUtility.cpp
deleted file mode 100644
index 356ca88f85..0000000000
--- a/experimental/Intersection/CubicParameterization_TestUtility.cpp
+++ /dev/null
@@ -1,53 +0,0 @@
-// included by CubicParameterization.cpp
-// accesses internal functions to validate parameterized coefficients
-
-#include "Parameterization_Test.h"
-
-static void parameter_coeffs(const Cubic& cubic, double coeffs[coeff_count]) {
-#if USE_SYVESTER
- double ax, bx, cx, dx;
- if (try_alt)
- alt_set_abcd(&cubic[0].x, ax, bx, cx, dx);
- else
- set_abcd(&cubic[0].x, ax, bx, cx, dx);
- double ay, by, cy, dy;
- if (try_alt)
- alt_set_abcd(&cubic[0].y, ay, by, cy, dy);
- else
- set_abcd(&cubic[0].y, ay, by, cy, dy);
- calc_ABCD(ax, ay, coeffs);
- if (!try_alt) calc_bc(dx, bx, cx);
- if (!try_alt) calc_bc(dy, by, cy);
-#else
- double ax = cubic[0].x;
- double bx = cubic[1].x;
- double cx = cubic[2].x;
- double dx = cubic[3].x;
- double ay = cubic[0].y;
- double by = cubic[1].y;
- double cy = cubic[2].y;
- double dy = cubic[3].y;
- calc_ABCD(ax, bx, cx, dx, ay, by, cy, dy, coeffs);
-#endif
- for (int index = xx_coeff; index < coeff_count; ++index) {
- int procIndex = index - xx_coeff;
- coeffs[index] = (*calc_proc[procIndex])(ax, bx, cx, dx, ay, by, cy, dy);
- }
-}
-
-bool point_on_parameterized_curve(const Cubic& cubic, const _Point& point) {
- double coeffs[coeff_count];
- parameter_coeffs(cubic, coeffs);
- double xxx = coeffs[xxx_coeff] * point.x * point.x * point.x;
- double xxy = coeffs[xxy_coeff] * point.x * point.x * point.y;
- double xyy = coeffs[xyy_coeff] * point.x * point.y * point.y;
- double yyy = coeffs[yyy_coeff] * point.y * point.y * point.y;
- double xx = coeffs[ xx_coeff] * point.x * point.x;
- double xy = coeffs[ xy_coeff] * point.x * point.y;
- double yy = coeffs[ yy_coeff] * point.y * point.y;
- double x = coeffs[ x_coeff] * point.x;
- double y = coeffs[ y_coeff] * point.y;
- double c = coeffs[ c_coeff];
- double sum = xxx + xxy + xyy + yyy + xx + xy + yy + x + y + c;
- return approximately_zero(sum);
-}
diff --git a/experimental/Intersection/CubicRoots.cpp b/experimental/Intersection/CubicRoots.cpp
deleted file mode 100644
index f776c2d811..0000000000
--- a/experimental/Intersection/CubicRoots.cpp
+++ /dev/null
@@ -1,64 +0,0 @@
-#include "CubicUtilities.h"
-#include "DataTypes.h"
-#include "QuadraticUtilities.h"
-
-const double PI = 4 * atan(1);
-
-static bool is_unit_interval(double x) {
- return x > 0 && x < 1;
-}
-
-// from SkGeometry.cpp (and Numeric Solutions, 5.6)
-int cubicRoots(double A, double B, double C, double D, double t[3]) {
- if (approximately_zero(A)) { // we're just a quadratic
- return quadraticRoots(B, C, D, t);
- }
- double a, b, c;
- {
- double invA = 1 / A;
- a = B * invA;
- b = C * invA;
- c = D * invA;
- }
- double a2 = a * a;
- double Q = (a2 - b * 3) / 9;
- double R = (2 * a2 * a - 9 * a * b + 27 * c) / 54;
- double Q3 = Q * Q * Q;
- double R2MinusQ3 = R * R - Q3;
- double adiv3 = a / 3;
- double* roots = t;
- double r;
-
- if (R2MinusQ3 < 0) // we have 3 real roots
- {
- double theta = acos(R / sqrt(Q3));
- double neg2RootQ = -2 * sqrt(Q);
-
- r = neg2RootQ * cos(theta / 3) - adiv3;
- if (is_unit_interval(r))
- *roots++ = r;
-
- r = neg2RootQ * cos((theta + 2 * PI) / 3) - adiv3;
- if (is_unit_interval(r))
- *roots++ = r;
-
- r = neg2RootQ * cos((theta - 2 * PI) / 3) - adiv3;
- if (is_unit_interval(r))
- *roots++ = r;
- }
- else // we have 1 real root
- {
- double A = fabs(R) + sqrt(R2MinusQ3);
- A = cube_root(A);
- if (R > 0) {
- A = -A;
- }
- if (A != 0) {
- A += Q / A;
- }
- r = A - adiv3;
- if (is_unit_interval(r))
- *roots++ = r;
- }
- return (int)(roots - t);
-}
diff --git a/experimental/Intersection/CurveIntersection.h b/experimental/Intersection/CurveIntersection.h
index f95e028632..88316fab7c 100644
--- a/experimental/Intersection/CurveIntersection.h
+++ b/experimental/Intersection/CurveIntersection.h
@@ -1,3 +1,6 @@
+#ifndef CurveIntersection_DEFINE
+#define CurveIntersection_DEFINE
+
#include "DataTypes.h"
class Intersections;
@@ -32,3 +35,5 @@ bool intersect(const Cubic& cubic1, const Cubic& cubic2, Intersections& );
int intersect(const Cubic& cubic, const _Line& line, double cRange[3], double lRange[3]);
bool intersect(const Quadratic& q1, const Quadratic& q2, Intersections& );
bool intersect(const Quadratic& quad, const _Line& line, Intersections& );
+
+#endif
diff --git a/experimental/Intersection/DataTypes.h b/experimental/Intersection/DataTypes.h
index 8b97cec0e0..290a336e35 100644
--- a/experimental/Intersection/DataTypes.h
+++ b/experimental/Intersection/DataTypes.h
@@ -1,15 +1,16 @@
#ifndef __DataTypes_h__
#define __DataTypes_h__
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-extern double fabs( double );
-
-#ifdef __cplusplus
-}
-#endif
+#include <assert.h>
+#include <float.h>
+#include <limits.h>
+#include <math.h>
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <strings.h>
+#include <sys/types.h>
extern const double PointEpsilon;
extern const double SquaredEpsilon;
diff --git a/experimental/Intersection/EdgeApp.cpp b/experimental/Intersection/EdgeApp.cpp
deleted file mode 100644
index 9bf419d7de..0000000000
--- a/experimental/Intersection/EdgeApp.cpp
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * EdgeApp.cpp
- * edge
- *
- * Created by Cary Clark on 7/6/11.
- * Copyright 2011 __MyCompanyName__. All rights reserved.
- *
- */
-
-#include "SkCanvas.h"
-#include "SkDevice.h"
-#include "SkGraphics.h"
-#include "SkImageEncoder.h"
-#include "SkPaint.h"
-#include "SkPicture.h"
-#include "SkStream.h"
-#include "SkTime.h"
-#include "SkWindow.h"
-
-#include "SkTouchGesture.h"
-#include "SkTypeface.h"
-
-#include "Intersection_Tests.h"
-
-extern void CreateSweep(SkBitmap* , float width);
-extern void CreateHorz(SkBitmap* );
-extern void CreateVert(SkBitmap* );
-extern void CreateAngle(SkBitmap* sweep, float angle);
-extern void SkAntiEdge_Test();
-
-
-static const char gCharEvtName[] = "Char_Event";
-static const char gKeyEvtName[] = "Key_Event";
-
-class SkEdgeView : public SkView {
-public:
- SkEdgeView() {
- CreateSweep(&fSweep_1_0, 1);
- CreateSweep(&fSweep_1_2, 1.2f);
- CreateSweep(&fSweep_1_4, 1.4f);
- CreateSweep(&fSweep_1_6, 1.6f);
- CreateHorz(&fBitmapH);
- CreateVert(&fBitmapV);
- CreateAngle(&fAngle_12, 12);
- CreateAngle(&fAngle_45, 45);
- }
- virtual ~SkEdgeView() {}
-
-protected:
- virtual void onDraw(SkCanvas* canvas) {
- canvas->drawColor(SK_ColorWHITE);
- canvas->drawBitmap(fSweep_1_0, 0, 10);
- canvas->drawBitmap(fBitmapH, 110, 10);
- canvas->drawBitmap(fBitmapV, 220, 10);
- canvas->drawBitmap(fSweep_1_2, 0, 110);
- canvas->drawBitmap(fSweep_1_4, 100, 110);
- canvas->drawBitmap(fSweep_1_6, 200, 110);
- canvas->drawBitmap(fAngle_12, 0, 200);
- canvas->drawBitmap(fAngle_45, 124, 220);
- }
-
-private:
- SkBitmap fSweep_1_0;
- SkBitmap fSweep_1_2;
- SkBitmap fSweep_1_4;
- SkBitmap fSweep_1_6;
- SkBitmap fBitmapH;
- SkBitmap fBitmapV;
- SkBitmap fAngle_12;
- SkBitmap fAngle_45;
- typedef SkView INHERITED;
-};
-
-class EdgeWindow : public SkOSWindow {
-public:
- EdgeWindow(void* hwnd) : INHERITED(hwnd) {
- this->setConfig(SkBitmap::kARGB_8888_Config);
- this->setVisibleP(true);
- fView.setVisibleP(true);
- fView.setClipToBounds(false);
- this->attachChildToFront(&fView)->unref();
- }
- virtual ~EdgeWindow() {}
-
- virtual void draw(SkCanvas* canvas){
- this->INHERITED::draw(canvas);
- }
-
-
-protected:
- SkEdgeView fView;
-
- virtual void onDraw(SkCanvas* canvas) {
- }
-
- virtual bool onHandleKey(SkKey key) {
- SkEvent evt(gKeyEvtName);
- evt.setFast32(key);
- if (fView.doQuery(&evt)) {
- return true;
- }
- return this->INHERITED::onHandleKey(key);
- }
-
- virtual bool onHandleChar(SkUnichar uni) {
- SkEvent evt(gCharEvtName);
- evt.setFast32(uni);
- if (fView.doQuery(&evt)) {
- return true;
- }
- return this->INHERITED::onHandleChar(uni);
- }
-
- virtual void onSizeChange() {
- fView.setSize(this->width(), this->height());
- this->INHERITED::onSizeChange();
- }
-
- virtual SkCanvas* beforeChildren(SkCanvas* canvas) {
- return this->INHERITED::beforeChildren(canvas);
- }
-
- virtual void afterChildren(SkCanvas*) {}
- virtual void beforeChild(SkView* child, SkCanvas* canvas) {}
- virtual void afterChild(SkView* child, SkCanvas* canvas) {}
-
- virtual bool onEvent(const SkEvent& evt) {
- return this->INHERITED::onEvent(evt);
- }
-
- virtual bool onQuery(SkEvent* evt) {
- return this->INHERITED::onQuery(evt);
- }
-
- virtual bool onDispatchClick(int x, int y, Click::State state, void* owner) {
- int w = SkScalarRound(this->width());
- int h = SkScalarRound(this->height());
- // check for the resize-box
- if (w - x < 16 && h - y < 16) {
- return false; // let the OS handle the click
- } else {
- return this->INHERITED::onDispatchClick(x, y, state, owner);
- }
- }
-
- virtual bool onClick(Click* click) {
- return false;
- }
-
- virtual Click* onFindClickHandler(SkScalar x, SkScalar y) {
- return 0;
- }
-
- typedef SkOSWindow INHERITED;
-};
-
-
-#include "SkApplication.h"
-
-SkOSWindow* create_sk_window(void* hwnd, int argc, char** argv) {
- return new EdgeWindow(hwnd);
-}
-
-void application_init() {
- SkGraphics::Init();
- SkEvent::Init();
-
- Intersection_Tests();
- SkAntiEdge_Test();
-}
-
-void application_term() {
- SkEvent::Term();
- SkGraphics::Term();
-}
-
diff --git a/experimental/Intersection/EdgeDemoApp-Info.plist b/experimental/Intersection/EdgeDemoApp-Info.plist
new file mode 100644
index 0000000000..8e102020bc
--- /dev/null
+++ b/experimental/Intersection/EdgeDemoApp-Info.plist
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+ <key>CFBundleDevelopmentRegion</key>
+ <string>English</string>
+ <key>CFBundleExecutable</key>
+ <string>${EXECUTABLE_NAME}</string>
+ <key>CFBundleIconFile</key>
+ <string></string>
+ <key>CFBundleIdentifier</key>
+ <string>com.googlecode.skia.${PRODUCT_NAME:rfc1034identifier}</string>
+ <key>CFBundleInfoDictionaryVersion</key>
+ <string>6.0</string>
+ <key>CFBundleName</key>
+ <string>${PRODUCT_NAME}</string>
+ <key>CFBundlePackageType</key>
+ <string>APPL</string>
+ <key>CFBundleShortVersionString</key>
+ <string>1.0</string>
+ <key>CFBundleSignature</key>
+ <string>????</string>
+ <key>CFBundleVersion</key>
+ <string>1</string>
+ <key>LSMinimumSystemVersion</key>
+ <string>${MACOSX_DEPLOYMENT_TARGET}</string>
+ <key>NSMainNibFile</key>
+ <string>EdgeDemoApp</string>
+ <key>NSPrincipalClass</key>
+ <string>NSApplication</string>
+</dict>
+</plist>
diff --git a/experimental/Intersection/EdgeDemoApp.mm b/experimental/Intersection/EdgeDemoApp.mm
new file mode 100644
index 0000000000..a8b233e424
--- /dev/null
+++ b/experimental/Intersection/EdgeDemoApp.mm
@@ -0,0 +1,116 @@
+#include "EdgeWalker_Test.h"
+#include "ShapeOps.h"
+#import "SkCanvas.h"
+#import "SkPaint.h"
+#import "SkWindow.h"
+#include "SkGraphics.h"
+#include "SkCGUtils.h"
+
+class SkSampleView : public SkView {
+public:
+ SkSampleView() {
+ this->setVisibleP(true);
+ this->setClipToBounds(false);
+ };
+protected:
+ virtual void onDraw(SkCanvas* canvas) {
+ // Three circles bounce inside a rectangle. The circles describe three, four
+ // or five points which in turn describe a polygon. The polygon points
+ // bounce inside the circles. The circles rotate and scale over time. The
+ // polygons are combined into a single path, simplified, and stroked.
+ static int step = 0;
+ const int circles = 3;
+ int scales[circles];
+ int angles[circles];
+ int locs[circles * 2];
+ int pts[circles * 2 * 4];
+ int c, p;
+ for (c = 0; c < circles; ++c) {
+ scales[c] = abs(10 - (step + c * 4) % 21);
+ angles[c] = (step + c * 6) % 600;
+ locs[c * 2] = abs(130 - (step + c * 9) % 261);
+ locs[c * 2 + 1] = abs(170 - (step + c * 11) % 341);
+ for (p = 0; p < 4; ++p) {
+ pts[c * 8 + p * 2] = abs(90 - ((step + c * 121 + p * 13) % 190));
+ pts[c * 8 + p * 2 + 1] = abs(110 - ((step + c * 223 + p * 17) % 230));
+ }
+ }
+ SkPath path, out;
+ for (c = 0; c < circles; ++c) {
+ for (p = 0; p < 4; ++p) {
+ SkScalar x = pts[c * 8 + p * 2];
+ SkScalar y = pts[c * 8 + p * 2 + 1];
+ x *= 3 + scales[c] / 10.0f;
+ y *= 3 + scales[c] / 10.0f;
+ SkScalar angle = angles[c] * 3.1415f * 2 / 600;
+ SkScalar temp = x * cos(angle) - y * sin(angle);
+ y = x * sin(angle) + y * cos(angle);
+ x = temp;
+ x += locs[c * 2] * 200 / 130.0f;
+ y += locs[c * 2 + 1] * 200 / 170.0f;
+ x += 50;
+ // y += 200;
+ if (p == 0) {
+ path.moveTo(x, y);
+ } else {
+ path.lineTo(x, y);
+ }
+ }
+ path.close();
+ }
+ showPath(path, "original:");
+ simplify(path, true, out);
+ showPath(out, "simplified:");
+ SkPaint paint;
+ paint.setAntiAlias(true);
+ paint.setStyle(SkPaint::kStroke_Style);
+ paint.setStrokeWidth(3);
+ paint.setColor(0x3F007fbF);
+ canvas->drawPath(path, paint);
+ paint.setColor(0xFF60FF00);
+ paint.setStrokeWidth(1);
+ canvas->drawColor(SK_ColorWHITE);
+ canvas->drawPath(out, paint);
+ ++step;
+ inval(NULL);
+ }
+private:
+ typedef SkView INHERITED;
+};
+
+void application_init() {
+ SkGraphics::Init();
+ SkEvent::Init();
+}
+
+void application_term() {
+ SkGraphics::Term();
+ SkEvent::Term();
+}
+
+class FillLayout : public SkView::Layout {
+protected:
+ virtual void onLayoutChildren(SkView* parent) {
+ SkView* view = SkView::F2BIter(parent).next();
+ view->setSize(parent->width(), parent->height());
+ }
+};
+
+#import "SimpleApp.h"
+@implementation SimpleNSView
+
+- (id)initWithDefaults {
+ if (self = [super initWithDefaults]) {
+ fWind = new SkOSWindow(self);
+ fWind->setLayout(new FillLayout, false);
+ fWind->attachChildToFront(new SkSampleView)->unref();
+ }
+ return self;
+}
+
+- (void)drawRect:(NSRect)dirtyRect {
+ CGContextRef ctx = (CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
+ SkCGDrawBitmap(ctx, fWind->getBitmap(), 0, 0);
+}
+
+@end
diff --git a/experimental/Intersection/EdgeDemoApp.xib b/experimental/Intersection/EdgeDemoApp.xib
new file mode 100644
index 0000000000..863ead1eaa
--- /dev/null
+++ b/experimental/Intersection/EdgeDemoApp.xib
@@ -0,0 +1,3115 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<archive type="com.apple.InterfaceBuilder3.Cocoa.XIB" version="7.10">
+ <data>
+ <int key="IBDocument.SystemTarget">1060</int>
+ <string key="IBDocument.SystemVersion">10K549</string>
+ <string key="IBDocument.InterfaceBuilderVersion">851</string>
+ <string key="IBDocument.AppKitVersion">1038.36</string>
+ <string key="IBDocument.HIToolboxVersion">461.00</string>
+ <object class="NSMutableDictionary" key="IBDocument.PluginVersions">
+ <string key="NS.key.0">com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string key="NS.object.0">851</string>
+ </object>
+ <object class="NSMutableArray" key="IBDocument.EditedObjectIDs">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <integer value="261"/>
+ </object>
+ <object class="NSArray" key="IBDocument.PluginDependencies">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ </object>
+ <object class="NSMutableDictionary" key="IBDocument.Metadata">
+ <string key="NS.key.0">PluginDependencyRecalculationVersion</string>
+ <integer value="1" key="NS.object.0"/>
+ </object>
+ <object class="NSMutableArray" key="IBDocument.RootObjects" id="110858478">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSCustomObject" id="762632889">
+ <string key="NSClassName">IBInspector</string>
+ </object>
+ <object class="NSCustomObject" id="932410077">
+ <string key="NSClassName">FirstResponder</string>
+ </object>
+ <object class="NSCustomObject" id="858592610">
+ <string key="NSClassName">NSApplication</string>
+ </object>
+ <object class="NSMenu" id="403715256">
+ <string key="NSTitle">AMainMenu</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="65739106">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">hello</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <object class="NSCustomResource" key="NSOnImage" id="573986354">
+ <string key="NSClassName">NSImage</string>
+ <string key="NSResourceName">NSMenuCheckmark</string>
+ </object>
+ <object class="NSCustomResource" key="NSMixedImage" id="622334842">
+ <string key="NSClassName">NSImage</string>
+ <string key="NSResourceName">NSMenuMixedState</string>
+ </object>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="964556876">
+ <string key="NSTitle">hello</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="627636549">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">About hello</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="938722355">
+ <reference key="NSMenu" ref="964556876"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="1026802975">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Preferences…</string>
+ <string key="NSKeyEquiv">,</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="200976220">
+ <reference key="NSMenu" ref="964556876"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="226934908">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Services</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="785419060">
+ <string key="NSTitle">Services</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ </object>
+ <string key="NSName">_NSServicesMenu</string>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="1031569584">
+ <reference key="NSMenu" ref="964556876"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="650251791">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Hide hello</string>
+ <string key="NSKeyEquiv">h</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="890704348">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Hide Others</string>
+ <string key="NSKeyEquiv">h</string>
+ <int key="NSKeyEquivModMask">1572864</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="373184661">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Show All</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="140060996">
+ <reference key="NSMenu" ref="964556876"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="674334250">
+ <reference key="NSMenu" ref="964556876"/>
+ <string key="NSTitle">Quit hello</string>
+ <string key="NSKeyEquiv">q</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ <string key="NSName">_NSAppleMenu</string>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="849503563">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">File</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="899147076">
+ <string key="NSTitle">File</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="940143719">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">New</string>
+ <string key="NSKeyEquiv">n</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="416202392">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Open…</string>
+ <string key="NSKeyEquiv">o</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="802841280">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Open Recent</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="250982885">
+ <string key="NSTitle">Open Recent</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="940066582">
+ <reference key="NSMenu" ref="250982885"/>
+ <string key="NSTitle">Clear Menu</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ <string key="NSName">_NSRecentDocumentsMenu</string>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="646964482">
+ <reference key="NSMenu" ref="899147076"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="113331390">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Close</string>
+ <string key="NSKeyEquiv">w</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="717042078">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Save</string>
+ <string key="NSKeyEquiv">s</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="259193863">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Save As…</string>
+ <string key="NSKeyEquiv">S</string>
+ <int key="NSKeyEquivModMask">1179648</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="523869872">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Revert to Saved</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="425999990">
+ <reference key="NSMenu" ref="899147076"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="917170545">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Page Setup...</string>
+ <string key="NSKeyEquiv">P</string>
+ <int key="NSKeyEquivModMask">1179648</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSToolTip"/>
+ </object>
+ <object class="NSMenuItem" id="600825955">
+ <reference key="NSMenu" ref="899147076"/>
+ <string key="NSTitle">Print…</string>
+ <string key="NSKeyEquiv">p</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="825040645">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">Edit</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="411995980">
+ <string key="NSTitle">Edit</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="155877797">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Undo</string>
+ <string key="NSKeyEquiv">z</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="278282207">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Redo</string>
+ <string key="NSKeyEquiv">Z</string>
+ <int key="NSKeyEquivModMask">1179648</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="287041942">
+ <reference key="NSMenu" ref="411995980"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="761075222">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Cut</string>
+ <string key="NSKeyEquiv">x</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="617541932">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Copy</string>
+ <string key="NSKeyEquiv">c</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="404580975">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Paste</string>
+ <string key="NSKeyEquiv">v</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="890043556">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Paste and Match Style</string>
+ <string key="NSKeyEquiv">V</string>
+ <int key="NSKeyEquivModMask">1572864</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="572775670">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Delete</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="826813329">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Select All</string>
+ <string key="NSKeyEquiv">a</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="393301673">
+ <reference key="NSMenu" ref="411995980"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="726470551">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Find</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="759421779">
+ <string key="NSTitle">Find</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="871728498">
+ <reference key="NSMenu" ref="759421779"/>
+ <string key="NSTitle">Find…</string>
+ <string key="NSKeyEquiv">f</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">1</int>
+ </object>
+ <object class="NSMenuItem" id="392793967">
+ <reference key="NSMenu" ref="759421779"/>
+ <string key="NSTitle">Find Next</string>
+ <string key="NSKeyEquiv">g</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">2</int>
+ </object>
+ <object class="NSMenuItem" id="209754492">
+ <reference key="NSMenu" ref="759421779"/>
+ <string key="NSTitle">Find Previous</string>
+ <string key="NSKeyEquiv">G</string>
+ <int key="NSKeyEquivModMask">1179648</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">3</int>
+ </object>
+ <object class="NSMenuItem" id="300840686">
+ <reference key="NSMenu" ref="759421779"/>
+ <string key="NSTitle">Use Selection for Find</string>
+ <string key="NSKeyEquiv">e</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">7</int>
+ </object>
+ <object class="NSMenuItem" id="339241627">
+ <reference key="NSMenu" ref="759421779"/>
+ <string key="NSTitle">Jump to Selection</string>
+ <string key="NSKeyEquiv">j</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="394001634">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Spelling and Grammar</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="48019006">
+ <string key="NSTitle">Spelling and Grammar</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="641875902">
+ <reference key="NSMenu" ref="48019006"/>
+ <string key="NSTitle">Show Spelling and Grammar</string>
+ <string key="NSKeyEquiv">:</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="519234687">
+ <reference key="NSMenu" ref="48019006"/>
+ <string key="NSTitle">Check Document Now</string>
+ <string key="NSKeyEquiv">;</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="566175535">
+ <reference key="NSMenu" ref="48019006"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="32560783">
+ <reference key="NSMenu" ref="48019006"/>
+ <string key="NSTitle">Check Spelling While Typing</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="74735022">
+ <reference key="NSMenu" ref="48019006"/>
+ <string key="NSTitle">Check Grammar With Spelling</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="440900682">
+ <reference key="NSMenu" ref="48019006"/>
+ <string key="NSTitle">Correct Spelling Automatically</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="723250450">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Substitutions</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="60916223">
+ <string key="NSTitle">Substitutions</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="499113305">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Show Substitutions</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="604095584">
+ <reference key="NSMenu" ref="60916223"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="1037848121">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Smart Copy/Paste</string>
+ <string key="NSKeyEquiv">f</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">1</int>
+ </object>
+ <object class="NSMenuItem" id="253602211">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Smart Quotes</string>
+ <string key="NSKeyEquiv">g</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">2</int>
+ </object>
+ <object class="NSMenuItem" id="870101879">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Smart Dashes</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="818701236">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Smart Links</string>
+ <string key="NSKeyEquiv">G</string>
+ <int key="NSKeyEquivModMask">1179648</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">3</int>
+ </object>
+ <object class="NSMenuItem" id="682811574">
+ <reference key="NSMenu" ref="60916223"/>
+ <string key="NSTitle">Text Replacement</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="1022343180">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Transformations</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="799869067">
+ <string key="NSTitle">Transformations</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="242386505">
+ <reference key="NSMenu" ref="799869067"/>
+ <string key="NSTitle">Make Upper Case</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="980071763">
+ <reference key="NSMenu" ref="799869067"/>
+ <string key="NSTitle">Make Lower Case</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="138959048">
+ <reference key="NSMenu" ref="799869067"/>
+ <string key="NSTitle">Capitalize</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="538735815">
+ <reference key="NSMenu" ref="411995980"/>
+ <string key="NSTitle">Speech</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="92848229">
+ <string key="NSTitle">Speech</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="242466330">
+ <reference key="NSMenu" ref="92848229"/>
+ <string key="NSTitle">Start Speaking</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="892418348">
+ <reference key="NSMenu" ref="92848229"/>
+ <string key="NSTitle">Stop Speaking</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="126299768">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">Format</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="473359030">
+ <string key="NSTitle">Format</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="543679380">
+ <reference key="NSMenu" ref="473359030"/>
+ <string key="NSTitle">Font</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="420125509">
+ <string key="NSTitle">Font</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="1066858">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Show Fonts</string>
+ <string key="NSKeyEquiv">t</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="890909023">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Bold</string>
+ <string key="NSKeyEquiv">b</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">2</int>
+ </object>
+ <object class="NSMenuItem" id="460689417">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Italic</string>
+ <string key="NSKeyEquiv">i</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">1</int>
+ </object>
+ <object class="NSMenuItem" id="648810690">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Underline</string>
+ <string key="NSKeyEquiv">u</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="648523518">
+ <reference key="NSMenu" ref="420125509"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="554361477">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Bigger</string>
+ <string key="NSKeyEquiv">+</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">3</int>
+ </object>
+ <object class="NSMenuItem" id="509852642">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Smaller</string>
+ <string key="NSKeyEquiv">-</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <int key="NSTag">4</int>
+ </object>
+ <object class="NSMenuItem" id="684419220">
+ <reference key="NSMenu" ref="420125509"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="300760265">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Kern</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="692426030">
+ <string key="NSTitle">Kern</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="827985012">
+ <reference key="NSMenu" ref="692426030"/>
+ <string key="NSTitle">Use Default</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="114397248">
+ <reference key="NSMenu" ref="692426030"/>
+ <string key="NSTitle">Use None</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="464129683">
+ <reference key="NSMenu" ref="692426030"/>
+ <string key="NSTitle">Tighten</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="984558289">
+ <reference key="NSMenu" ref="692426030"/>
+ <string key="NSTitle">Loosen</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="764895229">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Ligature</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="1027046122">
+ <string key="NSTitle">Ligature</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="170445579">
+ <reference key="NSMenu" ref="1027046122"/>
+ <string key="NSTitle">Use Default</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="1054539967">
+ <reference key="NSMenu" ref="1027046122"/>
+ <string key="NSTitle">Use None</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="193227140">
+ <reference key="NSMenu" ref="1027046122"/>
+ <string key="NSTitle">Use All</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="185308913">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Baseline</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="412235399">
+ <string key="NSTitle">Baseline</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="708934364">
+ <reference key="NSMenu" ref="412235399"/>
+ <string key="NSTitle">Use Default</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="660376852">
+ <reference key="NSMenu" ref="412235399"/>
+ <string key="NSTitle">Superscript</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="887484660">
+ <reference key="NSMenu" ref="412235399"/>
+ <string key="NSTitle">Subscript</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="239990007">
+ <reference key="NSMenu" ref="412235399"/>
+ <string key="NSTitle">Raise</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="794052095">
+ <reference key="NSMenu" ref="412235399"/>
+ <string key="NSTitle">Lower</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="770408504">
+ <reference key="NSMenu" ref="420125509"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="968537172">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Show Colors</string>
+ <string key="NSKeyEquiv">C</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="576239163">
+ <reference key="NSMenu" ref="420125509"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="951733979">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Copy Style</string>
+ <string key="NSKeyEquiv">c</string>
+ <int key="NSKeyEquivModMask">1572864</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="726071842">
+ <reference key="NSMenu" ref="420125509"/>
+ <string key="NSTitle">Paste Style</string>
+ <string key="NSKeyEquiv">v</string>
+ <int key="NSKeyEquivModMask">1572864</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ <string key="NSName">_NSFontMenu</string>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="432500292">
+ <reference key="NSMenu" ref="473359030"/>
+ <string key="NSTitle">Text</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="239792765">
+ <string key="NSTitle">Text</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="209955373">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Align Left</string>
+ <string key="NSKeyEquiv">{</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="940415998">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Center</string>
+ <string key="NSKeyEquiv">|</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="667530981">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Justify</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="518803967">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Align Right</string>
+ <string key="NSKeyEquiv">}</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="755110083">
+ <reference key="NSMenu" ref="239792765"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="970864302">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Writing Direction</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="394707630">
+ <string key="NSTitle">Writing Direction</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="295941739">
+ <reference key="NSMenu" ref="394707630"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <string key="NSTitle">Paragraph</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="1016781112">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CURlZmF1bHQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="909594320">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CUxlZnQgdG8gUmlnaHQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="294875881">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CVJpZ2h0IHRvIExlZnQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="125873089">
+ <reference key="NSMenu" ref="394707630"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="448907901">
+ <reference key="NSMenu" ref="394707630"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <string key="NSTitle">Selection</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="719807015">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CURlZmF1bHQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="551093393">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CUxlZnQgdG8gUmlnaHQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="968290247">
+ <reference key="NSMenu" ref="394707630"/>
+ <string type="base64-UTF8" key="NSTitle">CVJpZ2h0IHRvIExlZnQ</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="624010617">
+ <reference key="NSMenu" ref="239792765"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="178871919">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Show Ruler</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="19133321">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Copy Ruler</string>
+ <string key="NSKeyEquiv">c</string>
+ <int key="NSKeyEquivModMask">1310720</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="971682598">
+ <reference key="NSMenu" ref="239792765"/>
+ <string key="NSTitle">Paste Ruler</string>
+ <string key="NSKeyEquiv">v</string>
+ <int key="NSKeyEquivModMask">1310720</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="474036278">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">View</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="1011573215">
+ <string key="NSTitle">View</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="84198938">
+ <reference key="NSMenu" ref="1011573215"/>
+ <string key="NSTitle">Show Toolbar</string>
+ <string key="NSKeyEquiv">t</string>
+ <int key="NSKeyEquivModMask">1572864</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="468947355">
+ <reference key="NSMenu" ref="1011573215"/>
+ <string key="NSTitle">Customize Toolbar…</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="179474997">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">Window</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="722436082">
+ <string key="NSTitle">Window</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="715853698">
+ <reference key="NSMenu" ref="722436082"/>
+ <string key="NSTitle">Minimize</string>
+ <string key="NSKeyEquiv">m</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="639724461">
+ <reference key="NSMenu" ref="722436082"/>
+ <string key="NSTitle">Zoom</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="541256952">
+ <reference key="NSMenu" ref="722436082"/>
+ <bool key="NSIsDisabled">YES</bool>
+ <bool key="NSIsSeparator">YES</bool>
+ <string key="NSTitle"/>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ <object class="NSMenuItem" id="801808839">
+ <reference key="NSMenu" ref="722436082"/>
+ <string key="NSTitle">Bring All to Front</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ <string key="NSName">_NSWindowsMenu</string>
+ </object>
+ </object>
+ <object class="NSMenuItem" id="964815204">
+ <reference key="NSMenu" ref="403715256"/>
+ <string key="NSTitle">Help</string>
+ <string key="NSKeyEquiv"/>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ <string key="NSAction">submenuAction:</string>
+ <object class="NSMenu" key="NSSubmenu" id="445400279">
+ <string key="NSTitle">Help</string>
+ <object class="NSMutableArray" key="NSMenuItems">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSMenuItem" id="820408786">
+ <reference key="NSMenu" ref="445400279"/>
+ <string key="NSTitle">hello Help</string>
+ <string key="NSKeyEquiv">?</string>
+ <int key="NSKeyEquivModMask">1048576</int>
+ <int key="NSMnemonicLoc">2147483647</int>
+ <reference key="NSOnImage" ref="573986354"/>
+ <reference key="NSMixedImage" ref="622334842"/>
+ </object>
+ </object>
+ <string key="NSName">_NSHelpMenu</string>
+ </object>
+ </object>
+ </object>
+ <string key="NSName">_NSMainMenu</string>
+ </object>
+ <object class="NSWindowTemplate" id="407166972">
+ <int key="NSWindowStyleMask">15</int>
+ <int key="NSWindowBacking">2</int>
+ <string key="NSWindowRect">{{335, 289}, {640, 461}}</string>
+ <int key="NSWTFlags">1954021376</int>
+ <string key="NSWindowTitle">hello</string>
+ <string key="NSWindowClass">NSWindow</string>
+ <nil key="NSViewClass"/>
+ <string key="NSWindowContentMaxSize">{1.79769e+308, 1.79769e+308}</string>
+ <object class="NSView" key="NSWindowView" id="813288216">
+ <reference key="NSNextResponder"/>
+ <int key="NSvFlags">256</int>
+ <object class="NSMutableArray" key="NSSubviews">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSCustomView" id="410337987">
+ <reference key="NSNextResponder" ref="813288216"/>
+ <int key="NSvFlags">286</int>
+ <string key="NSFrameSize">{640, 480}</string>
+ <reference key="NSSuperview" ref="813288216"/>
+ <string key="NSClassName">SimpleNSView</string>
+ </object>
+ </object>
+ <string key="NSFrameSize">{640, 461}</string>
+ <reference key="NSSuperview"/>
+ </object>
+ <string key="NSScreenRect">{{0, 0}, {1600, 2538}}</string>
+ <string key="NSMaxSize">{1.79769e+308, 1.79769e+308}</string>
+ </object>
+ </object>
+ <object class="IBObjectContainer" key="IBDocument.Objects">
+ <object class="NSMutableArray" key="connectionRecords">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ </object>
+ <object class="IBMutableOrderedSet" key="objectRecords">
+ <object class="NSArray" key="orderedObjects">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="IBObjectRecord">
+ <int key="objectID">0</int>
+ <object class="NSArray" key="object" id="485438096">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ </object>
+ <reference key="children" ref="110858478"/>
+ <nil key="parent"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">-2</int>
+ <reference key="object" ref="762632889"/>
+ <reference key="parent" ref="485438096"/>
+ <string key="objectName">File's Owner</string>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">-1</int>
+ <reference key="object" ref="932410077"/>
+ <reference key="parent" ref="485438096"/>
+ <string key="objectName">First Responder</string>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">-3</int>
+ <reference key="object" ref="858592610"/>
+ <reference key="parent" ref="485438096"/>
+ <string key="objectName">Application</string>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">114</int>
+ <reference key="object" ref="403715256"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="964815204"/>
+ <reference ref="126299768"/>
+ <reference ref="474036278"/>
+ <reference ref="849503563"/>
+ <reference ref="825040645"/>
+ <reference ref="65739106"/>
+ <reference ref="179474997"/>
+ </object>
+ <reference key="parent" ref="485438096"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">115</int>
+ <reference key="object" ref="964815204"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="445400279"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">116</int>
+ <reference key="object" ref="126299768"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="473359030"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">117</int>
+ <reference key="object" ref="474036278"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="1011573215"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">118</int>
+ <reference key="object" ref="849503563"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="899147076"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">119</int>
+ <reference key="object" ref="825040645"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="411995980"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">120</int>
+ <reference key="object" ref="65739106"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="964556876"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">121</int>
+ <reference key="object" ref="179474997"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="722436082"/>
+ </object>
+ <reference key="parent" ref="403715256"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">122</int>
+ <reference key="object" ref="722436082"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="715853698"/>
+ <reference ref="639724461"/>
+ <reference ref="801808839"/>
+ <reference ref="541256952"/>
+ </object>
+ <reference key="parent" ref="179474997"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">123</int>
+ <reference key="object" ref="715853698"/>
+ <reference key="parent" ref="722436082"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">124</int>
+ <reference key="object" ref="639724461"/>
+ <reference key="parent" ref="722436082"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">125</int>
+ <reference key="object" ref="801808839"/>
+ <reference key="parent" ref="722436082"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">126</int>
+ <reference key="object" ref="541256952"/>
+ <reference key="parent" ref="722436082"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">127</int>
+ <reference key="object" ref="964556876"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="890704348"/>
+ <reference ref="140060996"/>
+ <reference ref="226934908"/>
+ <reference ref="938722355"/>
+ <reference ref="200976220"/>
+ <reference ref="1026802975"/>
+ <reference ref="1031569584"/>
+ <reference ref="674334250"/>
+ <reference ref="373184661"/>
+ <reference ref="650251791"/>
+ <reference ref="627636549"/>
+ </object>
+ <reference key="parent" ref="65739106"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">128</int>
+ <reference key="object" ref="890704348"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">129</int>
+ <reference key="object" ref="140060996"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">130</int>
+ <reference key="object" ref="226934908"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="785419060"/>
+ </object>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">131</int>
+ <reference key="object" ref="938722355"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">132</int>
+ <reference key="object" ref="200976220"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">133</int>
+ <reference key="object" ref="1026802975"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">134</int>
+ <reference key="object" ref="1031569584"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">135</int>
+ <reference key="object" ref="674334250"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">136</int>
+ <reference key="object" ref="373184661"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">137</int>
+ <reference key="object" ref="650251791"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">138</int>
+ <reference key="object" ref="627636549"/>
+ <reference key="parent" ref="964556876"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">139</int>
+ <reference key="object" ref="785419060"/>
+ <reference key="parent" ref="226934908"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">140</int>
+ <reference key="object" ref="411995980"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="890043556"/>
+ <reference ref="1022343180"/>
+ <reference ref="723250450"/>
+ <reference ref="538735815"/>
+ <reference ref="394001634"/>
+ <reference ref="726470551"/>
+ <reference ref="278282207"/>
+ <reference ref="287041942"/>
+ <reference ref="617541932"/>
+ <reference ref="404580975"/>
+ <reference ref="761075222"/>
+ <reference ref="393301673"/>
+ <reference ref="155877797"/>
+ <reference ref="826813329"/>
+ <reference ref="572775670"/>
+ </object>
+ <reference key="parent" ref="825040645"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">141</int>
+ <reference key="object" ref="890043556"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">142</int>
+ <reference key="object" ref="1022343180"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="799869067"/>
+ </object>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">143</int>
+ <reference key="object" ref="723250450"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="60916223"/>
+ </object>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">144</int>
+ <reference key="object" ref="538735815"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="92848229"/>
+ </object>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">145</int>
+ <reference key="object" ref="394001634"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="48019006"/>
+ </object>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">146</int>
+ <reference key="object" ref="726470551"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="759421779"/>
+ </object>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">147</int>
+ <reference key="object" ref="278282207"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">148</int>
+ <reference key="object" ref="287041942"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">149</int>
+ <reference key="object" ref="617541932"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">150</int>
+ <reference key="object" ref="404580975"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">151</int>
+ <reference key="object" ref="761075222"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">152</int>
+ <reference key="object" ref="393301673"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">153</int>
+ <reference key="object" ref="155877797"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">154</int>
+ <reference key="object" ref="826813329"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">155</int>
+ <reference key="object" ref="572775670"/>
+ <reference key="parent" ref="411995980"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">156</int>
+ <reference key="object" ref="759421779"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="871728498"/>
+ <reference ref="392793967"/>
+ <reference ref="300840686"/>
+ <reference ref="339241627"/>
+ <reference ref="209754492"/>
+ </object>
+ <reference key="parent" ref="726470551"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">157</int>
+ <reference key="object" ref="871728498"/>
+ <reference key="parent" ref="759421779"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">158</int>
+ <reference key="object" ref="392793967"/>
+ <reference key="parent" ref="759421779"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">159</int>
+ <reference key="object" ref="300840686"/>
+ <reference key="parent" ref="759421779"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">160</int>
+ <reference key="object" ref="339241627"/>
+ <reference key="parent" ref="759421779"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">161</int>
+ <reference key="object" ref="209754492"/>
+ <reference key="parent" ref="759421779"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">162</int>
+ <reference key="object" ref="48019006"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="440900682"/>
+ <reference ref="566175535"/>
+ <reference ref="74735022"/>
+ <reference ref="641875902"/>
+ <reference ref="519234687"/>
+ <reference ref="32560783"/>
+ </object>
+ <reference key="parent" ref="394001634"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">163</int>
+ <reference key="object" ref="440900682"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">164</int>
+ <reference key="object" ref="566175535"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">165</int>
+ <reference key="object" ref="74735022"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">166</int>
+ <reference key="object" ref="641875902"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">167</int>
+ <reference key="object" ref="519234687"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">168</int>
+ <reference key="object" ref="32560783"/>
+ <reference key="parent" ref="48019006"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">169</int>
+ <reference key="object" ref="92848229"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="242466330"/>
+ <reference ref="892418348"/>
+ </object>
+ <reference key="parent" ref="538735815"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">170</int>
+ <reference key="object" ref="242466330"/>
+ <reference key="parent" ref="92848229"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">171</int>
+ <reference key="object" ref="892418348"/>
+ <reference key="parent" ref="92848229"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">172</int>
+ <reference key="object" ref="60916223"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="682811574"/>
+ <reference ref="870101879"/>
+ <reference ref="604095584"/>
+ <reference ref="499113305"/>
+ <reference ref="818701236"/>
+ <reference ref="253602211"/>
+ <reference ref="1037848121"/>
+ </object>
+ <reference key="parent" ref="723250450"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">173</int>
+ <reference key="object" ref="682811574"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">174</int>
+ <reference key="object" ref="870101879"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">175</int>
+ <reference key="object" ref="604095584"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">176</int>
+ <reference key="object" ref="499113305"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">177</int>
+ <reference key="object" ref="818701236"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">178</int>
+ <reference key="object" ref="253602211"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">179</int>
+ <reference key="object" ref="1037848121"/>
+ <reference key="parent" ref="60916223"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">180</int>
+ <reference key="object" ref="799869067"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="138959048"/>
+ <reference ref="980071763"/>
+ <reference ref="242386505"/>
+ </object>
+ <reference key="parent" ref="1022343180"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">181</int>
+ <reference key="object" ref="138959048"/>
+ <reference key="parent" ref="799869067"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">182</int>
+ <reference key="object" ref="980071763"/>
+ <reference key="parent" ref="799869067"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">183</int>
+ <reference key="object" ref="242386505"/>
+ <reference key="parent" ref="799869067"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">184</int>
+ <reference key="object" ref="899147076"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="425999990"/>
+ <reference ref="523869872"/>
+ <reference ref="646964482"/>
+ <reference ref="113331390"/>
+ <reference ref="917170545"/>
+ <reference ref="802841280"/>
+ <reference ref="940143719"/>
+ <reference ref="416202392"/>
+ <reference ref="600825955"/>
+ <reference ref="259193863"/>
+ <reference ref="717042078"/>
+ </object>
+ <reference key="parent" ref="849503563"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">185</int>
+ <reference key="object" ref="425999990"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">186</int>
+ <reference key="object" ref="523869872"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">187</int>
+ <reference key="object" ref="646964482"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">188</int>
+ <reference key="object" ref="113331390"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">189</int>
+ <reference key="object" ref="917170545"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">190</int>
+ <reference key="object" ref="802841280"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="250982885"/>
+ </object>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">191</int>
+ <reference key="object" ref="940143719"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">192</int>
+ <reference key="object" ref="416202392"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">193</int>
+ <reference key="object" ref="600825955"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">194</int>
+ <reference key="object" ref="259193863"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">195</int>
+ <reference key="object" ref="717042078"/>
+ <reference key="parent" ref="899147076"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">196</int>
+ <reference key="object" ref="250982885"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="940066582"/>
+ </object>
+ <reference key="parent" ref="802841280"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">197</int>
+ <reference key="object" ref="940066582"/>
+ <reference key="parent" ref="250982885"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">198</int>
+ <reference key="object" ref="1011573215"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="468947355"/>
+ <reference ref="84198938"/>
+ </object>
+ <reference key="parent" ref="474036278"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">199</int>
+ <reference key="object" ref="468947355"/>
+ <reference key="parent" ref="1011573215"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">200</int>
+ <reference key="object" ref="84198938"/>
+ <reference key="parent" ref="1011573215"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">201</int>
+ <reference key="object" ref="473359030"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="432500292"/>
+ <reference ref="543679380"/>
+ </object>
+ <reference key="parent" ref="126299768"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">202</int>
+ <reference key="object" ref="432500292"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="239792765"/>
+ </object>
+ <reference key="parent" ref="473359030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">203</int>
+ <reference key="object" ref="543679380"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="420125509"/>
+ </object>
+ <reference key="parent" ref="473359030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">204</int>
+ <reference key="object" ref="420125509"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="726071842"/>
+ <reference ref="951733979"/>
+ <reference ref="576239163"/>
+ <reference ref="968537172"/>
+ <reference ref="770408504"/>
+ <reference ref="185308913"/>
+ <reference ref="764895229"/>
+ <reference ref="300760265"/>
+ <reference ref="684419220"/>
+ <reference ref="509852642"/>
+ <reference ref="554361477"/>
+ <reference ref="648523518"/>
+ <reference ref="648810690"/>
+ <reference ref="460689417"/>
+ <reference ref="890909023"/>
+ <reference ref="1066858"/>
+ </object>
+ <reference key="parent" ref="543679380"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">205</int>
+ <reference key="object" ref="726071842"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">206</int>
+ <reference key="object" ref="951733979"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">207</int>
+ <reference key="object" ref="576239163"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">208</int>
+ <reference key="object" ref="968537172"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">209</int>
+ <reference key="object" ref="770408504"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">210</int>
+ <reference key="object" ref="185308913"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="412235399"/>
+ </object>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">211</int>
+ <reference key="object" ref="764895229"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="1027046122"/>
+ </object>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">212</int>
+ <reference key="object" ref="300760265"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="692426030"/>
+ </object>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">213</int>
+ <reference key="object" ref="684419220"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">214</int>
+ <reference key="object" ref="509852642"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">215</int>
+ <reference key="object" ref="554361477"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">216</int>
+ <reference key="object" ref="648523518"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">217</int>
+ <reference key="object" ref="648810690"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">218</int>
+ <reference key="object" ref="460689417"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">219</int>
+ <reference key="object" ref="890909023"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">220</int>
+ <reference key="object" ref="1066858"/>
+ <reference key="parent" ref="420125509"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">221</int>
+ <reference key="object" ref="692426030"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="984558289"/>
+ <reference ref="464129683"/>
+ <reference ref="114397248"/>
+ <reference ref="827985012"/>
+ </object>
+ <reference key="parent" ref="300760265"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">222</int>
+ <reference key="object" ref="984558289"/>
+ <reference key="parent" ref="692426030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">223</int>
+ <reference key="object" ref="464129683"/>
+ <reference key="parent" ref="692426030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">224</int>
+ <reference key="object" ref="114397248"/>
+ <reference key="parent" ref="692426030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">225</int>
+ <reference key="object" ref="827985012"/>
+ <reference key="parent" ref="692426030"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">226</int>
+ <reference key="object" ref="1027046122"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="193227140"/>
+ <reference ref="1054539967"/>
+ <reference ref="170445579"/>
+ </object>
+ <reference key="parent" ref="764895229"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">227</int>
+ <reference key="object" ref="193227140"/>
+ <reference key="parent" ref="1027046122"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">228</int>
+ <reference key="object" ref="1054539967"/>
+ <reference key="parent" ref="1027046122"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">229</int>
+ <reference key="object" ref="170445579"/>
+ <reference key="parent" ref="1027046122"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">230</int>
+ <reference key="object" ref="412235399"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="794052095"/>
+ <reference ref="239990007"/>
+ <reference ref="887484660"/>
+ <reference ref="660376852"/>
+ <reference ref="708934364"/>
+ </object>
+ <reference key="parent" ref="185308913"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">231</int>
+ <reference key="object" ref="794052095"/>
+ <reference key="parent" ref="412235399"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">232</int>
+ <reference key="object" ref="239990007"/>
+ <reference key="parent" ref="412235399"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">233</int>
+ <reference key="object" ref="887484660"/>
+ <reference key="parent" ref="412235399"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">234</int>
+ <reference key="object" ref="660376852"/>
+ <reference key="parent" ref="412235399"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">235</int>
+ <reference key="object" ref="708934364"/>
+ <reference key="parent" ref="412235399"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">236</int>
+ <reference key="object" ref="239792765"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="971682598"/>
+ <reference ref="19133321"/>
+ <reference ref="178871919"/>
+ <reference ref="624010617"/>
+ <reference ref="970864302"/>
+ <reference ref="755110083"/>
+ <reference ref="518803967"/>
+ <reference ref="667530981"/>
+ <reference ref="940415998"/>
+ <reference ref="209955373"/>
+ </object>
+ <reference key="parent" ref="432500292"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">237</int>
+ <reference key="object" ref="971682598"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">238</int>
+ <reference key="object" ref="19133321"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">239</int>
+ <reference key="object" ref="178871919"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">240</int>
+ <reference key="object" ref="624010617"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">241</int>
+ <reference key="object" ref="970864302"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="394707630"/>
+ </object>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">242</int>
+ <reference key="object" ref="755110083"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">243</int>
+ <reference key="object" ref="518803967"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">244</int>
+ <reference key="object" ref="667530981"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">245</int>
+ <reference key="object" ref="940415998"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">246</int>
+ <reference key="object" ref="209955373"/>
+ <reference key="parent" ref="239792765"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">247</int>
+ <reference key="object" ref="394707630"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="968290247"/>
+ <reference ref="551093393"/>
+ <reference ref="719807015"/>
+ <reference ref="448907901"/>
+ <reference ref="125873089"/>
+ <reference ref="294875881"/>
+ <reference ref="909594320"/>
+ <reference ref="1016781112"/>
+ <reference ref="295941739"/>
+ </object>
+ <reference key="parent" ref="970864302"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">248</int>
+ <reference key="object" ref="968290247"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">249</int>
+ <reference key="object" ref="551093393"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">250</int>
+ <reference key="object" ref="719807015"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">251</int>
+ <reference key="object" ref="448907901"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">252</int>
+ <reference key="object" ref="125873089"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">253</int>
+ <reference key="object" ref="294875881"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">254</int>
+ <reference key="object" ref="909594320"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">255</int>
+ <reference key="object" ref="1016781112"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">256</int>
+ <reference key="object" ref="295941739"/>
+ <reference key="parent" ref="394707630"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">257</int>
+ <reference key="object" ref="445400279"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="820408786"/>
+ </object>
+ <reference key="parent" ref="964815204"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">258</int>
+ <reference key="object" ref="820408786"/>
+ <reference key="parent" ref="445400279"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">259</int>
+ <reference key="object" ref="407166972"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="813288216"/>
+ </object>
+ <reference key="parent" ref="485438096"/>
+ <string key="objectName">Window (SimpleApp)</string>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">260</int>
+ <reference key="object" ref="813288216"/>
+ <object class="NSMutableArray" key="children">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference ref="410337987"/>
+ </object>
+ <reference key="parent" ref="407166972"/>
+ </object>
+ <object class="IBObjectRecord">
+ <int key="objectID">261</int>
+ <reference key="object" ref="410337987"/>
+ <reference key="parent" ref="813288216"/>
+ </object>
+ </object>
+ </object>
+ <object class="NSMutableDictionary" key="flattenedProperties">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSArray" key="dict.sortedKeys">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <string>-3.IBPluginDependency</string>
+ <string>-3.ImportedFromIB2</string>
+ <string>114.IBEditorWindowLastContentRect</string>
+ <string>114.IBPluginDependency</string>
+ <string>114.ImportedFromIB2</string>
+ <string>114.WindowOrigin</string>
+ <string>114.editorWindowContentRectSynchronizationRect</string>
+ <string>115.IBPluginDependency</string>
+ <string>116.IBPluginDependency</string>
+ <string>117.IBPluginDependency</string>
+ <string>118.IBPluginDependency</string>
+ <string>118.ImportedFromIB2</string>
+ <string>119.IBPluginDependency</string>
+ <string>119.ImportedFromIB2</string>
+ <string>120.IBPluginDependency</string>
+ <string>120.ImportedFromIB2</string>
+ <string>121.IBPluginDependency</string>
+ <string>121.ImportedFromIB2</string>
+ <string>122.IBEditorWindowLastContentRect</string>
+ <string>122.IBPluginDependency</string>
+ <string>122.ImportedFromIB2</string>
+ <string>122.editorWindowContentRectSynchronizationRect</string>
+ <string>123.IBPluginDependency</string>
+ <string>123.ImportedFromIB2</string>
+ <string>124.IBPluginDependency</string>
+ <string>124.ImportedFromIB2</string>
+ <string>125.IBPluginDependency</string>
+ <string>125.ImportedFromIB2</string>
+ <string>126.IBPluginDependency</string>
+ <string>126.ImportedFromIB2</string>
+ <string>127.IBEditorWindowLastContentRect</string>
+ <string>127.IBPluginDependency</string>
+ <string>127.ImportedFromIB2</string>
+ <string>127.editorWindowContentRectSynchronizationRect</string>
+ <string>128.IBPluginDependency</string>
+ <string>128.ImportedFromIB2</string>
+ <string>129.IBPluginDependency</string>
+ <string>129.ImportedFromIB2</string>
+ <string>130.IBPluginDependency</string>
+ <string>130.ImportedFromIB2</string>
+ <string>131.IBPluginDependency</string>
+ <string>131.ImportedFromIB2</string>
+ <string>132.IBPluginDependency</string>
+ <string>132.ImportedFromIB2</string>
+ <string>133.IBPluginDependency</string>
+ <string>133.ImportedFromIB2</string>
+ <string>134.IBPluginDependency</string>
+ <string>134.ImportedFromIB2</string>
+ <string>135.IBPluginDependency</string>
+ <string>135.ImportedFromIB2</string>
+ <string>136.IBPluginDependency</string>
+ <string>136.ImportedFromIB2</string>
+ <string>137.IBPluginDependency</string>
+ <string>137.ImportedFromIB2</string>
+ <string>138.IBPluginDependency</string>
+ <string>138.ImportedFromIB2</string>
+ <string>139.IBPluginDependency</string>
+ <string>139.ImportedFromIB2</string>
+ <string>139.editorWindowContentRectSynchronizationRect</string>
+ <string>140.IBEditorWindowLastContentRect</string>
+ <string>140.IBPluginDependency</string>
+ <string>140.ImportedFromIB2</string>
+ <string>140.editorWindowContentRectSynchronizationRect</string>
+ <string>141.IBPluginDependency</string>
+ <string>142.IBPluginDependency</string>
+ <string>143.IBPluginDependency</string>
+ <string>143.ImportedFromIB2</string>
+ <string>144.IBPluginDependency</string>
+ <string>144.ImportedFromIB2</string>
+ <string>145.IBPluginDependency</string>
+ <string>145.ImportedFromIB2</string>
+ <string>146.IBPluginDependency</string>
+ <string>146.ImportedFromIB2</string>
+ <string>147.IBPluginDependency</string>
+ <string>147.ImportedFromIB2</string>
+ <string>148.IBPluginDependency</string>
+ <string>148.ImportedFromIB2</string>
+ <string>149.IBPluginDependency</string>
+ <string>149.ImportedFromIB2</string>
+ <string>150.IBPluginDependency</string>
+ <string>150.ImportedFromIB2</string>
+ <string>151.IBPluginDependency</string>
+ <string>151.ImportedFromIB2</string>
+ <string>152.IBPluginDependency</string>
+ <string>152.ImportedFromIB2</string>
+ <string>153.IBPluginDependency</string>
+ <string>153.ImportedFromIB2</string>
+ <string>154.IBPluginDependency</string>
+ <string>154.ImportedFromIB2</string>
+ <string>155.IBPluginDependency</string>
+ <string>155.ImportedFromIB2</string>
+ <string>156.IBEditorWindowLastContentRect</string>
+ <string>156.IBPluginDependency</string>
+ <string>156.ImportedFromIB2</string>
+ <string>156.editorWindowContentRectSynchronizationRect</string>
+ <string>157.IBPluginDependency</string>
+ <string>157.ImportedFromIB2</string>
+ <string>158.IBPluginDependency</string>
+ <string>158.ImportedFromIB2</string>
+ <string>159.IBPluginDependency</string>
+ <string>159.ImportedFromIB2</string>
+ <string>160.IBPluginDependency</string>
+ <string>160.ImportedFromIB2</string>
+ <string>161.IBPluginDependency</string>
+ <string>161.ImportedFromIB2</string>
+ <string>162.IBEditorWindowLastContentRect</string>
+ <string>162.IBPluginDependency</string>
+ <string>162.ImportedFromIB2</string>
+ <string>162.editorWindowContentRectSynchronizationRect</string>
+ <string>163.IBPluginDependency</string>
+ <string>164.IBPluginDependency</string>
+ <string>165.IBPluginDependency</string>
+ <string>165.ImportedFromIB2</string>
+ <string>166.IBPluginDependency</string>
+ <string>166.ImportedFromIB2</string>
+ <string>167.IBPluginDependency</string>
+ <string>167.ImportedFromIB2</string>
+ <string>168.IBPluginDependency</string>
+ <string>168.ImportedFromIB2</string>
+ <string>169.IBPluginDependency</string>
+ <string>169.ImportedFromIB2</string>
+ <string>169.editorWindowContentRectSynchronizationRect</string>
+ <string>170.IBPluginDependency</string>
+ <string>170.ImportedFromIB2</string>
+ <string>171.IBPluginDependency</string>
+ <string>171.ImportedFromIB2</string>
+ <string>172.IBEditorWindowLastContentRect</string>
+ <string>172.IBPluginDependency</string>
+ <string>172.ImportedFromIB2</string>
+ <string>172.editorWindowContentRectSynchronizationRect</string>
+ <string>173.IBPluginDependency</string>
+ <string>174.IBPluginDependency</string>
+ <string>175.IBPluginDependency</string>
+ <string>176.IBPluginDependency</string>
+ <string>177.IBPluginDependency</string>
+ <string>177.ImportedFromIB2</string>
+ <string>178.IBPluginDependency</string>
+ <string>178.ImportedFromIB2</string>
+ <string>179.IBPluginDependency</string>
+ <string>179.ImportedFromIB2</string>
+ <string>180.IBEditorWindowLastContentRect</string>
+ <string>180.IBPluginDependency</string>
+ <string>181.IBPluginDependency</string>
+ <string>182.IBPluginDependency</string>
+ <string>183.IBPluginDependency</string>
+ <string>184.IBEditorWindowLastContentRect</string>
+ <string>184.IBPluginDependency</string>
+ <string>184.ImportedFromIB2</string>
+ <string>184.editorWindowContentRectSynchronizationRect</string>
+ <string>185.IBPluginDependency</string>
+ <string>185.ImportedFromIB2</string>
+ <string>186.IBPluginDependency</string>
+ <string>186.ImportedFromIB2</string>
+ <string>187.IBPluginDependency</string>
+ <string>187.ImportedFromIB2</string>
+ <string>188.IBPluginDependency</string>
+ <string>188.ImportedFromIB2</string>
+ <string>189.IBPluginDependency</string>
+ <string>189.ImportedFromIB2</string>
+ <string>190.IBPluginDependency</string>
+ <string>190.ImportedFromIB2</string>
+ <string>191.IBPluginDependency</string>
+ <string>191.ImportedFromIB2</string>
+ <string>192.IBPluginDependency</string>
+ <string>192.ImportedFromIB2</string>
+ <string>193.IBPluginDependency</string>
+ <string>193.ImportedFromIB2</string>
+ <string>194.IBPluginDependency</string>
+ <string>194.ImportedFromIB2</string>
+ <string>195.IBPluginDependency</string>
+ <string>195.ImportedFromIB2</string>
+ <string>196.IBPluginDependency</string>
+ <string>196.ImportedFromIB2</string>
+ <string>196.editorWindowContentRectSynchronizationRect</string>
+ <string>197.IBPluginDependency</string>
+ <string>197.ImportedFromIB2</string>
+ <string>198.IBEditorWindowLastContentRect</string>
+ <string>198.IBPluginDependency</string>
+ <string>198.editorWindowContentRectSynchronizationRect</string>
+ <string>199.IBPluginDependency</string>
+ <string>200.IBPluginDependency</string>
+ <string>201.IBEditorWindowLastContentRect</string>
+ <string>201.IBPluginDependency</string>
+ <string>202.IBPluginDependency</string>
+ <string>203.IBPluginDependency</string>
+ <string>204.IBEditorWindowLastContentRect</string>
+ <string>204.IBPluginDependency</string>
+ <string>205.IBPluginDependency</string>
+ <string>206.IBPluginDependency</string>
+ <string>207.IBPluginDependency</string>
+ <string>208.IBPluginDependency</string>
+ <string>209.IBPluginDependency</string>
+ <string>210.IBPluginDependency</string>
+ <string>211.IBPluginDependency</string>
+ <string>212.IBPluginDependency</string>
+ <string>213.IBPluginDependency</string>
+ <string>214.IBPluginDependency</string>
+ <string>215.IBPluginDependency</string>
+ <string>216.IBPluginDependency</string>
+ <string>217.IBPluginDependency</string>
+ <string>218.IBPluginDependency</string>
+ <string>219.IBPluginDependency</string>
+ <string>220.IBPluginDependency</string>
+ <string>221.IBPluginDependency</string>
+ <string>222.IBPluginDependency</string>
+ <string>223.IBPluginDependency</string>
+ <string>224.IBPluginDependency</string>
+ <string>225.IBPluginDependency</string>
+ <string>226.IBPluginDependency</string>
+ <string>227.IBPluginDependency</string>
+ <string>228.IBPluginDependency</string>
+ <string>229.IBPluginDependency</string>
+ <string>230.IBPluginDependency</string>
+ <string>231.IBPluginDependency</string>
+ <string>232.IBPluginDependency</string>
+ <string>233.IBPluginDependency</string>
+ <string>234.IBPluginDependency</string>
+ <string>235.IBPluginDependency</string>
+ <string>236.IBEditorWindowLastContentRect</string>
+ <string>236.IBPluginDependency</string>
+ <string>237.IBPluginDependency</string>
+ <string>238.IBPluginDependency</string>
+ <string>239.IBPluginDependency</string>
+ <string>240.IBPluginDependency</string>
+ <string>241.IBPluginDependency</string>
+ <string>242.IBPluginDependency</string>
+ <string>243.IBPluginDependency</string>
+ <string>244.IBPluginDependency</string>
+ <string>245.IBPluginDependency</string>
+ <string>246.IBPluginDependency</string>
+ <string>247.IBEditorWindowLastContentRect</string>
+ <string>247.IBPluginDependency</string>
+ <string>248.IBPluginDependency</string>
+ <string>249.IBPluginDependency</string>
+ <string>250.IBPluginDependency</string>
+ <string>251.IBPluginDependency</string>
+ <string>252.IBPluginDependency</string>
+ <string>253.IBPluginDependency</string>
+ <string>254.IBPluginDependency</string>
+ <string>255.IBPluginDependency</string>
+ <string>256.IBPluginDependency</string>
+ <string>257.IBEditorWindowLastContentRect</string>
+ <string>257.IBPluginDependency</string>
+ <string>258.IBPluginDependency</string>
+ <string>259.IBEditorWindowLastContentRect</string>
+ <string>259.IBPluginDependency</string>
+ <string>259.IBWindowTemplateEditedContentRect</string>
+ <string>259.NSWindowTemplate.visibleAtLaunch</string>
+ <string>259.editorWindowContentRectSynchronizationRect</string>
+ <string>259.windowTemplate.maxSize</string>
+ <string>260.IBPluginDependency</string>
+ <string>261.IBPluginDependency</string>
+ <string>261.IBViewBoundsToFrameTransform</string>
+ </object>
+ <object class="NSMutableArray" key="dict.values">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{380, 836}, {400, 20}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{74, 862}</string>
+ <string>{{6, 978}, {478, 20}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{654, 239}, {194, 73}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{525, 802}, {197, 73}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{286, 129}, {275, 183}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{23, 794}, {245, 183}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{436, 809}, {64, 6}}</string>
+ <string>{{547, 180}, {254, 283}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{187, 434}, {243, 243}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{753, 217}, {238, 103}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{608, 612}, {241, 103}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{753, 187}, {275, 113}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{608, 612}, {275, 83}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{608, 612}, {167, 43}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{746, 287}, {220, 133}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{608, 612}, {215, 63}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{753, 197}, {170, 63}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{452, 109}, {196, 203}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{145, 474}, {199, 203}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{522, 812}, {146, 23}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <integer value="1"/>
+ <string>{{604, 269}, {231, 43}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{475, 832}, {234, 43}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{591, 420}, {83, 43}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{523, 2}, {178, 283}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{674, 260}, {204, 183}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{878, 180}, {164, 173}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{725, 289}, {246, 23}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{451, 1180}, {640, 461}}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>{{451, 1180}, {640, 461}}</string>
+ <integer value="1"/>
+ <string>{{33, 99}, {480, 360}}</string>
+ <string>{3.40282e+38, 3.40282e+38}</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <string>com.apple.InterfaceBuilder.CocoaPlugin</string>
+ <object class="NSAffineTransform"/>
+ </object>
+ </object>
+ <object class="NSMutableDictionary" key="unlocalizedProperties">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference key="dict.sortedKeys" ref="485438096"/>
+ <object class="NSMutableArray" key="dict.values">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ </object>
+ </object>
+ <nil key="activeLocalization"/>
+ <object class="NSMutableDictionary" key="localizations">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <reference key="dict.sortedKeys" ref="485438096"/>
+ <object class="NSMutableArray" key="dict.values">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ </object>
+ </object>
+ <nil key="sourceID"/>
+ <int key="maxID">263</int>
+ </object>
+ <object class="IBClassDescriber" key="IBDocument.Classes">
+ <object class="NSMutableArray" key="referencedPartialClassDescriptionsV3.2+">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSArchiver.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSClassDescription.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSError.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSFileManager.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSKeyValueCoding.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSKeyValueObserving.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSKeyedArchiver.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSObject.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSObjectScripting.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSPortCoder.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSRunLoop.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSScriptClassDescription.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSScriptKeyValueCoding.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSScriptObjectSpecifiers.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSScriptWhoseTests.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSThread.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSURL.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSURLConnection.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">Foundation.framework/Headers/NSURLDownload.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">PrintCore.framework/Headers/PDEPluginInterface.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">QuartzCore.framework/Headers/CAAnimation.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">QuartzCore.framework/Headers/CALayer.h</string>
+ </object>
+ </object>
+ <object class="IBPartialClassDescription">
+ <string key="className">NSObject</string>
+ <object class="IBClassDescriptionSource" key="sourceIdentifier">
+ <string key="majorKey">IBFrameworkSource</string>
+ <string key="minorKey">QuartzCore.framework/Headers/CIImageProvider.h</string>
+ </object>
+ </object>
+ </object>
+ </object>
+ <int key="IBDocument.localizationMode">0</int>
+ <string key="IBDocument.TargetRuntimeIdentifier">IBCocoaFramework</string>
+ <object class="NSMutableDictionary" key="IBDocument.PluginDeclaredDependencyDefaults">
+ <string key="NS.key.0">com.apple.InterfaceBuilder.CocoaPlugin.macosx</string>
+ <integer value="1060" key="NS.object.0"/>
+ </object>
+ <object class="NSMutableDictionary" key="IBDocument.PluginDeclaredDevelopmentDependencies">
+ <string key="NS.key.0">com.apple.InterfaceBuilder.CocoaPlugin.InterfaceBuilder3</string>
+ <integer value="3000" key="NS.object.0"/>
+ </object>
+ <bool key="IBDocument.PluginDeclaredDependenciesTrackSystemTargetVersion">YES</bool>
+ <string key="IBDocument.LastKnownRelativeProjectPath">../../out/gyp/shapeops_demo.xcodeproj</string>
+ <int key="IBDocument.defaultPropertyAccessControl">3</int>
+ <object class="NSMutableDictionary" key="IBDocument.LastKnownImageSizes">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <object class="NSArray" key="dict.sortedKeys">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <string>NSMenuCheckmark</string>
+ <string>NSMenuMixedState</string>
+ </object>
+ <object class="NSMutableArray" key="dict.values">
+ <bool key="EncodedWithXMLCoder">YES</bool>
+ <string>{9, 8}</string>
+ <string>{7, 2}</string>
+ </object>
+ </object>
+ </data>
+</archive>
diff --git a/experimental/Intersection/EdgeMain.cpp b/experimental/Intersection/EdgeMain.cpp
new file mode 100644
index 0000000000..a87a5cdd51
--- /dev/null
+++ b/experimental/Intersection/EdgeMain.cpp
@@ -0,0 +1,11 @@
+/*
+ * EdgeMain.cpp
+ * shapeops_edge
+ *
+ * Created by Cary Clark on 3/26/12.
+ * Copyright 2012 __MyCompanyName__. All rights reserved.
+ *
+ */
+
+#include "EdgeMain.h"
+
diff --git a/experimental/Intersection/EdgeMain.h b/experimental/Intersection/EdgeMain.h
new file mode 100644
index 0000000000..0ab897c07a
--- /dev/null
+++ b/experimental/Intersection/EdgeMain.h
@@ -0,0 +1,6 @@
+#include "Intersection_Tests.h"
+
+int main(int argc, char* argv) {
+ Intersection_Tests();
+ return 0;
+} \ No newline at end of file
diff --git a/experimental/Intersection/EdgeWalker.cpp b/experimental/Intersection/EdgeWalker.cpp
index 94d6e5a2a9..59ce914e23 100644
--- a/experimental/Intersection/EdgeWalker.cpp
+++ b/experimental/Intersection/EdgeWalker.cpp
@@ -12,10 +12,11 @@
#include "SkRect.h"
#include "SkTArray.h"
#include "SkTDArray.h"
+#include "ShapeOps.h"
#include "TSearch.h"
#if 0 // set to 1 for no debugging whatsoever
-static bool gShowDebugf = false; // FIXME: remove once debugging is complete
+const bool gShowDebugf = false; // FIXME: remove once debugging is complete
#define DEBUG_DUMP 0
#define DEBUG_ADD 0
@@ -31,13 +32,13 @@ static bool gShowDebugf = false; // FIXME: remove once debugging is complete
#define DEBUG_BOTTOM 0
#else
-static bool gShowDebugf = true; // FIXME: remove once debugging is complete
+const bool gShowDebugf = true; // FIXME: remove once debugging is complete
#define DEBUG_DUMP 01
#define DEBUG_ADD 01
#define DEBUG_ADD_INTERSECTING_TS 0
#define DEBUG_ADD_BOTTOM_TS 0
-#define COMPARE_DOUBLE 01
+#define COMPARE_DOUBLE 0
#define DEBUG_ABOVE_BELOW 01
#define DEBUG_ACTIVE_LESS_THAN 01
#define DEBUG_SORT_HORIZONTAL 01
@@ -48,9 +49,7 @@ static bool gShowDebugf = true; // FIXME: remove once debugging is complete
#endif
-// FIXME: not wild about this -- min delta should be based on size of curve, not t
-// #define MIN_T_DELTA 0.000001
-// not wild about this either -- for SkScalars backed by floats, would like to
+// FIXME: not wild about this -- for SkScalars backed by floats, would like to
// represent deltas in terms of number of significant matching bits
#define MIN_PT_DELTA 0.000001
@@ -117,9 +116,6 @@ static void LineSubDivide(const SkPoint a[2], double startT, double endT,
}
#endif
-// functions
-void contourBounds(const SkPath& path, SkTDArray<SkRect>& boundsArray);
-void simplify(const SkPath& path, bool asFill, SkPath& simple);
/*
list of edges
bounds for edge
@@ -290,7 +286,9 @@ public:
}
gap = lastLine[1] != *start;
if (gap) {
- SkASSERT(fFill && lastLine[1].fY == start->fY);
+ // FIXME: see comment in bridge -- this probably
+ // conceals errors
+ SkASSERT(fFill && UlpsDiff(lastLine[1].fY, start->fY) <= 10);
simple.lineTo(lastLine[1].fX, lastLine[1].fY);
if (gShowDebugf) {
SkDebugf("%s lineTo x (%g,%g)\n", __FUNCTION__,
@@ -298,8 +296,10 @@ public:
}
}
if (gap || !extendLine(lastLine, *end)) {
+ // FIXME: see comment in bridge -- this probably
+ // conceals errors
SkASSERT(lastLine[1] == *start ||
- (fFill && lastLine[1].fY == start->fY));
+ (fFill && UlpsDiff(lastLine[1].fY, start->fY) <= 10));
simple.lineTo(start->fX, start->fY);
if (gShowDebugf) {
SkDebugf("%s lineTo (%g,%g)\n", __FUNCTION__,
@@ -447,8 +447,10 @@ public:
pairUp = leftMatch == rightMatch;
} else {
#if DEBUG_OUT
- if (left.fPts[leftIndex < 0 ? 0 : left.fVerb].fY
- != right.fPts[rightIndex < 0 ? 0 : right.fVerb].fY) {
+ // FIXME : not happy that error in low bit is allowed
+ // this probably conceals error elsewhere
+ if (UlpsDiff(left.fPts[leftIndex < 0 ? 0 : left.fVerb].fY,
+ right.fPts[rightIndex < 0 ? 0 : right.fVerb].fY) > 1) {
*fMismatches.append() = leftIndex;
if (rightPtr == lastPtr) {
*fMismatches.append() = rightIndex;
@@ -456,8 +458,8 @@ public:
pairUp = false;
}
#else
- SkASSERT(left.fPts[leftIndex < 0 ? 0 : left.fVerb].fY
- == right.fPts[rightIndex < 0 ? 0 : right.fVerb].fY);
+ SkASSERT(UlpsDiff(left.fPts[leftIndex < 0 ? 0 : left.fVerb].fY,
+ right.fPts[rightIndex < 0 ? 0 : right.fVerb].fY) <= 10);
#endif
}
if (pairUp) {
@@ -895,8 +897,29 @@ struct WorkEdge {
// as active edges are introduced, only local sorting should be required
class ActiveEdge {
public:
- // OPTIMIZATION: fold return statements into one
bool operator<(const ActiveEdge& rh) const {
+ double topD = fAbove.fX - rh.fAbove.fX;
+ if (rh.fAbove.fY < fAbove.fY) {
+ topD = (rh.fBelow.fY - rh.fAbove.fY) * topD
+ - (fAbove.fY - rh.fAbove.fY) * (rh.fBelow.fX - rh.fAbove.fX);
+ } else if (rh.fAbove.fY > fAbove.fY) {
+ topD = (fBelow.fY - fAbove.fY) * topD
+ + (rh.fAbove.fY - fAbove.fY) * (fBelow.fX - fAbove.fX);
+ }
+ double botD = fBelow.fX - rh.fBelow.fX;
+ if (rh.fBelow.fY > fBelow.fY) {
+ botD = (rh.fBelow.fY - rh.fAbove.fY) * botD
+ - (fBelow.fY - rh.fBelow.fY) * (rh.fBelow.fX - rh.fAbove.fX);
+ } else if (rh.fBelow.fY < fBelow.fY) {
+ botD = (fBelow.fY - fAbove.fY) * botD
+ + (rh.fBelow.fY - fBelow.fY) * (fBelow.fX - fAbove.fX);
+ }
+ // return sign of greater absolute value
+ return (fabs(topD) > fabs(botD) ? topD : botD) < 0;
+ }
+
+ // OPTIMIZATION: fold return statements into one
+ bool operator_less_than(const ActiveEdge& rh) const {
if (rh.fAbove.fY - fAbove.fY > fBelow.fY - rh.fAbove.fY
&& fBelow.fY < rh.fBelow.fY
|| fAbove.fY - rh.fAbove.fY < rh.fBelow.fY - fAbove.fY
@@ -1114,10 +1137,16 @@ public:
// edges.
bool isCoincidentWith(const ActiveEdge* edge, SkScalar y) const {
+#if 0
if (!fAbove.equalsWithinTolerance(edge->fAbove, MIN_PT_DELTA)
|| !fBelow.equalsWithinTolerance(edge->fBelow, MIN_PT_DELTA)) {
return false;
}
+#else
+ if (fAbove != edge->fAbove || fBelow != edge->fBelow) {
+ return false;
+ }
+#endif
uint8_t verb = fDone ? fWorkEdge.lastVerb() : fWorkEdge.verb();
uint8_t edgeVerb = edge->fDone ? edge->fWorkEdge.lastVerb()
: edge->fWorkEdge.verb();
@@ -1138,6 +1167,11 @@ public:
// The shortest close call edge should be moved into a position where
// it contributes if the winding is transitioning to or from zero.
bool swapClose(const ActiveEdge* next, int prev, int wind, int mask) const {
+#if DEBUG_ADJUST_COINCIDENT
+ SkDebugf("%s edge=%d (%g) next=%d (%g) prev=%d wind=%d nextWind=%d\n",
+ __FUNCTION__, ID(), fBelow.fY, next->ID(), next->fBelow.fY,
+ prev, wind, wind + next->fWorkEdge.winding());
+#endif
if ((prev & mask) == 0 || (wind & mask) == 0) {
return next->fBelow.fY < fBelow.fY;
}
@@ -1170,6 +1204,11 @@ public:
bool tooCloseToCall(const ActiveEdge* edge) const {
int ulps;
+ // FIXME: the first variation works better (or at least causes fewer tests
+ // to fail than the second, although the second's logic better matches the
+ // current sort criteria. Need to track down the cause of the crash, and
+ // see if the second case isn't somehow buggy.
+#if 01
// FIXME: don't compare points for equality
// OPTIMIZATION: refactor to make one call to UlpsDiff
if (edge->fAbove.fY - fAbove.fY > fBelow.fY - edge->fAbove.fY
@@ -1189,6 +1228,38 @@ public:
(check.fY - edge->fAbove.fY)
* (edge->fBelow.fX - edge->fAbove.fX));
}
+#else
+ double t1, t2, b1, b2;
+ if (edge->fAbove.fY < fAbove.fY) {
+ t1 = (edge->fBelow.fY - edge->fAbove.fY) * (fAbove.fX - edge->fAbove.fX);
+ t2 = (fAbove.fY - edge->fAbove.fY) * (edge->fBelow.fX - edge->fAbove.fX);
+ } else if (edge->fAbove.fY > fAbove.fY) {
+ t1 = (fBelow.fY - fAbove.fY) * (fAbove.fX - edge->fAbove.fX);
+ t2 = (fAbove.fY - edge->fAbove.fY) * (fBelow.fX - fAbove.fX);
+ } else {
+ t1 = fAbove.fX;
+ t2 = edge->fAbove.fX;
+ }
+ if (edge->fBelow.fY > fBelow.fY) {
+ b1 = (edge->fBelow.fY - edge->fAbove.fY) * (fBelow.fX - edge->fBelow.fX);
+ b2 = (fBelow.fY - edge->fBelow.fY) * (edge->fBelow.fX - edge->fAbove.fX);
+ } else if (edge->fBelow.fY < fBelow.fY) {
+ b1 = (fBelow.fY - fAbove.fY) * (fBelow.fX - edge->fBelow.fX);
+ b2 = (fBelow.fY - edge->fBelow.fY) * (fBelow.fX - fAbove.fX);
+ } else {
+ b1 = fBelow.fX;
+ b2 = edge->fBelow.fX;
+ }
+ if (fabs(t1 - t2) > fabs(b1 - b2)) {
+ ulps = UlpsDiff(t1, t2);
+ } else {
+ ulps = UlpsDiff(b1, b2);
+ }
+#if DEBUG_ADJUST_COINCIDENT
+ SkDebugf("%s this=%d edge=%d ulps=%d\n", __FUNCTION__, ID(), edge->ID(),
+ ulps);
+#endif
+#endif
return ulps >= 0 && ulps <= 32;
}
@@ -1522,12 +1593,12 @@ static void skipCoincidence(int lastWinding, int winding, int windingMask,
static void sortHorizontal(SkTDArray<ActiveEdge>& activeEdges,
SkTDArray<ActiveEdge*>& edgeList, SkScalar y) {
- const int tab = 3; // FIXME: debugging only
size_t edgeCount = activeEdges.count();
if (edgeCount == 0) {
return;
}
#if DEBUG_SORT_HORIZONTAL
+ const int tab = 3; // FIXME: debugging only
SkDebugf("%s y=%1.9g\n", __FUNCTION__, y);
#endif
size_t index;
diff --git a/experimental/Intersection/EdgeWalkerPolygon4x4_Test.cpp b/experimental/Intersection/EdgeWalkerPolygon4x4_Test.cpp
new file mode 100755
index 0000000000..27ec5be90f
--- /dev/null
+++ b/experimental/Intersection/EdgeWalkerPolygon4x4_Test.cpp
@@ -0,0 +1,306 @@
+#include "EdgeWalker_Test.h"
+#include "Intersection_Tests.h"
+#include <assert.h>
+#include <pthread.h>
+
+struct State {
+ int a;
+ int b;
+ int c;
+ int d;
+ pthread_t threadID;
+ bool abcIsATriangle;
+};
+
+void createThread(State* statePtr, void* (*test)(void* )) {
+ int threadError = pthread_create(&statePtr->threadID, NULL, test,
+ (void*) statePtr);
+ SkASSERT(!threadError);
+}
+
+void waitForCompletion(State threadState[], int& threadIndex) {
+ for (int index = 0; index < threadIndex; ++index) {
+ pthread_join(threadState[index].threadID, NULL);
+ }
+ SkDebugf(".");
+ threadIndex = 0;
+}
+
+static void* testSimplify4x4QuadralateralsMain(void* data)
+{
+ char pathStr[1024];
+ bzero(pathStr, sizeof(pathStr));
+ SkASSERT(data);
+ State& state = *(State*) data;
+ int ax = state.a & 0x03;
+ int ay = state.a >> 2;
+ int bx = state.b & 0x03;
+ int by = state.b >> 2;
+ int cx = state.c & 0x03;
+ int cy = state.c >> 2;
+ int dx = state.d & 0x03;
+ int dy = state.d >> 2;
+ for (int e = 0 ; e < 16; ++e) {
+ int ex = e & 0x03;
+ int ey = e >> 2;
+ for (int f = e ; f < 16; ++f) {
+ int fx = f & 0x03;
+ int fy = f >> 2;
+ for (int g = f ; g < 16; ++g) {
+ int gx = g & 0x03;
+ int gy = g >> 2;
+ for (int h = g ; h < 16; ++h) {
+ int hx = h & 0x03;
+ int hy = h >> 2;
+ SkPath path, out;
+ path.setFillType(SkPath::kWinding_FillType);
+ path.moveTo(ax, ay);
+ path.lineTo(bx, by);
+ path.lineTo(cx, cy);
+ path.lineTo(dx, dy);
+ path.close();
+ path.moveTo(ex, ey);
+ path.lineTo(fx, fy);
+ path.lineTo(gx, gy);
+ path.lineTo(hx, hy);
+ path.close();
+ if (1) { // gdb: set print elements 400
+ char* str = pathStr;
+ str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", dx, dy);
+ str += sprintf(str, " path.close();\n");
+ str += sprintf(str, " path.moveTo(%d, %d);\n", ex, ey);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", gx, gy);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", hx, hy);
+ str += sprintf(str, " path.close();");
+ }
+ if (!testSimplify(path, true, out)) {
+ SkDebugf("*/\n{ SkPath::kWinding_FillType, %d, %d, %d, %d,"
+ " %d, %d, %d, %d },\n/*\n", state.a, state.b, state.c, state.d,
+ e, f, g, h);
+ }
+ path.setFillType(SkPath::kEvenOdd_FillType);
+ if (!testSimplify(path, true, out)) {
+ SkDebugf("*/\n{ SkPath::kEvenOdd_FillType, %d, %d, %d, %d,"
+ " %d, %d, %d, %d },\n/*\n", state.a, state.b, state.c, state.d,
+ e, f, g, h);
+ }
+ }
+ }
+ }
+ }
+ return NULL;
+}
+
+const int maxThreads = gShowDebugf ? 1 : 24;
+
+void Simplify4x4QuadralateralsThreaded_Test()
+{
+ State threadState[maxThreads];
+ int threadIndex = 0;
+ for (int a = 0; a < 16; ++a) {
+ for (int b = a ; b < 16; ++b) {
+ for (int c = b ; c < 16; ++c) {
+ for (int d = c; d < 16; ++d) {
+ State* statePtr = &threadState[threadIndex];
+ statePtr->a = a;
+ statePtr->b = b;
+ statePtr->c = c;
+ statePtr->d = d;
+ if (maxThreads > 1) {
+ createThread(statePtr, testSimplify4x4QuadralateralsMain);
+ if (++threadIndex >= maxThreads) {
+ waitForCompletion(threadState, threadIndex);
+ }
+ } else {
+ testSimplify4x4QuadralateralsMain(statePtr);
+ }
+ }
+ }
+ }
+ }
+ waitForCompletion(threadState, threadIndex);
+}
+
+
+static void* testSimplify4x4NondegeneratesMain(void* data) {
+ char pathStr[1024];
+ bzero(pathStr, sizeof(pathStr));
+ SkASSERT(data);
+ State& state = *(State*) data;
+ int ax = state.a & 0x03;
+ int ay = state.a >> 2;
+ int bx = state.b & 0x03;
+ int by = state.b >> 2;
+ int cx = state.c & 0x03;
+ int cy = state.c >> 2;
+ for (int d = 0; d < 15; ++d) {
+ int dx = d & 0x03;
+ int dy = d >> 2;
+ for (int e = d + 1; e < 16; ++e) {
+ int ex = e & 0x03;
+ int ey = e >> 2;
+ for (int f = d + 1; f < 16; ++f) {
+ if (e == f) {
+ continue;
+ }
+ int fx = f & 0x03;
+ int fy = f >> 2;
+ if ((ex - dx) * (fy - dy) == (ey - dy) * (fx - dx)) {
+ continue;
+ }
+ SkPath path, out;
+ path.setFillType(SkPath::kWinding_FillType);
+ path.moveTo(ax, ay);
+ path.lineTo(bx, by);
+ path.lineTo(cx, cy);
+ path.close();
+ path.moveTo(dx, dy);
+ path.lineTo(ex, ey);
+ path.lineTo(fx, fy);
+ path.close();
+ if (1) {
+ char* str = pathStr;
+ str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
+ str += sprintf(str, " path.close();\n");
+ str += sprintf(str, " path.moveTo(%d, %d);\n", dx, dy);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", ex, ey);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
+ str += sprintf(str, " path.close();");
+ }
+ testSimplify(path, true, out);
+ path.setFillType(SkPath::kEvenOdd_FillType);
+ testSimplify(path, true, out);
+ }
+ }
+ }
+ return NULL;
+}
+
+void SimplifyNondegenerate4x4TrianglesThreaded_Test() {
+ State threadState[maxThreads];
+ int threadIndex = 0;
+ for (int a = 0; a < 15; ++a) {
+ int ax = a & 0x03;
+ int ay = a >> 2;
+ for (int b = a + 1; b < 16; ++b) {
+ int bx = b & 0x03;
+ int by = b >> 2;
+ for (int c = a + 1; c < 16; ++c) {
+ if (b == c) {
+ continue;
+ }
+ int cx = c & 0x03;
+ int cy = c >> 2;
+ if ((bx - ax) * (cy - ay) == (by - ay) * (cx - ax)) {
+ continue;
+ }
+ State* statePtr = &threadState[threadIndex];
+ statePtr->a = a;
+ statePtr->b = b;
+ statePtr->c = c;
+ if (maxThreads > 1) {
+ createThread(statePtr, testSimplify4x4NondegeneratesMain);
+ if (++threadIndex >= maxThreads) {
+ waitForCompletion(threadState, threadIndex);
+ }
+ } else {
+ testSimplify4x4NondegeneratesMain(statePtr);
+ }
+ }
+ }
+ }
+ waitForCompletion(threadState, threadIndex);
+}
+
+static void* testSimplify4x4DegeneratesMain(void* data) {
+ char pathStr[1024];
+ bzero(pathStr, sizeof(pathStr));
+ SkASSERT(data);
+ State& state = *(State*) data;
+ int ax = state.a & 0x03;
+ int ay = state.a >> 2;
+ int bx = state.b & 0x03;
+ int by = state.b >> 2;
+ int cx = state.c & 0x03;
+ int cy = state.c >> 2;
+ for (int d = 0; d < 16; ++d) {
+ int dx = d & 0x03;
+ int dy = d >> 2;
+ for (int e = d ; e < 16; ++e) {
+ int ex = e & 0x03;
+ int ey = e >> 2;
+ for (int f = d ; f < 16; ++f) {
+ int fx = f & 0x03;
+ int fy = f >> 2;
+ if (state.abcIsATriangle && (ex - dx) * (fy - dy)
+ != (ey - dy) * (fx - dx)) {
+ continue;
+ }
+ SkPath path, out;
+ path.setFillType(SkPath::kWinding_FillType);
+ path.moveTo(ax, ay);
+ path.lineTo(bx, by);
+ path.lineTo(cx, cy);
+ path.close();
+ path.moveTo(dx, dy);
+ path.lineTo(ex, ey);
+ path.lineTo(fx, fy);
+ path.close();
+ if (1) {
+ char* str = pathStr;
+ str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
+ str += sprintf(str, " path.close();\n");
+ str += sprintf(str, " path.moveTo(%d, %d);\n", dx, dy);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", ex, ey);
+ str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
+ str += sprintf(str, " path.close();");
+ }
+ testSimplify(path, true, out);
+ path.setFillType(SkPath::kEvenOdd_FillType);
+ testSimplify(path, true, out);
+ }
+ }
+ }
+ return NULL;
+}
+
+void SimplifyDegenerate4x4TrianglesThreaded_Test() {
+ State threadState[maxThreads];
+ int threadIndex = 0;
+ for (int a = 0; a < 16; ++a) {
+ int ax = a & 0x03;
+ int ay = a >> 2;
+ for (int b = a ; b < 16; ++b) {
+ int bx = b & 0x03;
+ int by = b >> 2;
+ for (int c = a ; c < 16; ++c) {
+ int cx = c & 0x03;
+ int cy = c >> 2;
+ State* statePtr = &threadState[threadIndex];
+ statePtr->abcIsATriangle = (bx - ax) * (cy - ay)
+ != (by - ay) * (cx - ax);
+ statePtr->a = a;
+ statePtr->b = b;
+ statePtr->c = c;
+ if (maxThreads > 1) {
+ createThread(statePtr, testSimplify4x4DegeneratesMain);
+ if (++threadIndex >= maxThreads) {
+ waitForCompletion(threadState, threadIndex);
+ }
+ } else {
+ testSimplify4x4DegeneratesMain(statePtr);
+ }
+ }
+ }
+ }
+ waitForCompletion(threadState, threadIndex);
+}
+
diff --git a/experimental/Intersection/EdgeWalkerPolygons_Test.cpp b/experimental/Intersection/EdgeWalkerPolygons_Test.cpp
index 3cc1b5d982..51f65348f1 100644
--- a/experimental/Intersection/EdgeWalkerPolygons_Test.cpp
+++ b/experimental/Intersection/EdgeWalkerPolygons_Test.cpp
@@ -356,130 +356,6 @@ static void testSimplifyTriangle2() {
testSimplify(path, true, out); // expect | |
} // |_|
-static void testSimplifyNondegenerate4x4Triangles() {
- char pathStr[1024];
- bzero(pathStr, sizeof(pathStr));
- for (int a = 0; a < 15; ++a) {
- int ax = a & 0x03;
- int ay = a >> 2;
- for (int b = a + 1; b < 16; ++b) {
- int bx = b & 0x03;
- int by = b >> 2;
- for (int c = a + 1; c < 16; ++c) {
- if (b == c) {
- continue;
- }
- int cx = c & 0x03;
- int cy = c >> 2;
- if ((bx - ax) * (cy - ay) == (by - ay) * (cx - ax)) {
- continue;
- }
- for (int d = 0; d < 15; ++d) {
- int dx = d & 0x03;
- int dy = d >> 2;
- for (int e = d + 1; e < 16; ++e) {
- int ex = e & 0x03;
- int ey = e >> 2;
- for (int f = d + 1; f < 16; ++f) {
- if (e == f) {
- continue;
- }
- int fx = f & 0x03;
- int fy = f >> 2;
- if ((ex - dx) * (fy - dy) == (ey - dy) * (fx - dx)) {
- continue;
- }
- SkPath path, out;
- path.setFillType(SkPath::kWinding_FillType);
- path.moveTo(ax, ay);
- path.lineTo(bx, by);
- path.lineTo(cx, cy);
- path.close();
- path.moveTo(dx, dy);
- path.lineTo(ex, ey);
- path.lineTo(fx, fy);
- path.close();
- if (1) {
- char* str = pathStr;
- str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
- str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
- str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
- str += sprintf(str, " path.close();\n");
- str += sprintf(str, " path.moveTo(%d, %d);\n", dx, dy);
- str += sprintf(str, " path.lineTo(%d, %d);\n", ex, ey);
- str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
- str += sprintf(str, " path.close();");
- }
- testSimplify(path, true, out);
- path.setFillType(SkPath::kEvenOdd_FillType);
- testSimplify(path, true, out);
- }
- }
- }
- }
- }
- }
-}
-
-static void testSimplifyDegenerate4x4Triangles() {
- char pathStr[1024];
- bzero(pathStr, sizeof(pathStr));
- for (int a = 0; a < 16; ++a) {
- int ax = a & 0x03;
- int ay = a >> 2;
- for (int b = a ; b < 16; ++b) {
- int bx = b & 0x03;
- int by = b >> 2;
- for (int c = a ; c < 16; ++c) {
- int cx = c & 0x03;
- int cy = c >> 2;
- bool abcIsATriangle = (bx - ax) * (cy - ay)
- != (by - ay) * (cx - ax);
- for (int d = 0; d < 16; ++d) {
- int dx = d & 0x03;
- int dy = d >> 2;
- for (int e = d ; e < 16; ++e) {
- int ex = e & 0x03;
- int ey = e >> 2;
- for (int f = d ; f < 16; ++f) {
- int fx = f & 0x03;
- int fy = f >> 2;
- if (abcIsATriangle && (ex - dx) * (fy - dy)
- != (ey - dy) * (fx - dx)) {
- continue;
- }
- SkPath path, out;
- path.setFillType(SkPath::kWinding_FillType);
- path.moveTo(ax, ay);
- path.lineTo(bx, by);
- path.lineTo(cx, cy);
- path.close();
- path.moveTo(dx, dy);
- path.lineTo(ex, ey);
- path.lineTo(fx, fy);
- path.close();
- if (1) {
- char* str = pathStr;
- str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
- str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
- str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
- str += sprintf(str, " path.close();\n");
- str += sprintf(str, " path.moveTo(%d, %d);\n", dx, dy);
- str += sprintf(str, " path.lineTo(%d, %d);\n", ex, ey);
- str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
- str += sprintf(str, " path.close();");
- }
- testSimplify(path, true, out);
- path.setFillType(SkPath::kEvenOdd_FillType);
- testSimplify(path, true, out);
- }
- }
- }
- }
- }
- }
-}
-
static void testPathTriangleRendering() {
SkPath one, two;
one.moveTo(0, 0);
@@ -773,7 +649,79 @@ path.close();
simplify(__FUNCTION__, path, true, out);
}
+static void testSimplifySkinnyTriangle11() {
+ SkPath path, out;
+path.moveTo(-177.878387, 265.368988);
+path.lineTo(-254.415771, 303.709961);
+path.lineTo(-317.465363, 271.325562);
+path.lineTo(-374.520386, 207.507660);
+path.lineTo(-177.878387, 265.368988);
+path.close();
+path.moveTo(-63.582489, -3.679123);
+path.lineTo(-134.496841, 26.434566);
+path.lineTo(-205.411209, 56.548256);
+path.lineTo(-276.325562, 86.661942);
+path.lineTo(-63.582489, -3.679123);
+path.close();
+path.moveTo(-57.078423, 162.633453);
+path.lineTo(-95.963928, 106.261139);
+path.lineTo(-134.849457, 49.888824);
+path.lineTo(-173.734955, -6.483480);
+path.lineTo(-57.078423, 162.633453);
+path.close();
+ simplify(__FUNCTION__, path, true, out);
+}
+
+static void testSimplifySkinnyTriangle12() {
+ SkPath path, out;
+path.moveTo(98.666489, -94.295059);
+path.lineTo(156.584320, -61.939133);
+path.lineTo(174.672974, -12.343765);
+path.lineTo(158.622345, 52.028267);
+path.lineTo(98.666489, -94.295059);
+path.close();
+path.moveTo(-133.225616, -48.622055);
+path.lineTo(-73.855499, -10.375397);
+path.lineTo(-14.485367, 27.871277);
+path.lineTo(44.884750, 66.117935);
+path.lineTo(-133.225616, -48.622055);
+path.close();
+path.moveTo( 9.030045, -163.413132);
+path.lineTo(-19.605331, -89.588760);
+path.lineTo(-48.240707, -15.764404);
+path.lineTo(-76.876053, 58.059944);
+path.lineTo( 9.030045, -163.413132);
+path.close();
+ simplify(__FUNCTION__, path, true, out);
+}
+
+static void testSimplifySkinnyTriangle13() {
+ SkPath path, out;
+path.moveTo(340.41568, -170.97171);
+path.lineTo(418.846893, -142.428329);
+path.lineTo(497.278107, -113.884933);
+path.lineTo(449.18222, -45.6723022);
+path.lineTo(340.41568, -170.97171);
+path.close();
+path.moveTo(301.372925, -213.590073);
+path.lineTo(348.294434, -271.975586);
+path.lineTo(395.215973, -330.361145);
+path.lineTo(400.890381, -263.276855);
+path.lineTo(301.372925, -213.590073);
+path.close();
+path.moveTo(326.610535, 34.0393639);
+path.lineTo(371.334595, -14.9620667);
+path.lineTo(416.058624, -63.9634857);
+path.lineTo(460.782654, -112.96492);
+path.lineTo(326.610535, 34.0393639);
+path.close();
+ simplify(__FUNCTION__, path, true, out);
+}
+
static void (*simplifyTests[])() = {
+ testSimplifySkinnyTriangle13,
+ testSimplifySkinnyTriangle12,
+ testSimplifySkinnyTriangle11,
testSimplifySkinnyTriangle10,
testSimplifySkinnyTriangle9,
testSimplifySkinnyTriangle8,
@@ -812,8 +760,6 @@ static void (*simplifyTests[])() = {
testSimplifyTriangle2,
testSimplifyWindingParallelogram,
testSimplifyXorParallelogram,
- testSimplifyDegenerate4x4Triangles,
- testSimplifyNondegenerate4x4Triangles,
testPathTriangleRendering,
};
diff --git a/experimental/Intersection/EdgeWalkerQuadralaterals_Test.cpp b/experimental/Intersection/EdgeWalkerQuadralaterals_Test.cpp
index 6cb24171a4..a87b37f31b 100644
--- a/experimental/Intersection/EdgeWalkerQuadralaterals_Test.cpp
+++ b/experimental/Intersection/EdgeWalkerQuadralaterals_Test.cpp
@@ -91,79 +91,6 @@ static void testSimplifyQuad6() {
testSimplify(path, true, out);
}
-static void testSimplify4x4Quadralaterals() {
- char pathStr[1024];
- bzero(pathStr, sizeof(pathStr));
- for (int a = 0; a < 16; ++a) {
- int ax = a & 0x03;
- int ay = a >> 2;
- for (int b = a ; b < 16; ++b) {
- int bx = b & 0x03;
- int by = b >> 2;
- for (int c = b ; c < 16; ++c) {
- int cx = c & 0x03;
- int cy = c >> 2;
- for (int d = c; d < 16; ++d) {
- int dx = d & 0x03;
- int dy = d >> 2;
- for (int e = 0 ; e < 16; ++e) {
- int ex = e & 0x03;
- int ey = e >> 2;
- for (int f = e ; f < 16; ++f) {
- int fx = f & 0x03;
- int fy = f >> 2;
- for (int g = f ; g < 16; ++g) {
- int gx = g & 0x03;
- int gy = g >> 2;
- for (int h = g ; h < 16; ++h) {
- int hx = h & 0x03;
- int hy = h >> 2;
- SkPath path, out;
- path.setFillType(SkPath::kWinding_FillType);
- path.moveTo(ax, ay);
- path.lineTo(bx, by);
- path.lineTo(cx, cy);
- path.lineTo(dx, dy);
- path.close();
- path.moveTo(ex, ey);
- path.lineTo(fx, fy);
- path.lineTo(gx, gy);
- path.lineTo(hx, hy);
- path.close();
- if (1) { // gdb: set print elements 400
- char* str = pathStr;
- str += sprintf(str, " path.moveTo(%d, %d);\n", ax, ay);
- str += sprintf(str, " path.lineTo(%d, %d);\n", bx, by);
- str += sprintf(str, " path.lineTo(%d, %d);\n", cx, cy);
- str += sprintf(str, " path.lineTo(%d, %d);\n", dx, dy);
- str += sprintf(str, " path.close();\n");
- str += sprintf(str, " path.moveTo(%d, %d);\n", ex, ey);
- str += sprintf(str, " path.lineTo(%d, %d);\n", fx, fy);
- str += sprintf(str, " path.lineTo(%d, %d);\n", gx, gy);
- str += sprintf(str, " path.lineTo(%d, %d);\n", hx, hy);
- str += sprintf(str, " path.close();");
- }
- if (!testSimplify(path, true, out)) {
- SkDebugf("*/\n{ SkPath::kWinding_FillType, %d, %d, %d, %d, %d, %d, %d, %d },\n/*\n",
- a, b, c, d, e, f, g, h);
- }
- path.setFillType(SkPath::kEvenOdd_FillType);
- if (!testSimplify(path, true, out)) {
- SkDebugf("*/\n{ SkPath::kEvenOdd_FillType, %d, %d, %d, %d, %d, %d, %d, %d },\n/*\n",
- a, b, c, d, e, f, g, h);
- }
- }
- }
- }
- }
- }
- }
- }
- }
-}
-
-
-
static void (*simplifyTests[])() = {
testSimplifyQuad6,
testSimplifyQuad5,
@@ -171,7 +98,6 @@ static void (*simplifyTests[])() = {
testSimplifyQuad3,
testSimplifyQuad2,
testSimplifyQuad1,
- testSimplify4x4Quadralaterals,
};
static size_t simplifyTestsCount = sizeof(simplifyTests) / sizeof(simplifyTests[0]);
diff --git a/experimental/Intersection/EdgeWalker_Test.h b/experimental/Intersection/EdgeWalker_Test.h
index c7f405b19d..ac9743699a 100644
--- a/experimental/Intersection/EdgeWalker_Test.h
+++ b/experimental/Intersection/EdgeWalker_Test.h
@@ -1,12 +1,10 @@
-#include "SkPath.h"
+#include "ShapeOps.h"
-extern void contourBounds(const SkPath& path, SkTDArray<SkRect>& boundsArray);
extern bool comparePaths(const SkPath& one, const SkPath& two);
extern void comparePathsTiny(const SkPath& one, const SkPath& two);
extern bool drawAsciiPaths(const SkPath& one, const SkPath& two,
bool drawPaths);
-extern void simplify(const SkPath& path, bool asFill, SkPath& simple);
extern void showPath(const SkPath& path, const char* str = NULL);
extern bool testSimplify(const SkPath& path, bool fill, SkPath& out);
diff --git a/experimental/Intersection/EdgeWalker_TestUtility.cpp b/experimental/Intersection/EdgeWalker_TestUtility.cpp
index fc69516c40..2cd01539ba 100644
--- a/experimental/Intersection/EdgeWalker_TestUtility.cpp
+++ b/experimental/Intersection/EdgeWalker_TestUtility.cpp
@@ -19,17 +19,17 @@ void showPath(const SkPath& path, const char* str) {
while ((verb = iter.next(pts)) != SkPath::kDone_Verb) {
switch (verb) {
case SkPath::kMove_Verb:
- SkDebugf("path.moveTo(%3.6g, %3.6g);\n", pts[0].fX, pts[0].fY);
+ SkDebugf("path.moveTo(%1.9g, %1.9g);\n", pts[0].fX, pts[0].fY);
continue;
case SkPath::kLine_Verb:
- SkDebugf("path.lineTo(%3.6g, %3.6g);\n", pts[1].fX, pts[1].fY);
+ SkDebugf("path.lineTo(%1.9g, %1.9g);\n", pts[1].fX, pts[1].fY);
break;
case SkPath::kQuad_Verb:
- SkDebugf("path.quadTo(%3.6g, %3.6g, %3.6g, %3.6g);\n",
+ SkDebugf("path.quadTo(%1.9g, %1.9g, %1.9g, %1.9g);\n",
pts[1].fX, pts[1].fY, pts[2].fX, pts[2].fY);
break;
case SkPath::kCubic_Verb:
- SkDebugf("path.cubicTo(%3.6g, %3.6g, %3.6g, %3.6g);\n",
+ SkDebugf("path.cubicTo(%1.9g, %1.9g, %1.9g, %1.9g);\n",
pts[1].fX, pts[1].fY, pts[2].fX, pts[2].fY,
pts[3].fX, pts[3].fY);
break;
diff --git a/experimental/Intersection/IntersectionUtilities.cpp b/experimental/Intersection/IntersectionUtilities.cpp
index d05afdf947..e6ece7435f 100644
--- a/experimental/Intersection/IntersectionUtilities.cpp
+++ b/experimental/Intersection/IntersectionUtilities.cpp
@@ -1,4 +1,5 @@
+#if 0
// snippets that one day may be useful, unused for now...
// get sign, exponent, mantissa from double
@@ -37,4 +38,5 @@
{ /* i.e., Mantissa is even */
mantissa >>= 1;
exponent++;
- } \ No newline at end of file
+ }
+#endif \ No newline at end of file
diff --git a/experimental/Intersection/Intersection_Tests.cpp b/experimental/Intersection/Intersection_Tests.cpp
index 2cf960132f..d905b88934 100644
--- a/experimental/Intersection/Intersection_Tests.cpp
+++ b/experimental/Intersection/Intersection_Tests.cpp
@@ -5,6 +5,8 @@ void cubecode_test(int test);
void testSimplify();
void Intersection_Tests() {
+ ActiveEdge_Test();
+
cubecode_test(1);
convert_testx();
// tests are in dependency / complexity order
@@ -21,6 +23,10 @@ void Intersection_Tests() {
SimplifyRectangularPaths_Test();
SimplifyQuadralateralPaths_Test();
+ SimplifyDegenerate4x4TrianglesThreaded_Test();
+ SimplifyNondegenerate4x4TrianglesThreaded_Test();
+ Simplify4x4QuadralateralsThreaded_Test();
+
QuadraticCoincidence_Test();
QuadraticReduceOrder_Test();
QuadraticBezierClip_Test();
diff --git a/experimental/Intersection/Intersection_Tests.h b/experimental/Intersection/Intersection_Tests.h
index f007dda8de..f1287e1a1f 100644
--- a/experimental/Intersection/Intersection_Tests.h
+++ b/experimental/Intersection/Intersection_Tests.h
@@ -1,3 +1,4 @@
+void ActiveEdge_Test();
void ConvexHull_Test();
void ConvexHull_X_Test();
void CubicBezierClip_Test();
@@ -11,8 +12,11 @@ void LineCubicIntersection_Test();
void LineIntersection_Test();
void LineParameter_Test();
void LineQuadraticIntersection_Test();
+void SimplifyDegenerate4x4TrianglesThreaded_Test();
+void SimplifyNondegenerate4x4TrianglesThreaded_Test();
void SimplifyPolygonPaths_Test();
void SimplifyQuadralateralPaths_Test();
+void Simplify4x4QuadralateralsThreaded_Test();
void SimplifyRectangularPaths_Test();
void QuadraticBezierClip_Test();
void QuadraticCoincidence_Test();
diff --git a/experimental/Intersection/LineIntersection.h b/experimental/Intersection/LineIntersection.h
index 687b77d557..bb8b4b7d6f 100644
--- a/experimental/Intersection/LineIntersection.h
+++ b/experimental/Intersection/LineIntersection.h
@@ -1,3 +1,5 @@
+#ifndef LineIntersection_DEFINE
+#define LineIntersection_DEFINE
#include "DataTypes.h"
@@ -6,3 +8,5 @@ int horizontalLineIntersect(const _Line& line, double left, double right,
double y, double tRange[2]);
int intersect(const _Line& a, const _Line& b, double aRange[2], double bRange[2]);
bool testIntersect(const _Line& a, const _Line& b);
+
+#endif
diff --git a/experimental/Intersection/QuadraticParameterization_TestUtility.cpp b/experimental/Intersection/QuadraticParameterization_TestUtility.cpp
deleted file mode 100644
index 08a562bb8d..0000000000
--- a/experimental/Intersection/QuadraticParameterization_TestUtility.cpp
+++ /dev/null
@@ -1,17 +0,0 @@
-// included by QuadraticParameterization.cpp
-// accesses internal functions to validate parameterized coefficients
-
-#include "Parameterization_Test.h"
-
-bool point_on_parameterized_curve(const Quadratic& quad, const _Point& point) {
- double coeffs[coeff_count];
- implicit_coefficients(quad, coeffs);
- double xx = coeffs[ xx_coeff] * point.x * point.x;
- double xy = coeffs[ xy_coeff] * point.x * point.y;
- double yy = coeffs[ yy_coeff] * point.y * point.y;
- double x = coeffs[ x_coeff] * point.x;
- double y = coeffs[ y_coeff] * point.y;
- double c = coeffs[ c_coeff];
- double sum = xx + xy + yy + x + y + c;
- return approximately_zero(sum);
-}
diff --git a/experimental/Intersection/QuadraticUtilities.cpp b/experimental/Intersection/QuadraticUtilities.cpp
index aa784cbda5..51a7569609 100644
--- a/experimental/Intersection/QuadraticUtilities.cpp
+++ b/experimental/Intersection/QuadraticUtilities.cpp
@@ -1,4 +1,5 @@
#include "QuadraticUtilities.h"
+#include <math.h>
int quadraticRoots(double A, double B, double C, double t[2]) {
B *= 2;
diff --git a/experimental/Intersection/ReduceOrder.cpp b/experimental/Intersection/ReduceOrder.cpp
deleted file mode 100644
index e742a265e0..0000000000
--- a/experimental/Intersection/ReduceOrder.cpp
+++ /dev/null
@@ -1,238 +0,0 @@
-#include "CubicIntersection.h"
-#include "Extrema.h"
-#include "IntersectionUtilities.h"
-#include "LineParameters.h"
-
-#ifdef MAYBE_USEFUL_IN_THE_FUTURE
-static double interp_quad_coords(double a, double b, double c, double t)
-{
- double ab = interp(a, b, t);
- double bc = interp(b, c, t);
- return interp(ab, bc, t);
-}
-#endif
-
-static double interp_cubic_coords(const double* src, double t)
-{
- double ab = interp(src[0], src[2], t);
- double bc = interp(src[2], src[4], t);
- double cd = interp(src[4], src[6], t);
- double abc = interp(ab, bc, t);
- double bcd = interp(bc, cd, t);
- return interp(abc, bcd, t);
-}
-
-static int coincident_line(const Cubic& cubic, Cubic& reduction) {
- reduction[0] = reduction[1] = cubic[0];
- return 1;
-}
-
-static int vertical_line(const Cubic& cubic, Cubic& reduction) {
- double tValues[2];
- reduction[0] = cubic[0];
- reduction[1] = cubic[3];
- int smaller = reduction[1].y > reduction[0].y;
- int larger = smaller ^ 1;
- int roots = SkFindCubicExtrema(cubic[0].y, cubic[1].y, cubic[2].y, cubic[3].y, tValues);
- for (int index = 0; index < roots; ++index) {
- double yExtrema = interp_cubic_coords(&cubic[0].y, tValues[index]);
- if (reduction[smaller].y > yExtrema) {
- reduction[smaller].y = yExtrema;
- continue;
- }
- if (reduction[larger].y < yExtrema) {
- reduction[larger].y = yExtrema;
- }
- }
- return 2;
-}
-
-static int horizontal_line(const Cubic& cubic, Cubic& reduction) {
- double tValues[2];
- reduction[0] = cubic[0];
- reduction[1] = cubic[3];
- int smaller = reduction[1].x > reduction[0].x;
- int larger = smaller ^ 1;
- int roots = SkFindCubicExtrema(cubic[0].x, cubic[1].x, cubic[2].x, cubic[3].x, tValues);
- for (int index = 0; index < roots; ++index) {
- double xExtrema = interp_cubic_coords(&cubic[0].x, tValues[index]);
- if (reduction[smaller].x > xExtrema) {
- reduction[smaller].x = xExtrema;
- continue;
- }
- if (reduction[larger].x < xExtrema) {
- reduction[larger].x = xExtrema;
- }
- }
- return 2;
-}
-
-// check to see if it is a quadratic or a line
-static int check_quadratic(const Cubic& cubic, Cubic& reduction,
- int minX, int maxX, int minY, int maxY) {
- double dx10 = cubic[1].x - cubic[0].x;
- double dx23 = cubic[2].x - cubic[3].x;
- double midX = cubic[0].x + dx10 * 3 / 2;
- if (!approximately_equal(midX - cubic[3].x, dx23 * 3 / 2)) {
- return 0;
- }
- double dy10 = cubic[1].y - cubic[0].y;
- double dy23 = cubic[2].y - cubic[3].y;
- double midY = cubic[0].y + dy10 * 3 / 2;
- if (!approximately_equal(midY - cubic[3].y, dy23 * 3 / 2)) {
- return 0;
- }
- reduction[0] = cubic[0];
- reduction[1].x = midX;
- reduction[1].y = midY;
- reduction[2] = cubic[3];
- return 3;
-}
-
-static int check_linear(const Cubic& cubic, Cubic& reduction,
- int minX, int maxX, int minY, int maxY) {
- int startIndex = 0;
- int endIndex = 3;
- while (cubic[startIndex].approximatelyEqual(cubic[endIndex])) {
- --endIndex;
- if (endIndex == 0) {
- printf("%s shouldn't get here if all four points are about equal", __FUNCTION__);
- assert(0);
- }
- }
- LineParameters lineParameters;
- lineParameters.cubicEndPoints(cubic, startIndex, endIndex);
- double normalSquared = lineParameters.normalSquared();
- double distance[2]; // distance is not normalized
- int mask = other_two(startIndex, endIndex);
- int inner1 = startIndex ^ mask;
- int inner2 = endIndex ^ mask;
- lineParameters.controlPtDistance(cubic, inner1, inner2, distance);
- double limit = normalSquared * SquaredEpsilon;
- int index;
- for (index = 0; index < 2; ++index) {
- double distSq = distance[index];
- distSq *= distSq;
- if (distSq > limit) {
- return 0;
- }
- }
- // four are colinear: return line formed by outside
- reduction[0] = cubic[0];
- reduction[1] = cubic[3];
- int sameSide1;
- int sameSide2;
- bool useX = cubic[maxX].x - cubic[minX].x >= cubic[maxY].y - cubic[minY].y;
- if (useX) {
- sameSide1 = sign(cubic[0].x - cubic[1].x) + sign(cubic[3].x - cubic[1].x);
- sameSide2 = sign(cubic[0].x - cubic[2].x) + sign(cubic[3].x - cubic[2].x);
- } else {
- sameSide1 = sign(cubic[0].y - cubic[1].y) + sign(cubic[3].y - cubic[1].y);
- sameSide2 = sign(cubic[0].y - cubic[2].y) + sign(cubic[3].y - cubic[2].y);
- }
- if (sameSide1 == sameSide2 && (sameSide1 & 3) != 2) {
- return 2;
- }
- double tValues[2];
- int roots;
- if (useX) {
- roots = SkFindCubicExtrema(cubic[0].x, cubic[1].x, cubic[2].x, cubic[3].x, tValues);
- } else {
- roots = SkFindCubicExtrema(cubic[0].y, cubic[1].y, cubic[2].y, cubic[3].y, tValues);
- }
- for (index = 0; index < roots; ++index) {
- _Point extrema;
- extrema.x = interp_cubic_coords(&cubic[0].x, tValues[index]);
- extrema.y = interp_cubic_coords(&cubic[0].y, tValues[index]);
- // sameSide > 0 means mid is smaller than either [0] or [3], so replace smaller
- int replace;
- if (useX) {
- if (extrema.x < cubic[0].x ^ extrema.x < cubic[3].x) {
- continue;
- }
- replace = (extrema.x < cubic[0].x | extrema.x < cubic[3].x)
- ^ cubic[0].x < cubic[3].x;
- } else {
- if (extrema.y < cubic[0].y ^ extrema.y < cubic[3].y) {
- continue;
- }
- replace = (extrema.y < cubic[0].y | extrema.y < cubic[3].y)
- ^ cubic[0].y < cubic[3].y;
- }
- reduction[replace] = extrema;
- }
- return 2;
-}
-
-/* food for thought:
-http://objectmix.com/graphics/132906-fast-precision-driven-cubic-quadratic-piecewise-degree-reduction-algos-2-a.html
-
-Given points c1, c2, c3 and c4 of a cubic Bezier, the points of the
-corresponding quadratic Bezier are (given in convex combinations of
-points):
-
-q1 = (11/13)c1 + (3/13)c2 -(3/13)c3 + (2/13)c4
-q2 = -c1 + (3/2)c2 + (3/2)c3 - c4
-q3 = (2/13)c1 - (3/13)c2 + (3/13)c3 + (11/13)c4
-
-Of course, this curve does not interpolate the end-points, but it would
-be interesting to see the behaviour of such a curve in an applet.
-
---
-Kalle Rutanen
-http://kaba.hilvi.org
-
-*/
-
-// reduce to a quadratic or smaller
-// look for identical points
-// look for all four points in a line
- // note that three points in a line doesn't simplify a cubic
-// look for approximation with single quadratic
- // save approximation with multiple quadratics for later
-int reduceOrder(const Cubic& cubic, Cubic& reduction, ReduceOrder_Flags allowQuadratics) {
- int index, minX, maxX, minY, maxY;
- int minXSet, minYSet;
- minX = maxX = minY = maxY = 0;
- minXSet = minYSet = 0;
- for (index = 1; index < 4; ++index) {
- if (cubic[minX].x > cubic[index].x) {
- minX = index;
- }
- if (cubic[minY].y > cubic[index].y) {
- minY = index;
- }
- if (cubic[maxX].x < cubic[index].x) {
- maxX = index;
- }
- if (cubic[maxY].y < cubic[index].y) {
- maxY = index;
- }
- }
- for (index = 0; index < 4; ++index) {
- if (approximately_equal(cubic[index].x, cubic[minX].x)) {
- minXSet |= 1 << index;
- }
- if (approximately_equal(cubic[index].y, cubic[minY].y)) {
- minYSet |= 1 << index;
- }
- }
- if (minXSet == 0xF) { // test for vertical line
- if (minYSet == 0xF) { // return 1 if all four are coincident
- return coincident_line(cubic, reduction);
- }
- return vertical_line(cubic, reduction);
- }
- if (minYSet == 0xF) { // test for horizontal line
- return horizontal_line(cubic, reduction);
- }
- int result = check_linear(cubic, reduction, minX, maxX, minY, maxY);
- if (result) {
- return result;
- }
- if (allowQuadratics && (result = check_quadratic(cubic, reduction, minX, maxX, minY, maxY))) {
- return result;
- }
- memcpy(reduction, cubic, sizeof(Cubic));
- return 4;
-}
diff --git a/experimental/Intersection/ReduceOrder_Test.cpp b/experimental/Intersection/ReduceOrder_Test.cpp
deleted file mode 100644
index e213015bad..0000000000
--- a/experimental/Intersection/ReduceOrder_Test.cpp
+++ /dev/null
@@ -1,138 +0,0 @@
-#include "CubicIntersection.h"
-#include "CubicIntersection_TestData.h"
-#include "CubicIntersection_Tests.h"
-#include "QuadraticIntersection_TestData.h"
-#include "TestUtilities.h"
-
-void ReduceOrder_Test() {
- size_t index;
- Cubic reduce;
- int order;
- enum {
- RunAll,
- RunPointDegenerates,
- RunNotPointDegenerates,
- RunLines,
- RunNotLines,
- RunModEpsilonLines,
- RunLessEpsilonLines,
- RunNegEpsilonLines,
- RunQuadraticLines,
- RunQuadraticModLines,
- RunComputedLines,
- RunNone
- } run = RunAll;
- int firstTestIndex = 0;
-#if 0
- run = RunComputedLines;
- firstTestIndex = 18;
-#endif
- int firstPointDegeneratesTest = run == RunAll ? 0 : run == RunPointDegenerates ? firstTestIndex : INT_MAX;
- int firstNotPointDegeneratesTest = run == RunAll ? 0 : run == RunNotPointDegenerates ? firstTestIndex : INT_MAX;
- int firstLinesTest = run == RunAll ? 0 : run == RunLines ? firstTestIndex : INT_MAX;
- int firstNotLinesTest = run == RunAll ? 0 : run == RunNotLines ? firstTestIndex : INT_MAX;
- int firstModEpsilonTest = run == RunAll ? 0 : run == RunModEpsilonLines ? firstTestIndex : INT_MAX;
- int firstLessEpsilonTest = run == RunAll ? 0 : run == RunLessEpsilonLines ? firstTestIndex : INT_MAX;
- int firstNegEpsilonTest = run == RunAll ? 0 : run == RunNegEpsilonLines ? firstTestIndex : INT_MAX;
- int firstQuadraticLineTest = run == RunAll ? 0 : run == RunQuadraticLines ? firstTestIndex : INT_MAX;
- int firstQuadraticModLineTest = run == RunAll ? 0 : run == RunQuadraticModLines ? firstTestIndex : INT_MAX;
- int firstComputedLinesTest = run == RunAll ? 0 : run == RunComputedLines ? firstTestIndex : INT_MAX;
-
- for (index = firstPointDegeneratesTest; index < pointDegenerates_count; ++index) {
- const Cubic& cubic = pointDegenerates[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 1) {
- printf("[%d] pointDegenerates order=%d\n", (int) index, order);
- }
- }
- for (index = firstNotPointDegeneratesTest; index < notPointDegenerates_count; ++index) {
- const Cubic& cubic = notPointDegenerates[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order == 1) {
- printf("[%d] notPointDegenerates order=%d\n", (int) index, order);
- }
- }
- for (index = firstLinesTest; index < lines_count; ++index) {
- const Cubic& cubic = lines[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 2) {
- printf("[%d] lines order=%d\n", (int) index, order);
- }
- }
- for (index = firstNotLinesTest; index < notLines_count; ++index) {
- const Cubic& cubic = notLines[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order == 2) {
- printf("[%d] notLines order=%d\n", (int) index, order);
- }
- }
- for (index = firstModEpsilonTest; index < modEpsilonLines_count; ++index) {
- const Cubic& cubic = modEpsilonLines[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order == 2) {
- printf("[%d] line mod by epsilon order=%d\n", (int) index, order);
- }
- }
- for (index = firstLessEpsilonTest; index < lessEpsilonLines_count; ++index) {
- const Cubic& cubic = lessEpsilonLines[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 2) {
- printf("[%d] line less by epsilon/2 order=%d\n", (int) index, order);
- }
- }
- for (index = firstNegEpsilonTest; index < negEpsilonLines_count; ++index) {
- const Cubic& cubic = negEpsilonLines[index];
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 2) {
- printf("[%d] line neg by epsilon/2 order=%d\n", (int) index, order);
- }
- }
- for (index = firstQuadraticLineTest; index < quadraticLines_count; ++index) {
- const Quadratic& quad = quadraticLines[index];
- Cubic cubic;
- quad_to_cubic(quad, cubic);
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 2) {
- printf("[%d] line quad order=%d\n", (int) index, order);
- }
- }
- for (index = firstQuadraticModLineTest; index < quadraticModEpsilonLines_count; ++index) {
- const Quadratic& quad = quadraticModEpsilonLines[index];
- Cubic cubic;
- quad_to_cubic(quad, cubic);
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (order != 3) {
- printf("[%d] line mod quad order=%d\n", (int) index, order);
- }
- }
-
- // test if computed line end points are valid
- for (index = firstComputedLinesTest; index < lines_count; ++index) {
- const Cubic& cubic = lines[index];
- bool controlsInside = controls_inside(cubic);
- order = reduceOrder(cubic, reduce, kReduceOrder_QuadraticsAllowed);
- if (reduce[0].x == reduce[1].x && reduce[0].y == reduce[1].y) {
- printf("[%d] line computed ends match order=%d\n", (int) index, order);
- }
- if (controlsInside) {
- if ( reduce[0].x != cubic[0].x && reduce[0].x != cubic[3].x
- || reduce[0].y != cubic[0].y && reduce[0].y != cubic[3].y
- || reduce[1].x != cubic[0].x && reduce[1].x != cubic[3].x
- || reduce[1].y != cubic[0].y && reduce[1].y != cubic[3].y) {
- printf("[%d] line computed ends order=%d\n", (int) index, order);
- }
- } else {
- // binary search for extrema, compare against actual results
- // while a control point is outside of bounding box formed by end points, split
- _Rect bounds = {DBL_MAX, DBL_MAX, -DBL_MAX, -DBL_MAX};
- find_tight_bounds(cubic, bounds);
- if ( !approximately_equal(reduce[0].x, bounds.left) && !approximately_equal(reduce[0].x, bounds.right)
- || !approximately_equal(reduce[0].y, bounds.top) && !approximately_equal(reduce[0].y, bounds.bottom)
- || !approximately_equal(reduce[1].x, bounds.left) && !approximately_equal(reduce[1].x, bounds.right)
- || !approximately_equal(reduce[1].y, bounds.top) && !approximately_equal(reduce[1].y, bounds.bottom)) {
- printf("[%d] line computed tight bounds order=%d\n", (int) index, order);
- }
-
- }
- }
-}
diff --git a/experimental/Intersection/ShapeOps.h b/experimental/Intersection/ShapeOps.h
new file mode 100644
index 0000000000..d532e872dc
--- /dev/null
+++ b/experimental/Intersection/ShapeOps.h
@@ -0,0 +1,6 @@
+#include "SkPath.h"
+
+void contourBounds(const SkPath& path, SkTDArray<SkRect>& boundsArray);
+void simplify(const SkPath& path, bool asFill, SkPath& simple);
+
+extern const bool gShowDebugf; // FIXME: remove once debugging is complete \ No newline at end of file
diff --git a/experimental/Intersection/ShapeOpsDemo-Info.plist b/experimental/Intersection/ShapeOpsDemo-Info.plist
new file mode 100644
index 0000000000..5dd4506c0e
--- /dev/null
+++ b/experimental/Intersection/ShapeOpsDemo-Info.plist
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+ <key>CFBundleDevelopmentRegion</key>
+ <string>English</string>
+ <key>CFBundleExecutable</key>
+ <string>${EXECUTABLE_NAME}</string>
+ <key>CFBundleIconFile</key>
+ <string></string>
+ <key>CFBundleIdentifier</key>
+ <string>com.googlecode.skia.${PRODUCT_NAME:rfc1034identifier}</string>
+ <key>CFBundleInfoDictionaryVersion</key>
+ <string>6.0</string>
+ <key>CFBundleName</key>
+ <string>${PRODUCT_NAME}</string>
+ <key>CFBundlePackageType</key>
+ <string>APPL</string>
+ <key>CFBundleShortVersionString</key>
+ <string>1.0</string>
+ <key>CFBundleSignature</key>
+ <string>????</string>
+ <key>CFBundleVersion</key>
+ <string>1</string>
+ <key>LSMinimumSystemVersion</key>
+ <string>${MACOSX_DEPLOYMENT_TARGET}</string>
+ <key>NSMainNibFile</key>
+ <string>ShapeOpsDemo</string>
+ <key>NSPrincipalClass</key>
+ <string>NSApplication</string>
+</dict>
+</plist>
diff --git a/experimental/Intersection/ShapeOpsDemo.cpp b/experimental/Intersection/ShapeOpsDemo.cpp
new file mode 100644
index 0000000000..a2690ea42a
--- /dev/null
+++ b/experimental/Intersection/ShapeOpsDemo.cpp
@@ -0,0 +1,110 @@
+#include "EdgeWalker_Test.h"
+#include "ShapeOps.h"
+#include "SkApplication.h"
+#include "SkCanvas.h"
+#include "SkEvent.h"
+#include "SkGraphics.h"
+#include "SkPaint.h"
+
+SkCanvas* canvas = 0;
+SkBitmap* bitmap;
+
+static bool test15(SkCanvas* canvas) {
+ // Three circles bounce inside a rectangle. The circles describe three, four
+ // or five points which in turn describe a polygon. The polygon points
+ // bounce inside the circles. The circles rotate and scale over time. The
+ // polygons are combined into a single path, simplified, and stroked.
+ static int step = 0;
+ const int circles = 3;
+ int scales[circles];
+ int angles[circles];
+ int locs[circles * 2];
+ int pts[circles * 2 * 4];
+ int c, p;
+ for (c = 0; c < circles; ++c) {
+ scales[c] = abs(10 - (step + c * 4) % 21);
+ angles[c] = (step + c * 6) % 600;
+ locs[c * 2] = abs(130 - (step + c * 9) % 261);
+ locs[c * 2 + 1] = abs(170 - (step + c * 11) % 341);
+ for (p = 0; p < 4; ++p) {
+ pts[c * 8 + p * 2] = abs(90 - ((step + c * 121 + p * 13) % 190));
+ pts[c * 8 + p * 2 + 1] = abs(110 - ((step + c * 223 + p * 17) % 230));
+ }
+ }
+ SkPath path, out;
+ for (c = 0; c < circles; ++c) {
+ for (p = 0; p < 4; ++p) {
+ SkScalar x = pts[c * 8 + p * 2];
+ SkScalar y = pts[c * 8 + p * 2 + 1];
+ x *= 3 + scales[c] / 10.0f;
+ y *= 3 + scales[c] / 10.0f;
+ SkScalar angle = angles[c] * 3.1415f * 2 / 600;
+ SkScalar temp = x * cos(angle) - y * sin(angle);
+ y = x * sin(angle) + y * cos(angle);
+ x = temp;
+ x += locs[c * 2] * 200 / 130.0f;
+ y += locs[c * 2 + 1] * 200 / 170.0f;
+ x += 50;
+ // y += 200;
+ if (p == 0) {
+ path.moveTo(x, y);
+ } else {
+ path.lineTo(x, y);
+ }
+ }
+ path.close();
+ }
+ showPath(path, "original:");
+ simplify(path, true, out);
+ showPath(out, "simplified:");
+ SkPaint paint;
+ paint.setAntiAlias(true);
+ paint.setStyle(SkPaint::kStroke_Style);
+ paint.setStrokeWidth(3);
+ paint.setColor(0x3F007fbF);
+ canvas->drawPath(path, paint);
+ paint.setColor(0xFF60FF00);
+ paint.setStrokeWidth(1);
+ canvas->drawPath(out, paint);
+ ++step;
+ return true;
+}
+
+static bool (*tests[])(SkCanvas* ) = {
+ test15,
+};
+
+static size_t testsCount = sizeof(tests) / sizeof(tests[0]);
+
+static bool (*firstTest)(SkCanvas*) = test15;
+
+extern "C" void* getPixels(bool* animate);
+extern "C" void unlockPixels();
+
+extern "C" void* getPixels(bool* animate) {
+ if (!canvas) {
+ canvas = new SkCanvas();
+ bitmap = new SkBitmap();
+ SkBitmap::Config config = SkBitmap::kARGB_8888_Config;
+
+ bitmap->setConfig(config, 1100, 630);
+ bitmap->allocPixels();
+ bitmap->setIsOpaque(true);
+ canvas->setBitmapDevice(*bitmap);
+ }
+ canvas->drawColor(SK_ColorWHITE);
+ size_t index = 0;
+ if (index == 0 && firstTest) {
+ while (index < testsCount && tests[index] != firstTest) {
+ ++index;
+ }
+ }
+ *animate = (tests[index])(canvas);
+ bitmap->lockPixels();
+ return bitmap->getPixels();
+}
+
+extern "C" void unlockPixels() {
+ bitmap->unlockPixels();
+}
+
diff --git a/experimental/Intersection/TSearch.h b/experimental/Intersection/TSearch.h
index e4c4e95c38..e963373d3a 100644
--- a/experimental/Intersection/TSearch.h
+++ b/experimental/Intersection/TSearch.h
@@ -1,3 +1,6 @@
+#ifndef TSearch_DEFINED
+#define TSearch_DEFINED
+
#include "SkTypes.h"
// FIXME: Move this templated version into SKTSearch.h
@@ -61,3 +64,5 @@ void QSort(S& context, T* left, T* right,
QSort(context, left, pivot - 1, lessThan);
QSort(context, pivot + 1, right, lessThan);
}
+
+#endif
diff --git a/experimental/Intersection/edge.xcodeproj/project.pbxproj b/experimental/Intersection/edge.xcodeproj/project.pbxproj
index 0cd951e386..c91ac45f78 100644
--- a/experimental/Intersection/edge.xcodeproj/project.pbxproj
+++ b/experimental/Intersection/edge.xcodeproj/project.pbxproj
@@ -29,6 +29,8 @@
FE99AE40151B4ED10072AA0D /* tempskinny4.txt in Resources */ = {isa = PBXBuildFile; fileRef = FE99AE3F151B4ED10072AA0D /* tempskinny4.txt */; };
FE99AE44151B4EE70072AA0D /* xtempskinny4.txt in Resources */ = {isa = PBXBuildFile; fileRef = FE99AE43151B4EE70072AA0D /* xtempskinny4.txt */; };
FE99AEBE151B64ED0072AA0D /* op.htm in Resources */ = {isa = PBXBuildFile; fileRef = FE99AEBD151B64ED0072AA0D /* op.htm */; };
+ FE99AF2B151CC0AA0072AA0D /* ActiveEdge_Test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FE99AF2A151CC0AA0072AA0D /* ActiveEdge_Test.cpp */; };
+ FE99B13215209E300072AA0D /* EdgeWalkerPolygon4x4_Test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FE99B13115209E300072AA0D /* EdgeWalkerPolygon4x4_Test.cpp */; };
FEA5F4E21498000C005052F9 /* libports.a in Frameworks */ = {isa = PBXBuildFile; fileRef = FEA5F4E11497FFF6005052F9 /* libports.a */; };
FEA61B0014EF589900B736CB /* libanimator.a in Frameworks */ = {isa = PBXBuildFile; fileRef = FEED7268144DD3EA0059E97B /* libanimator.a */; };
FEA61B2C14F2AF6600B736CB /* EdgeWalkerRectangles_Test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FEA61B2B14F2AF6600B736CB /* EdgeWalkerRectangles_Test.cpp */; };
@@ -264,6 +266,8 @@
FE99AE3F151B4ED10072AA0D /* tempskinny4.txt */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = tempskinny4.txt; sourceTree = "<group>"; };
FE99AE43151B4EE70072AA0D /* xtempskinny4.txt */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = xtempskinny4.txt; sourceTree = "<group>"; };
FE99AEBD151B64ED0072AA0D /* op.htm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.html; path = op.htm; sourceTree = "<group>"; };
+ FE99AF2A151CC0AA0072AA0D /* ActiveEdge_Test.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ActiveEdge_Test.cpp; sourceTree = "<group>"; };
+ FE99B13115209E300072AA0D /* EdgeWalkerPolygon4x4_Test.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EdgeWalkerPolygon4x4_Test.cpp; sourceTree = "<group>"; };
FEA5F4D91497FFF6005052F9 /* ports.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = ports.xcodeproj; path = ../../out/gyp/ports.xcodeproj; sourceTree = SOURCE_ROOT; };
FEA61B2B14F2AF6600B736CB /* EdgeWalkerRectangles_Test.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = EdgeWalkerRectangles_Test.cpp; sourceTree = "<group>"; };
FEA670F013C49E2200FE6FC1 /* SkAntiEdge.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SkAntiEdge.cpp; sourceTree = "<group>"; };
@@ -525,6 +529,7 @@
FEC123A5149001540086BF1F /* Tests */ = {
isa = PBXGroup;
children = (
+ FE99AF2A151CC0AA0072AA0D /* ActiveEdge_Test.cpp */,
FEED76C0144F3E7F0059E97B /* ConvexHull_Test.cpp */,
FEC117CB14843B0A0086BF1F /* CubicBezierClip_Test.cpp */,
FEED7689144F2E7D0059E97B /* CubicIntersection_Test.cpp */,
@@ -533,8 +538,12 @@
FECA9A5914B3B09100B35E2C /* CubicParameterization_Test.cpp */,
FECAAB7F14BDFAFD00B35E2C /* CubicParameterization_TestUtility.cpp */,
FEED7625144F22E20059E97B /* CubicReduceOrder_Test.cpp */,
+ FE7413DB14F6926D00056D7B /* EdgeWalker_Test.h */,
FE7413D714F691C200056D7B /* EdgeWalker_TestUtility.cpp */,
FE7413D314F6915A00056D7B /* EdgeWalkerPolygons_Test.cpp */,
+ FE99B13115209E300072AA0D /* EdgeWalkerPolygon4x4_Test.cpp */,
+ FED866D615066642006F4508 /* EdgeWalkerPolygons_Mismatches.cpp */,
+ FED865F815056A79006F4508 /* EdgeWalkerQuadralaterals_Test.cpp */,
FEA61B2B14F2AF6600B736CB /* EdgeWalkerRectangles_Test.cpp */,
FED53C381483CB9400F6359E /* Inline_Tests.cpp */,
FEED7680144F2E480059E97B /* Intersection_Tests.h */,
@@ -553,9 +562,6 @@
FECAA6E014BDDF2D00B35E2C /* QuadraticReduceOrder_Test.cpp */,
FEED7673144F2D770059E97B /* TestUtilities.h */,
FEED764B144F29BD0059E97B /* TestUtilities.cpp */,
- FE7413DB14F6926D00056D7B /* EdgeWalker_Test.h */,
- FED865F815056A79006F4508 /* EdgeWalkerQuadralaterals_Test.cpp */,
- FED866D615066642006F4508 /* EdgeWalkerPolygons_Mismatches.cpp */,
);
name = Tests;
sourceTree = "<group>";
@@ -974,6 +980,8 @@
FE7413D814F691C200056D7B /* EdgeWalker_TestUtility.cpp in Sources */,
FED865F915056A79006F4508 /* EdgeWalkerQuadralaterals_Test.cpp in Sources */,
FED866D715066642006F4508 /* EdgeWalkerPolygons_Mismatches.cpp in Sources */,
+ FE99AF2B151CC0AA0072AA0D /* ActiveEdge_Test.cpp in Sources */,
+ FE99B13215209E300072AA0D /* EdgeWalkerPolygon4x4_Test.cpp in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -1025,92 +1033,77 @@
C01FCF4B08A954540054247B /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
- COPY_PHASE_STRIP = NO;
- GCC_DYNAMIC_NO_PIC = NO;
- GCC_ENABLE_FIX_AND_CONTINUE = YES;
- GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
+ CLANG_WARN_CXX0X_EXTENSIONS = NO;
GCC_OPTIMIZATION_LEVEL = 0;
- GCC_PRECOMPILE_PREFIX_HEADER = YES;
- GCC_PREFIX_HEADER = edge_Prefix.pch;
- GCC_WARN_ABOUT_RETURN_TYPE = YES;
- GCC_WARN_UNUSED_VARIABLE = YES;
INFOPLIST_FILE = "edge-Info.plist";
- INSTALL_PATH = "$(HOME)/Applications";
- LIBRARY_SEARCH_PATHS = "$(inherited)";
- PREBINDING = NO;
+ LIBRARY_SEARCH_PATHS = "$(SDKROOT)/System/Library/Frameworks";
PRODUCT_NAME = edge;
- SKIP_INSTALL = YES;
- WRAPPER_EXTENSION = app;
- ZERO_LINK = YES;
+ SDKROOT = macosx10.6;
+ SYMROOT = ../xcodebuild;
+ WRAPPER_PREFIX = "";
};
name = Debug;
};
C01FCF4C08A954540054247B /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
- ALWAYS_SEARCH_USER_PATHS = NO;
- DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
- GCC_MODEL_TUNING = G5;
- GCC_PRECOMPILE_PREFIX_HEADER = YES;
- GCC_PREFIX_HEADER = edge_Prefix.pch;
+ CLANG_WARN_CXX0X_EXTENSIONS = NO;
+ GCC_OPTIMIZATION_LEVEL = 3;
INFOPLIST_FILE = "edge-Info.plist";
- INSTALL_PATH = "$(HOME)/Applications";
- LIBRARY_SEARCH_PATHS = "$(inherited)";
+ LIBRARY_SEARCH_PATHS = "$(SDKROOT)/System/Library/Frameworks";
PRODUCT_NAME = edge;
+ SDKROOT = macosx10.6;
+ SYMROOT = ../xcodebuild;
+ WRAPPER_PREFIX = "";
};
name = Release;
};
C01FCF4F08A954540054247B /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
- GCC_ENABLE_CPP_EXCEPTIONS = YES;
- GCC_ENABLE_CPP_RTTI = YES;
- GCC_ENABLE_SYMBOL_SEPARATION = YES;
- GCC_MODEL_TUNING = G4;
GCC_PREPROCESSOR_DEFINITIONS = (
- SK_BUILD_FOR_MAC,
- SK_DEBUG,
+ "\"SK_SCALAR_IS_FLOAT\"",
+ "\"SK_CAN_USE_FLOAT\"",
+ "\"SK_BUILD_FOR_MAC\"",
+ "\"SK_USE_POSIX_THREADS\"",
+ "\"GR_MAC_BUILD=1\"",
+ "\"SK_SUPPORT_PDF\"",
+ "\"SK_DEBUG\"",
+ "\"GR_DEBUG=1\"",
+ );
+ HEADER_SEARCH_PATHS = (
+ ../../gpu/include,
+ ../../src/core,
+ "../../include/**",
+ ../../gm,
);
- GCC_SYMBOLS_PRIVATE_EXTERN = NO;
- GCC_THREADSAFE_STATICS = YES;
- GCC_TREAT_IMPLICIT_FUNCTION_DECLARATIONS_AS_ERRORS = YES;
- GCC_WARN_64_TO_32_BIT_CONVERSION = NO;
- GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
- GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
- GCC_WARN_ABOUT_RETURN_TYPE = YES;
- GCC_WARN_CHECK_SWITCH_STATEMENTS = YES;
- GCC_WARN_FOUR_CHARACTER_CONSTANTS = YES;
- GCC_WARN_HIDDEN_VIRTUAL_FUNCTIONS = YES;
- GCC_WARN_INHIBIT_ALL_WARNINGS = NO;
- GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
- GCC_WARN_MISSING_PARENTHESES = YES;
- GCC_WARN_PROTOTYPE_CONVERSION = YES;
- GCC_WARN_SIGN_COMPARE = YES;
- GCC_WARN_UNKNOWN_PRAGMAS = YES;
- GCC_WARN_UNUSED_FUNCTION = YES;
- GCC_WARN_UNUSED_LABEL = YES;
- GCC_WARN_UNUSED_VALUE = YES;
- GCC_WARN_UNUSED_VARIABLE = YES;
- HEADER_SEARCH_PATHS = "";
- INFOPLIST_PREPROCESS = YES;
- LD_RUNPATH_SEARCH_PATHS = "";
- LIBRARY_SEARCH_PATHS = "";
- OTHER_LDFLAGS = "";
- PREBINDING = YES;
- PRECOMPS_INCLUDE_HEADERS_FROM_BUILT_PRODUCTS_DIR = YES;
- SDKROOT = "";
- USER_HEADER_SEARCH_PATHS = "../../gpu/include ../../src/core ../../include/** ../../gm";
+ INTERMEDIATE_DIR = "$(PROJECT_DERIVED_FILE_DIR)/$(CONFIGURATION)";
+ SHARED_INTERMEDIATE_DIR = "$(SYMROOT)/DerivedSources/$(CONFIGURATION)";
};
name = Debug;
};
C01FCF5008A954540054247B /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
- GCC_C_LANGUAGE_STANDARD = gnu99;
- GCC_WARN_ABOUT_RETURN_TYPE = YES;
- GCC_WARN_UNUSED_VARIABLE = YES;
- PREBINDING = NO;
- SDKROOT = macosx10.6;
+ GCC_PREPROCESSOR_DEFINITIONS = (
+ "\"SK_SCALAR_IS_FLOAT\"",
+ "\"SK_CAN_USE_FLOAT\"",
+ "\"SK_BUILD_FOR_MAC\"",
+ "\"SK_USE_POSIX_THREADS\"",
+ "\"GR_MAC_BUILD=1\"",
+ "\"SK_SUPPORT_PDF\"",
+ "\"SK_RELEASE\"",
+ "\"GR_RELEASE=1\"",
+ "\"NDEBUG\"",
+ );
+ HEADER_SEARCH_PATHS = (
+ ../../gpu/include,
+ ../../src/core,
+ "../../include/**",
+ ../../gm,
+ );
+ INTERMEDIATE_DIR = "$(PROJECT_DERIVED_FILE_DIR)/$(CONFIGURATION)";
+ SHARED_INTERMEDIATE_DIR = "$(SYMROOT)/DerivedSources/$(CONFIGURATION)";
};
name = Release;
};
diff --git a/experimental/Intersection/op.htm b/experimental/Intersection/op.htm
index dcfb654c35..bd2bff0fee 100644
--- a/experimental/Intersection/op.htm
+++ b/experimental/Intersection/op.htm
@@ -15,11 +15,65 @@ path.lineTo(280.861267, 299.881470);
path.lineTo(43.485352, 308.984497);
path.close();
</div>
+<div id="test_2div">
+path.moveTo(-177.878387, 265.368988);
+path.lineTo(-254.415771, 303.709961);
+path.lineTo(-317.465363, 271.325562);
+path.lineTo(-374.520386, 207.507660);
+path.lineTo(-177.878387, 265.368988);
+path.close();
+path.moveTo(-63.582489, -3.679123);
+path.lineTo(-134.496841, 26.434566);
+path.lineTo(-205.411209, 56.548256);
+path.lineTo(-276.325562, 86.661942);
+path.lineTo(-63.582489, -3.679123);
+path.close();
+path.moveTo(-57.078423, 162.633453);
+path.lineTo(-95.963928, 106.261139);
+path.lineTo(-134.849457, 49.888824);
+path.lineTo(-173.734955, -6.483480);
+path.lineTo(-57.078423, 162.633453);
+path.close();
+</div>
+<div id="test_3div">
+path.moveTo(98.666489, -94.295059);
+path.lineTo(156.584320, -61.939133);
+path.lineTo(174.672974, -12.343765);
+path.lineTo(158.622345, 52.028267);
+path.lineTo(98.666489, -94.295059);
+path.close();
+path.moveTo(-133.225616, -48.622055);
+path.lineTo(-73.855499, -10.375397);
+path.lineTo(-14.485367, 27.871277);
+path.lineTo(44.884750, 66.117935);
+path.lineTo(-133.225616, -48.622055);
+path.close();
+path.moveTo( 9.030045, -163.413132);
+path.lineTo(-19.605331, -89.588760);
+path.lineTo(-48.240707, -15.764404);
+path.lineTo(-76.876053, 58.059944);
+path.lineTo( 9.030045, -163.413132);
+path.close();
+</div>
+<div id="test_4div">
+path.moveTo( -5503.40843,1749.49658);
+path.lineTo(-5503.40843,1749.49718);
+path.close();
+path.moveTo( -5503.40843,1749.49658);
+path.lineTo(-5503.40729,1749.50314);
+path.close();
+path.moveTo( -5503.40729,1749.50314);
+path.lineTo(-5503.40729,1749.50361);
+path.close();
+</div>
</div>
<script type="text/javascript">
var testDivs = [
+ test_4div,
+ test_3div,
+ test_2div,
test_1div,
];
@@ -37,7 +91,7 @@ var ctx;
function parse(test) {
var contours = [];
var contourStrs = test.split("path.close();");
- var pattern = /\d+\.*\d*/g;
+ var pattern = /-?\d+\.*\d*/g;
for (var c in contourStrs) {
var points = contourStrs[c].match(pattern);
var pts = [];
@@ -82,7 +136,7 @@ function init(test) {
}
function drawPoint(px, py, xoffset, yoffset, unit) {
- var label = px + "=" + px.toFixed(3) + ", " + py + "=" + py.toFixed(3);
+ var label = px.toFixed(3) + ", " + py.toFixed(3);
var _px = px * unit + xoffset;
var _py = py * unit + yoffset;
ctx.beginPath();