GPUImage에서 조각 셰이더에 배열을 전달하는 방법
13624 단어 iOSObjective-Cgpuimage
어쩌면 당연 너무 아무도 쓰지 않았겠지만, GPUImage에서는 처음으로 셰이더 만지는 내가 고생했기 때문에 정리했습니다.
뭔가 더 좋은 방법이 있으면 알려주세요.
GPUImageFilter를 상속한 클래스
GPUImageArrayTestFilter.h#import <GPUImage/GPUImage.h>
@interface GPUImageArrayTestFilter : GPUImageFilter
{
//配列のユニフォーム
GLint testUniform;
//長さのユニフォーム
GLint sizeUniform;
}
//配列データを受け取るプロパティ
@property(readwrite, nonatomic) GLfloat *test;
//配列の長さも同時に指定するセッタ
-(void)setTest:(GLfloat *)test withSize:(GLsizei)size;
@end
GPUImageArrayTestFilter.m#import "GPUImageArrayTestFilter.h"
//シェーダーをNSStringの文字列として用意する
NSString *const kGPUImageArrayTestShaderString = SHADER_STRING
(
varying highp vec2 textureCoordinate;
uniform sampler2D inputImageTexture;
//固定長しかダメ?
uniform highp float test[256];
//実際に使う配列の長さ
uniform highp int size;
void main()
{
//基本は黒
lowp vec3 color = vec3(0.0, 0.0, 0.0);
//配列内で指定された矩形だけ赤くする
for(int i = 0 ; i < size; i+=4){
if(test[i] < textureCoordinate.x
&& textureCoordinate.x < test[i] + test[i + 2]
&& test[i+1] < textureCoordinate.y
&& textureCoordinate.y < test[i+1] + test[i+3]
){
color = vec3(1.0, 0.0, 0.0);
break;
}
}
gl_FragColor = vec4(color, 1);
}
);
@implementation GPUImageArrayTestFilter
- (id)init{
if (!(self = [super initWithFragmentShaderFromString:kGPUImageArrayTestShaderString]))
{
return nil;
}
//配列のuniformIndexを登録
testUniform = [filterProgram uniformIndex:@"test"];
//長さのuniformIndexを登録
sizeUniform = [filterProgram uniformIndex:@"size"];
return self;
}
//C言語の配列とその長さも同時に指定するセッタ
-(void)setTestCArr:(GLfloat *)test withSize:(GLsizei)size{
_test = test;
//配列のポインタをセット
[self setFloatArray:_test length:size forUniform:testUniform program:filterProgram];
//実際のデータのサイズをセット
[self setInteger:size forUniform:_sizeUniform program:filterProgram];
}
//NSArrayを代入するセッタ
-(void)setTestNSArr:(NSArray*)test{
float *cArr = (float*)malloc(sizeof(float*)*test.size);
for(int i = 0 ; i < test.size ; i++){
cArr[i] = [test[i] floatValue];
}
[self setTestCArr:cArr withSize:test.size];
free(cArr);
}
//デフォルトのセッタは配列の長さを0としておく
-(void)setTest:(GLfloat *)test{
[self setTest:test withSize:0];
}
@end
사용법
test.m
//矩形表示用のテストデータ
float test[8] = {
//x,y,width,heightの順で入れている
0.2, 0.2, 0.1, 0.1
,0.6, 0.2, 0.1, 0.1
};
GPUImageArrayTestFilter *filter = [GPUImageArrayTestFilter new];
[filter setTestCArr:test withSize:8];
//あとはGPUImageのフィルタとして実行
실행 결과
이런 이미지를 할 수 있습니다.
마지막
이제 감지 된 각 얼굴 정보에 대해 뭔가를 처리하는 것처럼 보일 수 있습니다.
Reference
이 문제에 관하여(GPUImage에서 조각 셰이더에 배열을 전달하는 방법), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/sakiyamaK/items/268830606cd9766df031
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
#import <GPUImage/GPUImage.h>
@interface GPUImageArrayTestFilter : GPUImageFilter
{
//配列のユニフォーム
GLint testUniform;
//長さのユニフォーム
GLint sizeUniform;
}
//配列データを受け取るプロパティ
@property(readwrite, nonatomic) GLfloat *test;
//配列の長さも同時に指定するセッタ
-(void)setTest:(GLfloat *)test withSize:(GLsizei)size;
@end
#import "GPUImageArrayTestFilter.h"
//シェーダーをNSStringの文字列として用意する
NSString *const kGPUImageArrayTestShaderString = SHADER_STRING
(
varying highp vec2 textureCoordinate;
uniform sampler2D inputImageTexture;
//固定長しかダメ?
uniform highp float test[256];
//実際に使う配列の長さ
uniform highp int size;
void main()
{
//基本は黒
lowp vec3 color = vec3(0.0, 0.0, 0.0);
//配列内で指定された矩形だけ赤くする
for(int i = 0 ; i < size; i+=4){
if(test[i] < textureCoordinate.x
&& textureCoordinate.x < test[i] + test[i + 2]
&& test[i+1] < textureCoordinate.y
&& textureCoordinate.y < test[i+1] + test[i+3]
){
color = vec3(1.0, 0.0, 0.0);
break;
}
}
gl_FragColor = vec4(color, 1);
}
);
@implementation GPUImageArrayTestFilter
- (id)init{
if (!(self = [super initWithFragmentShaderFromString:kGPUImageArrayTestShaderString]))
{
return nil;
}
//配列のuniformIndexを登録
testUniform = [filterProgram uniformIndex:@"test"];
//長さのuniformIndexを登録
sizeUniform = [filterProgram uniformIndex:@"size"];
return self;
}
//C言語の配列とその長さも同時に指定するセッタ
-(void)setTestCArr:(GLfloat *)test withSize:(GLsizei)size{
_test = test;
//配列のポインタをセット
[self setFloatArray:_test length:size forUniform:testUniform program:filterProgram];
//実際のデータのサイズをセット
[self setInteger:size forUniform:_sizeUniform program:filterProgram];
}
//NSArrayを代入するセッタ
-(void)setTestNSArr:(NSArray*)test{
float *cArr = (float*)malloc(sizeof(float*)*test.size);
for(int i = 0 ; i < test.size ; i++){
cArr[i] = [test[i] floatValue];
}
[self setTestCArr:cArr withSize:test.size];
free(cArr);
}
//デフォルトのセッタは配列の長さを0としておく
-(void)setTest:(GLfloat *)test{
[self setTest:test withSize:0];
}
@end
test.m
//矩形表示用のテストデータ
float test[8] = {
//x,y,width,heightの順で入れている
0.2, 0.2, 0.1, 0.1
,0.6, 0.2, 0.1, 0.1
};
GPUImageArrayTestFilter *filter = [GPUImageArrayTestFilter new];
[filter setTestCArr:test withSize:8];
//あとはGPUImageのフィルタとして実行
실행 결과
이런 이미지를 할 수 있습니다.
마지막
이제 감지 된 각 얼굴 정보에 대해 뭔가를 처리하는 것처럼 보일 수 있습니다.
Reference
이 문제에 관하여(GPUImage에서 조각 셰이더에 배열을 전달하는 방법), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/sakiyamaK/items/268830606cd9766df031
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
이제 감지 된 각 얼굴 정보에 대해 뭔가를 처리하는 것처럼 보일 수 있습니다.
Reference
이 문제에 관하여(GPUImage에서 조각 셰이더에 배열을 전달하는 방법), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/sakiyamaK/items/268830606cd9766df031텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)