| page.title=RenderScript |
| @jd:body |
| |
| <div id="qv-wrapper"> |
| <div id="qv"> |
| <h2>In this document</h2> |
| |
| <ol> |
| <li><a href="#overview">RenderScript System Overview</a></li> |
| <li> |
| <ol> |
| <li><a href="#native">Native RenderScript layer</a></li> |
| |
| <li><a href="#reflected">Reflected layer</a></li> |
| |
| <li><a href="#framework">Android framework layer</a></li> |
| </ol> |
| </li> |
| |
| <li> |
| <a href="#mem-allocation">Memory Allocation APIs</a> |
| </li> |
| <li> |
| <a href="#dynamic">Dynamic Memory Allocations</a> |
| <ol> |
| <li><a href="#pointers">Declaring pointers</a></li> |
| |
| <li><a href="#struct-pointer-reflection">How pointers are reflected</a></li> |
| |
| <li><a href="#binding">Allocating and binding memory to the RenderScript</a></li> |
| |
| <li><a href="#read-write-dynamic">Reading and writing to memory</a></li> |
| |
| </ol> |
| </li> |
| <li> |
| <a href="#static">Static Memory Allocations</a> |
| </li> |
| </ol> |
| </div> |
| </div> |
| |
| <p>RenderScript offers a high performance 3D graphics rendering and compute API at the native |
| level, which you write in the C (C99 standard). The main advantages of RenderScript are:</p> |
| <ul> |
| <li>Portability: RenderScript is designed to run on many types of devices with different CPU |
| and GPU architectures. It supports all of these architectures without having to target each |
| device, because the code is compiled and cached on the device at runtime.</li> |
| |
| <li>Performance: RenderScript provides similar performance to OpenGL with the NDK while |
| offering the portability of the OpenGL APIs provided by the Android framework ({@link |
| android.opengl}). In addition, it also offers a high performance compute API that is not |
| offered by OpenGL.</li> |
| |
| <li>Usability: RenderScript simplifies development when possible, such as eliminating JNI glue code |
| and simplifying mesh setup.</li> |
| </ul> |
| |
| <p>The main disadvantages are:</p> |
| |
| <ul> |
| <li>Development complexity: RenderScript introduces a new set of APIs that you have to learn. |
| RenderScript also handles memory differently compared to OpenGL with the Android framework APIs |
| or NDK.</li> |
| |
| <li>Debugging visibility: RenderScript can potentially execute (planned feature for later releases) |
| on processors other than the main CPU (such as the GPU), so if this occurs, debugging becomes more difficult. |
| </li> |
| |
| <li>Less features: RenderScript does not provide as many features as OpenGL such as all the compressed |
| texture formats or GL extensions.</li> |
| </ul> |
| |
| <p>You need to consider all of the aspects of RenderScript before deciding when to use it. The following list describes |
| general guidelines on when to use OpenGL (framework APIs or NDK) or RenderScript:</p> |
| <ul> |
| <li>If you are doing simple graphics rendering and performance is not critical, you probably want to use the |
| Android framework OpenGL APIs, which still provide adequate performance, to eliminate the added coding and debugging complexity of |
| RenderScript.</li> |
| |
| <li>If you want the most flexibility and features while maintaining relatively good debugging |
| support, you probably want to use OpenGL and the NDK. Applications that require this are high end |
| or complicated games, for example.</li> |
| |
| <li>If you want a solution that is portable, has good performance, |
| and you don't need the full feature set of OpenGL, RenderScript is a good solution. If you also |
| need a high performance compute language, then RenderScript offers that as well. |
| Good candidates for RenderScript are graphics intensive UIs that require 3D rendering, live wallpapers, |
| or applications that require intensive mathematical computation.</li> |
| </ul> |
| |
| <p>For an example of RenderScript in action, install the RenderScript sample applications that |
| are shipped with the SDK in <code><sdk_root>/samples/android-11/RenderScript</code>. |
| You can also see a typical use of RenderScript with the 3D carousel view in the Android 3.x |
| versions of Google Books and YouTube.</p> |
| |
| <h2 id="overview">RenderScript System Overview</h2> |
| |
| <p>The RenderScript system adopts a control and slave architecture where the low-level native |
| code is controlled by the higher level Android system that runs in a virtual machine (VM). The |
| Android VM still retains all control of memory and lifecycle management and calls the native |
| RenderScript code when necessary. The native code is compiled to intermediate bytecode (LLVM) and |
| packaged inside your application's <code>.apk</code> file. On the device, the bytecode is |
| compiled (just-in-time) to machine code that is further optimized for the device that it is |
| running on. The compiled code on the device is cached, so subsequent uses of the RenderScript |
| enabled application do not recompile the intermediate code. RenderScript has three layers of code |
| to enable communication between the native and Android framework code:</p> |
| |
| <ul> |
| <li>The native RenderScript layer does the intensive computation or graphics rendering. You |
| define your native code in <code>.rs</code> and <code>.rsh</code> files.</li> |
| |
| <li>The reflected layer is a set of classes that are reflected from the native code. It is basically |
| a wrapper around the native code that allows the Android framework to interact with native RenderScripts. |
| The Android build tools automatically generate the classes for this layer during |
| the build process and eliminates the need to write JNI glue code, like with the NDK.</li> |
| |
| <li>The Android framework layer is comprised of the Android framework |
| APIs, which include the {@link android.renderscript} package. This layer gives high level commands |
| like, "rotate the view" or "filter the bitmap", by calling the reflected layer, which in turn calls |
| the native layer. </li> |
| </ul> |
| |
| <h3 id="native">Native RenderScript layer</h3> |
| |
| <p>The native RenderScript layer consists of your RenderScript code, which is compiled and |
| executed in a compact and well defined runtime. Your RenderScript code has access to a limited |
| amount of functions because it cannot access the NDK or standard C functions, since they must be guaranteed to |
| run on a standard CPU. The RenderScript runtime was designed to run on different types of processors, |
| which may not be the CPU, so it cannot guarantee support for standard C libraries. What |
| RenderScript does offer is an API that supports intensive computation and graphics rendering with a collection of math |
| and graphics APIs.</p> |
| |
| <p>Some key features of the native RenderScript libraries include:</p> |
| |
| <ul> |
| <li>A large collection of math functions with both scalar and vector typed overloaded versions |
| of many common routines. Operations such as adding, multiplying, dot product, and cross product |
| are available.</li> |
| |
| <li>Conversion routines for primitive data types and vectors, matrix routines, date and time |
| routines, and graphics routines.</li> |
| |
| <li>Logging functions</li> |
| |
| <li>Graphics rendering functions</li> |
| |
| <li>Memory allocation request features</li> |
| |
| <li>Data types and structures to support the RenderScript system such as Vector types for |
| defining two-, three-, or four-vectors.</li> |
| </ul> |
| |
| <p>The RenderScript header files and LLVM front-end libraries are located in the <code>include/</code> and |
| <code>clang-include/</code> directories in the |
| <code><sdk_root>/platforms/android-11/renderscript/</code> directory of the Android SDK. The |
| headers are automatically included for you, except for the RenderScript graphics specific header file, which |
| you can include as follows:</p> |
| <pre> |
| #include "rs_graphics.rsh" |
| </pre> |
| |
| <h3 id="reflected">Reflected layer</h3> |
| |
| <p>The reflected layer is a set of classes that the Android build tools generate to allow access |
| to the native RenderScript code from the Android VM. This layer defines entry points for |
| RenderScript functions and variables, so that you can interact with them with the Android |
| framework. This layer also provides methods and constructors that allow you to allocate memory |
| for pointers that are defined in your RenderScript code. The following list describes the major |
| components that are reflected:</p> |
| |
| <ul> |
| <li>Every <code>.rs</code> file that you create is generated into a class named |
| <code>ScriptC_<em>renderscript_filename</em></code> of type {@link |
| android.renderscript.ScriptC}. This is the <code>.java</code> version of your <code>.rs</code> |
| file, which you can call from the Android framework. This class contains the following |
| reflections: |
| |
| <ul> |
| <li>Non-static functions in your <code>.rs</code> file.</li> |
| |
| <li>Non-static, global RenderScript variables. Accessor methods are generated for each |
| variable, so you can read and write the natively declared variables from the Android |
| framework. The <code>get</code> method comes with a one-way communication restriction. The |
| last value that is set from the Android framework is always returned during a call to a |
| <code>get</code> method. If the native RenderScript code changes the value, the change does |
| not propagate back to the Android framework layer. |
| If the global variables are initialized |
| in the native RenderScript code, those values are used to initialize the corresponding |
| values in the Android framework layer. If global variables are marked as |
| <code>const</code>, then a <code>set</code> method is not generated.</li> |
| <li>Global pointers generate a special method named <code>bind_<em>pointer_name</em></code> |
| instead of a <code>set()</code> method. This method allows you to bind the memory that is |
| allocated in the Android VM for the pointer to the native RenderScript (you cannot allocate |
| memory in your <code>.rs</code> file). You can read and write to this memory from both the |
| Android framework and RenderScript code. For more information, see <a href="mem-mgmt">Working |
| with Memory and Data</a></li> |
| </ul> |
| </li> |
| |
| <li>A <code>struct</code> is reflected into its own class named |
| <code>ScriptField_<em>struct_name</em></code>, which extends {@link |
| android.renderscript.Script.FieldBase}. This class represents an array of the |
| <code>struct</code>, which allows you to allocate memory for one or more instances of this |
| <code>struct</code>.</li> |
| </ul> |
| |
| <h3 id="framework">Android framework layer</h3> |
| |
| <p>The Android framework layer consists of the usual Android framework APIs, which include the |
| RenderScript APIs in {@link android.renderscript}. This layer handles things such as the |
| Activity lifecycle and memory management of your application. It issues high level commands to |
| the native RenderScript code through the reflected layer and receives events from the user such |
| as touch and input events and relays them to your RenderScript code, if needed. |
| </p> |
| |
| <h2 id="mem-allocation">Memory Allocation APIs</h2> |
| |
| <p>Before you begin writing your first RenderScript application, you must understand how |
| memory is allocated for your RenderScript code and how data is shared between the native and VM |
| spaces. RenderScript allows you to access allocated memory in both the native layer |
| and Android system layer. All dynamic and static memory is allocated by the Android VM. |
| The Android VM also does reference counting and garbage collection for you. |
| You can also explicitly free memory that you no longer need.</p> |
| |
| <p class="note"><strong>Note:</strong> To declare temporary memory in your native RenderScript |
| code without allocating it in the Android VM, you can still do things like instantiate a scratch |
| buffer using an array.</p> |
| |
| <p>The following classes support the memory management features of RenderScript in the Android |
| VM. You normally do not need to work with these classes directly, because the reflected layer |
| classes provide constructors and methods that set up the memory allocation for you. There are |
| some situations where you would want to use these classes directly to allocate memory on your |
| own, such as loading a bitmap from a resource or when you want to allocate memory for pointers to |
| primitive types.</p> |
| |
| <table id="mem-mgmt-table"> |
| <tr> |
| <th>Android Object Type</th> |
| |
| <th>Description</th> |
| </tr> |
| |
| <tr> |
| <td>{@link android.renderscript.Element}</td> |
| |
| <td> |
| <p>An element represents one cell of a memory allocation and can have two forms: Basic or |
| Complex.</p> |
| |
| <p>A basic element contains a single component of data of any valid RenderScript data type. |
| Examples of basic element data types include a single float value, a float4 vector, or a |
| single RGB-565 color.</p> |
| |
| <p>Complex elements contain a list of basic elements and are created from |
| <code>struct</code>s that you declare in your RenderScript code. The most basic primitive |
| type determines the data alignment of the memory. For example, a float4 vector subelement |
| is alligned to <code>sizeof(float)</code> and not <code>sizeof(float4)</code>. The ordering |
| of the elements in memory are the order in which they were added, with each component |
| aligned as necessary.</p> |
| </td> |
| </tr> |
| |
| <tr> |
| <td>{@link android.renderscript.Type}</td> |
| |
| <td> |
| A type is a memory allocation template and consists of an element and one or more |
| dimensions. It describes the layout of the memory (basically an array of {@link |
| android.renderscript.Element}s) but does not allocate the memory for the data that it |
| describes. |
| |
| <p>A type consists of five dimensions: X, Y, Z, LOD (level of detail), and Faces (of a cube |
| map). You can assign the X,Y,Z dimensions to any positive integer value within the |
| constraints of available memory. A single dimension allocation has an X dimension of |
| greater than zero while the Y and Z dimensions are zero to indicate not present. For |
| example, an allocation of x=10, y=1 is considered two dimensional and x=10, y=0 is |
| considered one dimensional. The LOD and Faces dimensions are booleans to indicate present |
| or not present.</p> |
| </td> |
| </tr> |
| |
| <tr> |
| <td>{@link android.renderscript.Allocation}</td> |
| |
| <td> |
| <p>An allocation provides the memory for applications based on a description of the memory |
| that is represented by a {@link android.renderscript.Type}. Allocated memory can exist in |
| many memory spaces concurrently. If memory is modified in one space, you must explicitly |
| synchronize the memory, so that it is updated in all the other spaces that it exists |
| in.</p> |
| |
| <p>Allocation data is uploaded in one of two primary ways: type checked and type unchecked. |
| For simple arrays there are <code>copyFrom()</code> functions that take an array from the |
| Android system and copy it to the native layer memory store. The unchecked variants allow |
| the Android system to copy over arrays of structures because it does not support |
| structures. For example, if there is an allocation that is an array of n floats, the data |
| contained in a float[n] array or a byte[n*4] array can be copied.</p> |
| </td> |
| </tr> |
| </table> |
| |
| <h2 id="dynamic">Working with dynamic memory allocations</h2> |
| |
| <p>RenderScript has support for pointers, but you must allocate the memory in your Android framework |
| code. When you declare a global pointer in your <code>.rs</code> file, you allocate memory |
| through the appropriate reflected layer class and bind that memory to the native |
| RenderScript layer. You can read and write to this memory from the Android framework layer as well as the |
| RenderScript layer, which offers you the flexibility to modify variables in the most appropriate |
| layer. The following sections show you how to work with pointers, allocate memory for them, and |
| read and write to the memory.</p> |
| |
| <h3 id="pointers">Declaring pointers</h3> |
| |
| <p>Because RenderScript is written in C99, declaring a pointer is done in a familiar way. You can |
| declare pointers to a <code>struct</code> or a primitive type, but a <code>struct</code> cannot |
| contain pointers or nested arrays. The following code declares a <code>struct</code>, a pointer |
| to that <code>struct</code>, and a pointer of primitive type <code>int32_t</code> in an <code>.rs</code> file:</p> |
| <pre> |
| #pragma version(1) |
| #pragma rs java_package_name(com.example.renderscript) |
| |
| ... |
| |
| typedef struct Point { |
| float2 point; |
| } Point_t; |
| |
| Point_t *touchPoints; |
| int32_t *intPointer; |
| |
| ... |
| </pre> |
| |
| <p>You cannot allocate memory for these pointers in your RenderScript code, but the Android |
| build tools generate classes for you that allow you to allocate memory in the Android VM for use by |
| your RenderScript code. These classes also let you read and write to the memory. The next section |
| describes how these classes are generated through reflection.</p> |
| |
| <h3>How pointers are reflected</h3> |
| |
| <p>Global variables have a getter and setter method generated. A global pointer generates a |
| <code>bind_pointerName()</code> method instead of a set() method. This method allows you to bind |
| the memory that is allocated in the Android VM to the native RenderScript. For example, the two |
| pointers in the previous section generate the following accessor methods in the <code>ScriptC_<em>rs_filename</em></code> file:</p> |
| <pre> |
| |
| private ScriptField_Point mExportVar_touchPoints; |
| public void bind_touchPoints(ScriptField_Point v) { |
| mExportVar_touchPoints = v; |
| if (v == null) bindAllocation(null, mExportVarIdx_touchPoints); |
| else bindAllocation(v.getAllocation(), mExportVarIdx_touchPoints); |
| } |
| |
| public ScriptField_Point get_touchPoints() { |
| return mExportVar_touchPoints; |
| } |
| |
| private Allocation mExportVar_intPointer; |
| public void bind_intPointer(Allocation v) { |
| mExportVar_intPointer = v; |
| if (v == null) bindAllocation(null, mExportVarIdx_intPointer); |
| else bindAllocation(v, mExportVarIdx_intPointer); |
| } |
| |
| public Allocation get_intPointer() { |
| return mExportVar_intPointer; |
| } |
| |
| </pre> |
| |
| <h3>Allocating and binding memory to the RenderScript</h3> |
| |
| <p>When the build tools generate the reflected layer, you can use the appropriate class |
| (<code>ScriptField_Point</code>, in our example) to allocate memory for a pointer. To do this, |
| you call the constructor for the {@link android.renderscript.Script.FieldBase} class and specify |
| the amount of structures that you want to allocate memory for. To allocate memory for a primitive |
| type pointer, you must build an allocation manually, using the memory management classes |
| described in <a href="mem-mgmt-table">Table 1</a>. The example below allocates memory for both |
| the <code>intPointer</code> and <code>touchPoints</code> pointer and binds it to the |
| RenderScript:</p> |
| <pre> |
| private RenderScriptGL glRenderer; |
| private ScriptC_example script; |
| private Resources resources; |
| |
| public void init(RenderScriptGL rs, Resources res) { |
| //get the rendering context and resources from the calling method |
| glRenderer = rs; |
| resources = res; |
| |
| //allocate memory for the struct pointer, calling the constructor |
| ScriptField_Point touchPoints = new ScriptField_Point(glRenderer, 2); |
| |
| //Create an element manually and allocate memory for the int pointer |
| intPointer = Allocation.createSized(glRenderer, Element.I32(glRenderer), 2); |
| |
| //create an instance of the RenderScript, pointing it to the bytecode resource |
| mScript = new ScriptC_example(glRenderer, resources, R.raw.example); |
| |
| // bind the struct and int pointers to the RenderScript |
| mScript.bind_touchPoints(touchPoints); |
| script.bind_intPointer(intPointer); |
| |
| //bind the RenderScript to the rendering context |
| glRenderer.bindRootScript(script); |
| } |
| </pre> |
| |
| <h3>Reading and writing to memory</h3> |
| |
| <p>Although you have to allocate memory within the Android VM, you can work with the memory both |
| in your native RenderScript code and in your Android code. Once memory is bound, the native |
| RenderScript can read and write to the memory directly. You can also just use the accessor |
| methods in the reflected classes to access the memory. If you modify memory in the Android |
| framework, it gets automatically synchronized to the native layer. If you modify memory in the <code>.rs</code> |
| file, these changes do not get propagated back to the Android framework. |
| For example, you can modify the struct in your Android code like this:</p> |
| <pre> |
| int index = 0; |
| boolean copyNow = true; |
| Float2 point = new Float2(0.0f, 0.0f); |
| touchPoints.set_point(index, point, copyNow); |
| </pre>then read it in your native RenderScript code like this: |
| <pre> |
| rsDebug("Printing out a Point", touchPoints[0].point.x, touchPoints[0].point.y); |
| </pre> |
| |
| <h2>Working with statically allocated memory</h2> |
| |
| <p>Non-static, global primitives and structs that you declare in your RenderScript are easier to work with, |
| because the memory is statically allocated at compile time. Accessor methods to set and get these |
| variables are generated when the Android build tools generate the reflected layer classes. You |
| can get and set these variables using the provided accessor methods. |
| <p class="note"><strong>Note:</strong> The <code>get</code> method comes with a one-way communication restriction. The last value |
| that is set from the Android framework is always returned during a call to a <code>get</code> |
| method. If the native RenderScript code changes the value, the change does not propagate back to |
| the Android framework layer. If the global variables are initialized in the native RenderScript |
| code, those values are used to initialize the corresponding values in the Android framework |
| layer. If global variables are marked as <code>const</code>, then a <code>set</code> method is |
| not generated.</p> |
| </p> |
| |
| <p>For example, if you declare the following primitive in your RenderScript code:</p> |
| <pre> |
| uint32_t unsignedInteger = 1; |
| |
| </pre> |
| <p>then the following code is generated in <code>ScriptC_<em>script_name</em>.java</code>:</p> |
| <pre> |
| private final static int mExportVarIdx_unsignedInteger = 9; |
| private long mExportVar_unsignedInteger; |
| public void set_unsignedInteger(long v) { |
| mExportVar_unsignedInteger = v; |
| setVar(mExportVarIdx_unsignedInteger, v); |
| } |
| |
| public long get_unsignedInteger() { |
| return mExportVar_unsignedInteger; |
| } |
| </pre> |
| |
| <p class="note"><strong>Note:</strong> The mExportVarIdx_unsignedInteger variable represents the |
| index of the <code>unsignedInteger</code>'s in an array of statically allocated primitives. You do |
| not need to work with or be aware of this index.</p> |
| |
| <p>For a <code>struct</code>, the Android build tools generate a class named |
| <code><project_root>/gen/com/example/renderscript/ScriptField_struct_name</code>. This |
| class represents an array of the <code>struct</code> and allows you to allocate memory for a |
| specified number of <code>struct</code>s. This class defines:</p> |
| |
| <ul> |
| <li>Overloaded constructors that allow you to allocate memory. The |
| <code>ScriptField_<em>struct_name</em>(RenderScript rs, int count)</code> constructor allows |
| you to define the number of structures that you want to allocate memory for with the |
| <code>count</code> parameter. The <code>ScriptField_<em>struct_name</em>(RenderScript rs, int |
| count, int usages)</code> constructor defines an extra parameter, <code>usages</code>, that |
| lets you specify the memory space of this memory allocation. There are four memory space |
| possibilities: |
| |
| <ul> |
| <li>{@link android.renderscript.Allocation#USAGE_SCRIPT}: Allocates in the script memory |
| space. This is the default memory space if you do not specify a memory space.</li> |
| |
| <li>{@link android.renderscript.Allocation#USAGE_GRAPHICS_TEXTURE}: Allocates in the |
| texture memory space of the GPU.</li> |
| |
| <li>{@link android.renderscript.Allocation#USAGE_GRAPHICS_VERTEX}: Allocates in the vertex |
| memory space of the GPU.</li> |
| |
| <li>{@link android.renderscript.Allocation#USAGE_GRAPHICS_CONSTANTS}: Allocates in the |
| constants memory space of the GPU that is used by the various program objects.</li> |
| </ul> |
| |
| <p>You can specify one or all of these memory spaces by OR'ing them together. Doing so notifies |
| the RenderScript runtime that you intend on accessing the data in the specified memory spaces. The following |
| example allocates memory for a custom data type in both the script and vertex memory spaces:</p> |
| <pre> |
| ScriptField_Point touchPoints = new ScriptField_Point(glRenderer, 2, |
| Allocation.USAGE_SCRIPT | Allocation.USAGE_GRAPHICS_VERTEX); |
| </pre> |
| |
| <p>If you modify the memory in one memory space and want to push the updates to the rest of |
| the memory spaces, call <code>rsgAllocationSyncAll()</code> in your RenderScript code to |
| synchronize the memory.</p> |
| </li> |
| |
| <li>A static nested class, <code>Item</code>, allows you to create an instance of the |
| <code>struct</code>, in the form of an object. This is useful if it makes more sense to work |
| with the <code>struct</code> in your Android code. When you are done manipulating the object, |
| you can push the object to the allocated memory by calling <code>set(Item i, int index, boolean |
| copyNow)</code> and setting the <code>Item</code> to the desired position in the array. The |
| native RenderScript code automatically has access to the newly written memory. |
| |
| <li>Accessor methods to get and set the values of each field in a struct. Each of these |
| accessor methods have an <code>index</code> parameter to specify the <code>struct</code> in the |
| array that you want to read or write to. Each setter method also has a <code>copyNow</code> |
| parameter that specifies whether or not to immediately sync this memory to the native |
| RenderScript layer. To sync any memory that has not been synced, call <code>copyAll()</code>.</li> |
| |
| <li>The createElement() method creates an object that describes the memory layout of the struct.</li> |
| |
| <li>resize() works much like a <code>realloc</code>, allowing you to expand previously |
| allocated memory, maintaining the current values that were previously set.</li> |
| |
| <li>copyAll() synchronizes memory that was set on the framework level to the native level. When you call |
| a set accessor method on a member, there is an optional <code>copyNow</code> boolean parameter that you can specify. Specifying |
| <code>true</code> synchronizes the memory when you call the method. If you specify false, you can call <code>copyAll()</code> |
| once, and it synchronizes memory for the all the properties that are not synchronized.</li> |
| </ul> |
| |
| <p>The following example shows the reflected class, <code>ScriptField_Point.java</code> that is |
| generated from the Point <code>struct</code>.</p> |
| <pre> |
| package com.example.renderscript; |
| |
| import android.renderscript.*; |
| import android.content.res.Resources; |
| |
| |
| public class ScriptField_Point extends android.renderscript.Script.FieldBase { |
| static public class Item { |
| public static final int sizeof = 8; |
| |
| Float2 point; |
| |
| Item() { |
| point = new Float2(); |
| } |
| |
| } |
| |
| private Item mItemArray[]; |
| private FieldPacker mIOBuffer; |
| public static Element createElement(RenderScript rs) { |
| Element.Builder eb = new Element.Builder(rs); |
| eb.add(Element.F32_2(rs), "point"); |
| return eb.create(); |
| } |
| |
| public ScriptField_Point(RenderScript rs, int count) { |
| mItemArray = null; |
| mIOBuffer = null; |
| mElement = createElement(rs); |
| init(rs, count); |
| } |
| |
| public ScriptField_Point(RenderScript rs, int count, int usages) { |
| mItemArray = null; |
| mIOBuffer = null; |
| mElement = createElement(rs); |
| init(rs, count, usages); |
| } |
| |
| private void copyToArray(Item i, int index) { |
| if (mIOBuffer == null) mIOBuffer = new FieldPacker(Item.sizeof * getType().getX()/* count */); |
| mIOBuffer.reset(index * Item.sizeof); |
| mIOBuffer.addF32(i.point); |
| } |
| |
| public void set(Item i, int index, boolean copyNow) { |
| if (mItemArray == null) mItemArray = new Item[getType().getX() /* count */]; |
| mItemArray[index] = i; |
| if (copyNow) { |
| copyToArray(i, index); |
| mAllocation.setFromFieldPacker(index, mIOBuffer); |
| } |
| |
| } |
| |
| public Item get(int index) { |
| if (mItemArray == null) return null; |
| return mItemArray[index]; |
| } |
| |
| public void set_point(int index, Float2 v, boolean copyNow) { |
| if (mIOBuffer == null) mIOBuffer = new FieldPacker(Item.sizeof * getType().getX()/* count */)fnati; |
| if (mItemArray == null) mItemArray = new Item[getType().getX() /* count */]; |
| if (mItemArray[index] == null) mItemArray[index] = new Item(); |
| mItemArray[index].point = v; |
| if (copyNow) { |
| mIOBuffer.reset(index * Item.sizeof); |
| mIOBuffer.addF32(v); |
| FieldPacker fp = new FieldPacker(8); |
| fp.addF32(v); |
| mAllocation.setFromFieldPacker(index, 0, fp); |
| } |
| |
| } |
| |
| public Float2 get_point(int index) { |
| if (mItemArray == null) return null; |
| return mItemArray[index].point; |
| } |
| |
| public void copyAll() { |
| for (int ct = 0; ct < mItemArray.length; ct++) copyToArray(mItemArray[ct], ct); |
| mAllocation.setFromFieldPacker(0, mIOBuffer); |
| } |
| |
| public void resize(int newSize) { |
| if (mItemArray != null) { |
| int oldSize = mItemArray.length; |
| int copySize = Math.min(oldSize, newSize); |
| if (newSize == oldSize) return; |
| Item ni[] = new Item[newSize]; |
| System.arraycopy(mItemArray, 0, ni, 0, copySize); |
| mItemArray = ni; |
| } |
| |
| mAllocation.resize(newSize); |
| if (mIOBuffer != null) mIOBuffer = new FieldPacker(Item.sizeof * getType().getX()/* count */); |
| } |
| |
| } |
| </pre> |
| |
| </body> |
| </html> |