【问题标题】:How to make Renderscript update a pointer to struct?如何使 Renderscript 更新指向结构的指针?
【发布时间】:2016-01-18 14:18:19
【问题描述】:

所以我在 Renderscript 代码中有一个带有指针的结构:

typedef struct __attribute__((packed, aligned(4))) RGB {
    float red;
    float green;
    float blue;
} RGB_t;

RGB_t *rgb;

这就是我为这个指针分配和绑定内存的方式:

ScriptField_RGB rgbs = new ScriptField_RGB(mRS, bitmap.getWidth()*bitmap.getHeight());
function_script.bind_rgb(rgbs);

这是我设置初始值的方式:

int index = 0;
for(int y = 0; y < bitmap.getHeight(); ++y) {
    for(int x = 0; x < bitmap.getWidth(); ++x) {
       int color = bitmap.getPixel(x, y);
       ScriptField_RGB.Item i = new ScriptField_RGB.Item();
       i.red = Color.red(color) / 255.0f;
       i.green = Color.green(color) / 255.0f;
       i.blue = Color.blue(color) / 255.0f;
       rgbs.set(i, index, false);
       index++;
   }
}

rgbs.copyAll();

'function_script' 是一个带有内核的脚本来填充'RGB_t*',它就是这样的:

#pragma version(1)
#pragma rs java_package_name(my.package)

#include "rgb.rs"

void __attribute__((kernel)) root(RGB_t pixel, uint32_t x) {
    //rsDebug("before", rgb[x].red,rgb[x].green,rgb[x].blue);
    rgb[x].red = pixel.red * 255.0f;
    rgb[x].green = pixel.green * 255.0f;
    rgb[x].blue = pixel.blue * 255.0f;
    //rsDebug("after", rgb[x].red,rgb[x].green,rgb[x].blue);
}

运行这个内核:

function_script.forEach_root(arrayOperational);

不会在 Android 层更新我的 ScriptField 值。我仍然保留着我之前确定的旧价值观。

所以如果我打电话:

rgbs.get(index)

当然,在“foreach root”调用之后,我会得到我原来的值。

如何在 Android 层中反映我的更改?

【问题讨论】:

    标签: java android pointers struct renderscript


    【解决方案1】:

    由于您正在处理Bitmap 之类的数据(RGB 值),因此您应该考虑使用输入和输出Allocation 对象而不是您自己的绑定。 Rendescript 将有效地为您处理,而不必像这样手动绑定字段。

    但是,如果您必须执行此绑定,则需要设置该字段的用法以包含 Allocation.USAGE_SHARED(使用不同的重载构造函数。)有了它,您应该能够调用 @987654325 @ 在 Java 中的字段对象上以从脚本中获取最新数据。如果这不起作用(这取决于自动生成的代码),您可以尝试调用getAllocation(),然后调用Allocation.syncAll(Allocation.USAGE_SHARED) 以使用脚本中的任何更改更新Allocation。此时,您的字段访问方法应提供更新后的值。

    【讨论】:

    • 谢谢拉里!所以,这是一个好的开始。我使用这样的 RGB 只是为了测试,将来可能会有更复杂的结构,如 {int,float,char,...}。现在我正在使用这个构造函数:ScriptField_RGB rgbs = new ScriptField_RGB(mRS, bitmap.getWidth()*bitmap.getHeight(), Allocation.USAGE_SHARED);rgbs.updateAllocation() 在运行所有内核之后。它没有用。所以我试过了:rgbs.updateAllocation();rgbs.getAllocation().syncAll(Allocation.USAGE_SHARED); 现在我得到了 NullPointerException。有什么提示吗?
    • 嗯......副手,不。 updateAllocation() 的基本实现是无操作的。你可以尝试传递USAGE_SHARED | USAGE_SCRIPT 看看它是否改变;不过,我怀疑它会。我希望共享使用会导致它做一些事情。
    • 您可以查看的另一个选项(恕我直言)会更好,即创建自定义 Type 和该类型的 Allocation 然后在 RS 中设置一个字段,即 @987654337 @ 而不是指针。
    • 这可能是另一种选择,但是,我将如何使用分配从 Renderscript 复制回来?它只有copyTo 使用原始类型的方法。基本上使用这个解决方案,对吧? stackoverflow.com/questions/19418416/…
    • 正确。您只能使用原语进行复制。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2010-09-25
    • 1970-01-01
    • 1970-01-01
    • 2016-03-21
    • 2012-03-28
    • 1970-01-01
    相关资源
    最近更新 更多