1282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski/* 2282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Copyright (C) 2010 The Android Open Source Project 3282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 4282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Licensed under the Apache License, Version 2.0 (the "License"); 5282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * you may not use this file except in compliance with the License. 6282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * You may obtain a copy of the License at 7282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 8282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * http://www.apache.org/licenses/LICENSE-2.0 9282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 10282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Unless required by applicable law or agreed to in writing, software 11282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * distributed under the License is distributed on an "AS IS" BASIS, 12282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * See the License for the specific language governing permissions and 14282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * limitations under the License. 15282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski */ 16282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 17282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskipackage android.graphics; 18282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 19282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskiimport com.android.ide.common.rendering.api.LayoutLog; 20282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskiimport com.android.layoutlib.bridge.Bridge; 21282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskiimport com.android.layoutlib.bridge.impl.DelegateManager; 22282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskiimport com.android.tools.layoutlib.annotations.LayoutlibDelegate; 23282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 24282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskiimport android.graphics.Shader.TileMode; 25282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 26e5be1d7a397db08a4dd75c66bdbbc6e2b61baaa8Diego Perezimport java.awt.image.ColorModel; 27e5be1d7a397db08a4dd75c66bdbbc6e2b61baaa8Diego Perez 28282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski/** 29282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Delegate implementing the native methods of android.graphics.LinearGradient 30282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 31282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Through the layoutlib_create tool, the original native methods of LinearGradient have been 32282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * replaced by calls to methods of the same name in this delegate class. 33282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 34282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * This class behaves like the original native implementation, but in Java, keeping previously 35282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * native data into its own objects and mapping them to int that are sent back and forth between 36282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * it and the original LinearGradient class. 37282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 38282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Because this extends {@link Shader_Delegate}, there's no need to use a {@link DelegateManager}, 39282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * as all the Shader classes will be added to the manager owned by {@link Shader_Delegate}. 40282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 41282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @see Shader_Delegate 42282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 43282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski */ 44282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinskipublic final class LinearGradient_Delegate extends Gradient_Delegate { 45282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 46282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // ---- delegate data ---- 47282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private java.awt.Paint mJavaPaint; 48282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 49282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // ---- Public Helper methods ---- 50282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 51282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @Override 52282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public java.awt.Paint getJavaPaint() { 53282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return mJavaPaint; 54282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 55282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 56282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // ---- native methods ---- 57282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 58282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @LayoutlibDelegate 59afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard /*package*/ static long nativeCreate1(LinearGradient thisGradient, long matrix, 60282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float x0, float y0, float x1, float y1, 61282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski int colors[], float positions[], int tileMode) { 62afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard LinearGradient_Delegate newDelegate = new LinearGradient_Delegate(matrix, x0, y0, 63afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard x1, y1, colors, positions, Shader_Delegate.getTileMode(tileMode)); 64282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return sManager.addNewDelegate(newDelegate); 65282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 66282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 67282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @LayoutlibDelegate 68afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard /*package*/ static long nativeCreate2(LinearGradient thisGradient, long matrix, 69282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float x0, float y0, float x1, float y1, 70282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski int color0, int color1, int tileMode) { 71afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard return nativeCreate1(thisGradient, matrix, x0, y0, x1, y1, new int[] { color0, color1}, 72afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard null /*positions*/, tileMode); 73282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 74282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 75282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // ---- Private delegate/helper methods ---- 76282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 77282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski /** 78282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Create a shader that draws a linear gradient along a line. 79282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * 80afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard * @param nativeMatrix reference to the shader's native transformation matrix 81282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param x0 The x-coordinate for the start of the gradient line 82282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param y0 The y-coordinate for the start of the gradient line 83282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param x1 The x-coordinate for the end of the gradient line 84282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param y1 The y-coordinate for the end of the gradient line 85282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param colors The colors to be distributed along the gradient line 86282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param positions May be null. The relative positions [0..1] of each 87282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * corresponding color in the colors array. If this is null, the 88282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * the colors are distributed evenly along the gradient line. 89282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * @param tile The Shader tiling mode 90282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski */ 91afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard private LinearGradient_Delegate(long nativeMatrix, float x0, float y0, float x1, 92afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard float y1, int colors[], float positions[], TileMode tile) { 93afac7771f403eabc4a67b1d3ffdeeec1ed53794bJerome Gaillard super(nativeMatrix, colors, positions); 94282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mJavaPaint = new LinearGradientPaint(x0, y0, x1, y1, mColors, mPositions, tile); 95282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 96282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 97282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // ---- Custom Java Paint ---- 98282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski /** 99282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Linear Gradient (Java) Paint able to handle more than 2 points, as 100282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * {@link java.awt.GradientPaint} only supports 2 points and does not support Android's tile 101282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * modes. 102282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski */ 103282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private class LinearGradientPaint extends GradientPaint { 104282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 105282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final float mX0; 106282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final float mY0; 107282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final float mDx; 108282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final float mDy; 109282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final float mDSize2; 110282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 111282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public LinearGradientPaint(float x0, float y0, float x1, float y1, int colors[], 112282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float positions[], TileMode tile) { 113282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski super(colors, positions, tile); 114282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mX0 = x0; 115282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mY0 = y0; 116282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mDx = x1 - x0; 117282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mDy = y1 - y0; 118282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mDSize2 = mDx * mDx + mDy * mDy; 119282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 120282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 121282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @Override 122282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public java.awt.PaintContext createContext( 123282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.image.ColorModel colorModel, 124282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.Rectangle deviceBounds, 125282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.Rectangle2D userBounds, 126282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.AffineTransform xform, 127282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.RenderingHints hints) { 128282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski precomputeGradientColors(); 129282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 130282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.AffineTransform canvasMatrix; 131282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski try { 132282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski canvasMatrix = xform.createInverse(); 133282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } catch (java.awt.geom.NoninvertibleTransformException e) { 134282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski Bridge.getLog().fidelityWarning(LayoutLog.TAG_MATRIX_INVERSE, 135282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski "Unable to inverse matrix in LinearGradient", e, null /*data*/); 136282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski canvasMatrix = new java.awt.geom.AffineTransform(); 137282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 138282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 139282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.AffineTransform localMatrix = getLocalMatrix(); 140282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski try { 141282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski localMatrix = localMatrix.createInverse(); 142282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } catch (java.awt.geom.NoninvertibleTransformException e) { 143282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski Bridge.getLog().fidelityWarning(LayoutLog.TAG_MATRIX_INVERSE, 144282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski "Unable to inverse matrix in LinearGradient", e, null /*data*/); 145282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski localMatrix = new java.awt.geom.AffineTransform(); 146282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 147282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 148282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return new LinearGradientPaintContext(canvasMatrix, localMatrix, colorModel); 149282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 150282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 151282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private class LinearGradientPaintContext implements java.awt.PaintContext { 152282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 153282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final java.awt.geom.AffineTransform mCanvasMatrix; 154282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final java.awt.geom.AffineTransform mLocalMatrix; 155282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private final java.awt.image.ColorModel mColorModel; 156282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 157282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private LinearGradientPaintContext( 158282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.AffineTransform canvasMatrix, 159282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.geom.AffineTransform localMatrix, 160282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski java.awt.image.ColorModel colorModel) { 161282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mCanvasMatrix = canvasMatrix; 162282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mLocalMatrix = localMatrix; 163e5be1d7a397db08a4dd75c66bdbbc6e2b61baaa8Diego Perez mColorModel = colorModel.hasAlpha() ? colorModel : ColorModel.getRGBdefault(); 164282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 165282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 166282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @Override 167282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public void dispose() { 168282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 169282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 170282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @Override 171282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public java.awt.image.ColorModel getColorModel() { 172282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return mColorModel; 173282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 174282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 175282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski @Override 176282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski public java.awt.image.Raster getRaster(int x, int y, int w, int h) { 1772d3449f982f9f4b9f4370142bb846d2dbab5a38eDiego Perez java.awt.image.BufferedImage image = new java.awt.image.BufferedImage( 1782d3449f982f9f4b9f4370142bb846d2dbab5a38eDiego Perez mColorModel, mColorModel.createCompatibleWritableRaster(w, h), 1792d3449f982f9f4b9f4370142bb846d2dbab5a38eDiego Perez mColorModel.isAlphaPremultiplied(), null); 180282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 181282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski int[] data = new int[w*h]; 182282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 183282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski int index = 0; 184282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float[] pt1 = new float[2]; 185282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float[] pt2 = new float[2]; 186282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski for (int iy = 0 ; iy < h ; iy++) { 187282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski for (int ix = 0 ; ix < w ; ix++) { 188282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // handle the canvas transform 189282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pt1[0] = x + ix; 190282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pt1[1] = y + iy; 191282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mCanvasMatrix.transform(pt1, 0, pt2, 0, 1); 192282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 193282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // handle the local matrix. 194282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pt1[0] = pt2[0]; 195282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pt1[1] = pt2[1]; 196282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski mLocalMatrix.transform(pt1, 0, pt2, 0, 1); 197282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 198282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski data[index++] = getColor(pt2[0], pt2[1]); 199282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 200282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 201282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 202282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski image.setRGB(0 /*startX*/, 0 /*startY*/, w, h, data, 0 /*offset*/, w /*scansize*/); 203282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 204282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return image.getRaster(); 205282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 206282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 207282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 208282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski /** 209282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski * Returns a color for an arbitrary point. 210282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski */ 211282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski private int getColor(float x, float y) { 212282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float pos; 213282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski if (mDx == 0) { 214282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pos = (y - mY0) / mDy; 215282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } else if (mDy == 0) { 216282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pos = (x - mX0) / mDx; 217282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } else { 218282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // find the x position on the gradient vector. 219282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski float _x = (mDx*mDy*(y-mY0) + mDy*mDy*mX0 + mDx*mDx*x) / mDSize2; 220282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski // from it get the position relative to the vector 221282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski pos = (_x - mX0) / mDx; 222282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 223282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski 224282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski return getGradientColor(pos); 225282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 226282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski } 227282e181b58cf72b6ca770dc7ca5f91f135444502Adam Lesinski} 228