Richard Rosenman
Engaged
Richard Rosenman
Engaged
Activity
Nov 09, 2024
09:51 AM
Hi ya James! Thanks very much for your help - this does indeed work fine. However, correct me if I'm wrong, but isn't this just scaling an 8-bit color to 16-bit? So Cairo isn't actually providing a true 16-bit pixel in the case above? Funny regarding your last comment - I too noticed the Cairo floating point color support and of course, it was in a newer version than the one I had. So I tried to download all the latest Cairo pieces and compile them on my own as well and, just like you, I got absolutely nowhere. It's a real hot mess, with little to no information, and an absolute nightmare to get to work. It refused to compile correctly no matter what I tired. So in the end I gave up on it! lol So your 16-bit support is at least welcome for now until I can solve that later on. These plugins aren't 32-bit plugins anyway so this will do. But to clarify, you're saying if I start from a SmartFX plugin I don't need to worry about the 16 bit support as it will automatically output it if in 16-bit mode? That means though, I would need to get the latest Cairo version working in order to use its 32-bit floating point color capabilities. Thanks again for your help! Also, you mentioned you found this tidbit in the old AE forum - is there an actual way to access that? It was my understanding that it was mercilessly long blown away by Adobe. Such a shame as there was SO much helpful info on there... Regards, -Rich
... View more
Nov 04, 2024
04:20 PM
Hi Shachar; Thanks for your always helpful suggestions. Thanks for pointing out the A_u_char - I should have known that is limited to 255, and that was my careless mistake. The 16 bit shift, I would not have understood. I tried those suggestions but unfortunately, the output is still wrong. It outputs all channels but they are wrong - the alpha is aliased and the RGB channels display incorrect colors. This is the adapted code I used as per your suggestions: PF_Err cairoCopy16(void* refcon, A_long threadInd, A_long itemNum,
A_long iterTotal)
{
cairoRefcon* data = (cairoRefcon*)refcon;
int i = itemNum;
PF_Err err = PF_Err_NONE;
uint32_t* rowP;
PF_Pixel16* worldPtr = sampleIntegral16(data->output, 0, i);
rowP = (uint32_t*)(data->data + i * data->stride);
for (int x = 0; x < data->output.width; x++) {
worldPtr->alpha = rowP[x] >> 48;
if (worldPtr->alpha)
{
float rf = A_u_short(rowP[x] >> 32) / (float)worldPtr->alpha;
float gf = A_u_short(rowP[x] >> 16) / (float)worldPtr->alpha;
float bf = A_u_short(rowP[x] >> 0) / (float)worldPtr->alpha;
float af = A_u_short(rowP[x] >> 48) / (float)PF_MAX_CHAN16;
worldPtr->red = A_u_short(rf * PF_MAX_CHAN16);
worldPtr->green = A_u_short(gf * PF_MAX_CHAN16);
worldPtr->blue = A_u_short(bf * PF_MAX_CHAN16);
worldPtr->alpha = A_u_short(af * PF_MAX_CHAN16);
}
worldPtr++;
}
return err;
} Anyway, I understand if you are unfamiliar with Cairo, you might not have much else to suggest but perhaps someone who uses it might know? I assume Cairo supports 16 bit and 32 bit - I would be very, very surprised if it didn't. The only other thing I can think might be a culprit is the image format one specifies at the beginning: cairo_surface_t* surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, output->width, output->height); Looking in the docs, this is what they say about the image formats: https://cairographics.org/manual/cairo-Image-Surfaces.html#cairo-format-t Actually, the above suggests that the CAIRO_FORMAT_ARGB32 is a 8-bits per channel format? And I don't see any other formats that suggest higher bit depths... Am I nuts? There is the "CAIRO_FORMAT_RGB16_565" but that seems to carry less information than the ARGB32 so I don't see how that could be 16 bits per channel. However, I don't see how Cairo could only offer 8 bit color depth so perhaps I'm missing something here... *EDIT* I do see that it offers the option to use "CAIRO_FORMAT_RGBA128F" which is 32 bit. Perhaps this is one option to go with. It wasn't in my version of Cairo but a newer one. -Richard
... View more
Nov 03, 2024
08:04 AM
1 Upvote
Hi gang! I know there are a few developers on here using Cairo with the AE SDK and I have recently jumped into this as well. It is indeed quite powerful and makes life significantly easier. One thing I can't figure out is how to render in other depths like 16 bit and 32 bit. This is the familiar code for rendering in 8-bit from Cairo: // Write pixel 8-bit
PF_Pixel* sampleIntegral8(PF_EffectWorld& def, int x, int y) {
return (PF_Pixel*)((char*)def.data +
(y * def.rowbytes) +
(x * sizeof(PF_Pixel)));
}
PF_Err cairoCopy8(void* refcon, A_long threadInd, A_long itemNum,
A_long iterTotal)
{
cairoRefcon* data = (cairoRefcon*)refcon;
int i = itemNum;
PF_Err err = PF_Err_NONE;
uint32_t* rowP;
PF_Pixel8* worldPtr = sampleIntegral8(data->output, 0, i);
rowP = (uint32_t*)(data->data + i * data->stride);
for (int x = 0; x < data->output.width; x++) {
worldPtr->alpha = rowP[x] >> 24;
if (worldPtr->alpha)
{
float rf = A_u_char(rowP[x] >> 16) / (float)worldPtr->alpha;
float gf = A_u_char(rowP[x] >> 8) / (float)worldPtr->alpha;
float bf = A_u_char(rowP[x] >> 0) / (float)worldPtr->alpha;
worldPtr->red = A_u_char(rf * PF_MAX_CHAN8);
worldPtr->green = A_u_char(gf * PF_MAX_CHAN8);
worldPtr->blue = A_u_char(bf * PF_MAX_CHAN8);
}
worldPtr++;
}
return err;
} This is what I've done in my *attempt* to adapt it to 16-bit rendering: PF_Pixel16* sampleIntegral16(PF_EffectWorld& def, int x, int y) {
return (PF_Pixel16*)((char*)def.data +
(y * def.rowbytes) +
(x * sizeof(PF_Pixel16)));
}
PF_Err cairoCopy16(void* refcon, A_long threadInd, A_long itemNum,
A_long iterTotal)
{
cairoRefcon* data = (cairoRefcon*)refcon;
int i = itemNum;
PF_Err err = PF_Err_NONE;
uint32_t* rowP;
PF_Pixel16* worldPtr = sampleIntegral16(data->output, 0, i);
rowP = (uint32_t*)(data->data + i * data->stride);
for (int x = 0; x < data->output.width; x++) {
worldPtr->alpha = rowP[x] >> 24;
if (worldPtr->alpha)
{
float rf = A_u_char(rowP[x] >> 16) / (float)worldPtr->alpha;
float gf = A_u_char(rowP[x] >> 8) / (float)worldPtr->alpha;
float bf = A_u_char(rowP[x] >> 0) / (float)worldPtr->alpha;
worldPtr->red = A_u_char(rf * PF_MAX_CHAN16);
worldPtr->green = A_u_char(gf * PF_MAX_CHAN16);
worldPtr->blue = A_u_char(bf * PF_MAX_CHAN16);
}
worldPtr++;
}
return err;
} However, this renders incorrectly. It seems it still exports in the range of 0-255. Perhaps it has something to do with the bit-shifting which may need to be different for 16 / 32 bit and which, admittedly, I don't really understand. Does anyone have any ideas on how to correctly adapt this to 16-bit and 32-bit? Thank you as always in advance to everyone. Without this forum, I'd get nowhere. Regards, -Richard
... View more
Oct 14, 2024
10:37 AM
Hi gang; I am primarily a Windows developer and I have released a few AE plugins in the past. For those that I also released Mac versions for, I purchased a second-hand Mac, setup XCode and compiled my plugins. I released them like that and never really had any issues from Mac users about notarization since I suppose it's pretty common to allow un-notarized apps to run on Mac. I now see in this update: https://developer.apple.com/documentation/security/notarizing-macos-software-before-distribution that all plugins must now be notarized before release. I guess this means now adding an extra step. My understanding is that it involves running the notarization tool locally. Is that correct? Is this a required step for plugins that you want to upload to the app store or is it also required for someone like myself that simply wants to distribute them online? Next, I see that all Apple software also now needs to be signed. I see that here: https://support.apple.com/en-ca/guide/security/sec3ad8e6e53/web It seems this is for both software intended for the app store and outside of it, is that correct? And upon further reading, it says in order to sign you must pay a yearly fee of $99: "These certificates can only be obtained by joining the Apple Developer Program, which costs $99 per year." So just to be perfectly and 100% clear: To release my plugins for Windows, I simply compile them and release. To release my plugins for Mac, I need to compile them. Then notarize them with the notarization tool which I need to download. Then make an account and purchase a Mac developer certificated for $99 every year. Then sign the plugins following these steps: https://sslinsights.com/how-to-use-code-signing-in-macos/ If someone who knows the Mac process could confirm this, I would appreciate it. If this is really the required process for releasing Apple software, unfortunately I'm going to dump Mac support as I'm not really interested in wasting time and resources as well as jumping through hoops for Apple. Thanks, -Richard
... View more
Sep 25, 2024
12:51 PM
I'm getting some strange glitches in my plugin I'm developing when using MFR. This effect calls for many random numbers every frame to generate boxes and place them in random positions. It's a relatively simple plugin so there's not much more to it than that. However, when caching for a preview, some frames have the boxes in the same position as the previous frame. If I disable MFR from Settings - > Preferences -> Memory & Performance it goes away and every frame has correct random box positions. So that's how I'm assuming it has to do with MFR. I'm not using any out of the box functions just your bases srand() for see initialization and rand() for generating a new number. I even tried a thread-safe random generator but the issue persists: int intRand(const int & min, const int & max) {
static thread_local std::mt19937 generator;
std::uniform_int_distribution<int> distribution(min,max);
return distribution(generator);
} Any ideas what could be causing this? Has anyone else had similar issues? I should also say that it's the first bunch of frames that tend to have more issues and then they have fewer. -Richard
... View more
Aug 26, 2024
12:49 PM
Hi gang; I have an idea of the answer but I wanted to verify. When developing plugins, I am assuming it is important to have each and every parameter named uniquely in the actual interfact, correct? If not, when creating an expression and adding the parameter name, if there are multiple instances of the same name, there will be issues, right? There are times when you don't need unique names. In my case, I have a plugin that has a start and end point, under different topics. So I have, for example: Start Point (topic)
Position
Color
Width
etc...
Start Point (end topic)
End Point (topic)
Position
Color
Width
etc...
End Point (end topic) I am assuming that this is not wise and instead you would want unique names for each parameter like so: Start Point (topic)
Start Position
Start Color
Start Width
etc...
Start Point (end topic)
End Point (topic)
End Position
End Color
End Width
etc...
End Point (end topic) Otherwise creating an expression which contains the name "Position", After Effects wouldn't know if it's to refer to the start or the end position. Is this a correct assumption? Thanks, -Richard
... View more
Jul 17, 2024
04:03 PM
Hi Shachar; Thanks for your reply. Yeah, that makes sense. I'm pretty sure it doesn't use bilinear for downscaling because in my own test using standard bilinear scaling a 512x512 graphic down to 15x15, for example, results in brutal aliasing. Whereas the After Effects transform_world result is very good. So it must be using a different type of interpolation. -Rich
... View more
Jul 16, 2024
02:19 PM
Hi gang; I am developing a plug-in that requires heavy downscaling without using Transform_World. My tests with bilinear are not good enough (leads to heavy aliasing) and bicubic is quite slow. So I was wondering if anyone knew what type of pixel interpolation Transform_world uses? The results are quite good and I'd like to apply a similar approach. Thanks in advance, Richard
... View more
Jun 04, 2024
02:27 PM
Heya James! I'm giving this one more shot, in case you want to have one more guess at it. I installed the Freetype library like you suggested and sure enough, the number of errors dropped. However, I now get different ones. Here's what I've got in my "Other Linker Flags" /opt/local/lib/libcairo.a /opt/local/lib/libpng.a /opt/local/lib/libfreetype.a /opt/local/lib/libpixman-1.a And this is what I've got in my "Header Search Paths" /opt/local/include /opt/local/include/freetype2 /opt/local/include/cairo /opt/local/lib/cairo /opt/local/lib Finally, this is what I've got in my "Library Search Paths" /opt/local/lib/cairo /opt/local/lib I'm not really sure if there's any other settings I need in XCode but the documentation I've read didn't specify it. These are the errors I'm now getting. They still reference Freetype and LibCairo so could it be a version issue (like the ones I installed being too old or too new)? Undefined symbols for architecture x86_64:
"_BZ2_bzDecompress", referenced from:
_ft_bzip2_file_fill_output in libfreetype.a(ftbzip2.o)
"_BZ2_bzDecompressEnd", referenced from:
_ft_bzip2_stream_io in libfreetype.a(ftbzip2.o)
_ft_bzip2_stream_close in libfreetype.a(ftbzip2.o)
"_BZ2_bzDecompressInit", referenced from:
_FT_Stream_OpenBzip2 in libfreetype.a(ftbzip2.o)
_ft_bzip2_stream_io in libfreetype.a(ftbzip2.o)
"_BrotliDecoderDecompress", referenced from:
_sfnt_open_font in libfreetype.a(sfnt.o)
"_FcConfigGetCurrent", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcConfigSubstitute", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcDefaultSubstitute", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcFontMatch", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcFreeTypeCharIndex", referenced from:
__cairo_ft_ucs4_to_index in libcairo.a(cairo-ft-font.o)
"_FcInitBringUptoDate", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternAddBool", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternAddDouble", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternAddInteger", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternAddString", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
"_FcPatternCreate", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
"_FcPatternDel", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternDestroy", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_destroy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternDuplicate", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_create_for_pattern in libcairo.a(cairo-ft-font.o)
"_FcPatternGet", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternGetBool", referenced from:
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
"_FcPatternGetFTFace", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
"_FcPatternGetInteger", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
"_FcPatternGetString", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
"_adler32", referenced from:
_png_icc_set_sRGB in libpng.a(png.o)
"_crc32", referenced from:
_png_reset_crc in libpng.a(png.o)
_png_calculate_crc in libpng.a(png.o)
_png_icc_set_sRGB in libpng.a(png.o)
"_deflate", referenced from:
_png_compress_IDAT in libpng.a(pngwutil.o)
_png_text_compress in libpng.a(pngwutil.o)
"_deflateEnd", referenced from:
_png_destroy_write_struct in libpng.a(pngwrite.o)
_png_deflate_claim in libpng.a(pngwutil.o)
"_deflateInit2_", referenced from:
_png_deflate_claim in libpng.a(pngwutil.o)
"_deflateReset", referenced from:
_png_deflate_claim in libpng.a(pngwutil.o)
"_inflate", referenced from:
_FT_Gzip_Uncompress in libfreetype.a(ftgzip.o)
_ft_gzip_file_fill_output in libfreetype.a(ftgzip.o)
_png_zlib_inflate in libpng.a(pngrutil.o)
(maybe you meant: _png_zlib_inflate)
"_inflateEnd", referenced from:
_FT_Stream_OpenGzip in libfreetype.a(ftgzip.o)
_ft_gzip_stream_close in libfreetype.a(ftgzip.o)
_FT_Gzip_Uncompress in libfreetype.a(ftgzip.o)
_png_destroy_read_struct in libpng.a(pngread.o)
"_inflateInit2_", referenced from:
_FT_Stream_OpenGzip in libfreetype.a(ftgzip.o)
_FT_Gzip_Uncompress in libfreetype.a(ftgzip.o)
_png_inflate_claim in libpng.a(pngrutil.o)
"_inflateReset", referenced from:
_ft_gzip_file_io in libfreetype.a(ftgzip.o)
_png_reset_zstream in libpng.a(png.o)
_png_decompress_chunk in libpng.a(pngrutil.o)
"_inflateReset2", referenced from:
_png_inflate_claim in libpng.a(pngrutil.o)
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation) -Rich
... View more
May 31, 2024
02:24 PM
Heya James! Thank you as always for your suggestions. I did as you suggested and used the full path of the cair library in the "Other Linker Flags". Like so: /opt/local/lib/libcairo.a /opt/local/lib/libcairo.dylib And sure enough, I no longer get the "library not found" error. So that seems to have found it. However, I now get a ton of "Undefined Symbol Errors". I noted what you said about the possibility of requiring the pixman library but these errors seem to point to libcairo.a: Undefined symbols for architecture x86_64:
"_FT_Bitmap_Convert", referenced from:
__get_bitmap_surface in libcairo.a(cairo-ft-font.o)
"_FT_Bitmap_Done", referenced from:
__get_bitmap_surface in libcairo.a(cairo-ft-font.o)
"_FT_Bitmap_New", referenced from:
__get_bitmap_surface in libcairo.a(cairo-ft-font.o)
"_FT_Done_Face", referenced from:
__cairo_ft_unscaled_font_lock_face in libcairo.a(cairo-ft-font.o)
__cairo_ft_unscaled_font_destroy in libcairo.a(cairo-ft-font.o)
__cairo_ft_unscaled_font_map_pluck_entry in libcairo.a(cairo-ft-font.o)
"_FT_Done_FreeType", referenced from:
__cairo_ft_font_reset_static_data in libcairo.a(cairo-ft-font.o)
"_FT_Done_MM_Var", referenced from:
_cairo_ft_apply_variations in libcairo.a(cairo-ft-font.o)
__cairo_ft_is_synthetic in libcairo.a(cairo-ft-font.o)
__cairo_ft_unscaled_font_create_internal in libcairo.a(cairo-ft-font.o)
"_FT_Get_Color_Glyph_Layer", referenced from:
__cairo_ft_scaled_glyph_init_surface in libcairo.a(cairo-ft-font.o)
"_FT_Get_First_Char", referenced from:
__cairo_ft_index_to_ucs4 in libcairo.a(cairo-ft-font.o)
"_FT_Get_Glyph_Name", referenced from:
__cairo_index_to_glyph_name in libcairo.a(cairo-ft-font.o)
"_FT_Get_MM_Var", referenced from:
_cairo_ft_apply_variations in libcairo.a(cairo-ft-font.o)
__cairo_ft_is_synthetic in libcairo.a(cairo-ft-font.o)
__cairo_ft_unscaled_font_create_internal in libcairo.a(cairo-ft-font.o)
"_FT_Get_Next_Char", referenced from:
__cairo_ft_index_to_ucs4 in libcairo.a(cairo-ft-font.o)
"_FT_Get_Var_Blend_Coordinates", referenced from:
__cairo_ft_is_synthetic in libcairo.a(cairo-ft-font.o)
"_FT_Get_Var_Design_Coordinates", referenced from:
_cairo_ft_apply_variations in libcairo.a(cairo-ft-font.o)
__cairo_ft_unscaled_font_create_internal in libcairo.a(cairo-ft-font.o)
"_FT_Get_X11_Font_Format", referenced from:
__cairo_ft_load_type1_data in libcairo.a(cairo-ft-font.o)
"_FT_GlyphSlot_Embolden", referenced from:
__cairo_ft_scaled_glyph_load_glyph in libcairo.a(cairo-ft-font.o)
"_FT_GlyphSlot_Oblique", referenced from:
__cairo_ft_scaled_glyph_load_glyph in libcairo.a(cairo-ft-font.o)
"_FT_Init_FreeType", referenced from:
__cairo_ft_unscaled_font_map_lock in libcairo.a(cairo-ft-font.o)
"_FT_Library_SetLcdFilter", referenced from:
__cairo_ft_scaled_glyph_init_surface in libcairo.a(cairo-ft-font.o)
"_FT_Load_Glyph", referenced from:
__cairo_ft_scaled_glyph_load_glyph in libcairo.a(cairo-ft-font.o)
"_FT_Load_Sfnt_Table", referenced from:
__cairo_ft_load_truetype_table in libcairo.a(cairo-ft-font.o)
"_FT_New_Face", referenced from:
__cairo_ft_unscaled_font_lock_face in libcairo.a(cairo-ft-font.o)
"_FT_Outline_Decompose", referenced from:
__cairo_ft_scaled_glyph_init in libcairo.a(cairo-ft-font.o)
"_FT_Outline_Get_CBox", referenced from:
__cairo_ft_scaled_glyph_init_surface in libcairo.a(cairo-ft-font.o)
"_FT_Outline_Transform", referenced from:
__cairo_ft_scaled_glyph_init in libcairo.a(cairo-ft-font.o)
"_FT_Outline_Translate", referenced from:
__cairo_ft_scaled_glyph_load_glyph in libcairo.a(cairo-ft-font.o)
"_FT_Palette_Set_Foreground_Color", referenced from:
__cairo_ft_scaled_glyph_init_surface in libcairo.a(cairo-ft-font.o)
"_FT_Render_Glyph", referenced from:
__cairo_ft_scaled_glyph_init_surface in libcairo.a(cairo-ft-font.o)
"_FT_Set_Char_Size", referenced from:
__cairo_ft_unscaled_font_set_scale in libcairo.a(cairo-ft-font.o)
"_FT_Set_Transform", referenced from:
__cairo_ft_unscaled_font_set_scale in libcairo.a(cairo-ft-font.o)
"_FT_Set_Var_Design_Coordinates", referenced from:
_cairo_ft_apply_variations in libcairo.a(cairo-ft-font.o)
"_FT_Vector_Transform", referenced from:
__cairo_ft_scaled_glyph_load_glyph in libcairo.a(cairo-ft-font.o)
"_FcConfigGetCurrent", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcConfigSubstitute", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcDefaultSubstitute", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcFontMatch", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcFreeTypeCharIndex", referenced from:
__cairo_ft_ucs4_to_index in libcairo.a(cairo-ft-font.o)
"_FcInitBringUptoDate", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternAddBool", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternAddDouble", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternAddInteger", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternAddString", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
"_FcPatternCreate", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
"_FcPatternDel", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternDestroy", referenced from:
__cairo_ft_font_face_create_for_toy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_destroy in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
"_FcPatternDuplicate", referenced from:
__cairo_ft_font_face_get_implementation in libcairo.a(cairo-ft-font.o)
__cairo_ft_font_face_create_for_pattern in libcairo.a(cairo-ft-font.o)
"_FcPatternGet", referenced from:
__cairo_ft_font_options_substitute in libcairo.a(cairo-ft-font.o)
"_FcPatternGetBool", referenced from:
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
"_FcPatternGetFTFace", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
"_FcPatternGetInteger", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
"_FcPatternGetString", referenced from:
__cairo_ft_unscaled_font_create_for_pattern in libcairo.a(cairo-ft-font.o)
__get_pattern_ft_options in libcairo.a(cairo-ft-font.o)
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation) Showing Recent Issues
Undefined symbol: _FT_Bitmap_Convert
Undefined symbol: _FT_Bitmap_Done
Undefined symbol: _FT_Bitmap_New
Undefined symbol: _FT_Done_Face
Undefined symbol: _FT_Done_FreeType
Undefined symbol: _FT_Done_MM_Var
Undefined symbol: _FT_Get_Color_Glyph_Layer
Undefined symbol: _FT_Get_First_Char
Undefined symbol: _FT_Get_Glyph_Name
Undefined symbol: _FT_Get_MM_Var
Undefined symbol: _FT_Get_Next_Char
Undefined symbol: _FT_Get_Var_Blend_Coordinates
Undefined symbol: _FT_Get_Var_Design_Coordinates
Undefined symbol: _FT_Get_X11_Font_Format
Undefined symbol: _FT_GlyphSlot_Embolden
Undefined symbol: _FT_GlyphSlot_Oblique
Undefined symbol: _FT_Init_FreeType
Undefined symbol: _FT_Library_SetLcdFilter
Undefined symbol: _FT_Load_Glyph
Undefined symbol: _FT_Load_Sfnt_Table
Undefined symbol: _FT_New_Face
Undefined symbol: _FT_Outline_Decompose
Undefined symbol: _FT_Outline_Get_CBox
Undefined symbol: _FT_Outline_Transform
Undefined symbol: _FT_Outline_Translate
Undefined symbol: _FT_Palette_Set_Foreground_Color
Undefined symbol: _FT_Render_Glyph
Undefined symbol: _FT_Set_Char_Size
Undefined symbol: _FT_Set_Transform
Undefined symbol: _FT_Set_Var_Design_Coordinates
Undefined symbol: _FT_Vector_Transform
Undefined symbol: _FcConfigGetCurrent
Undefined symbol: _FcConfigSubstitute
Undefined symbol: _FcDefaultSubstitute
Undefined symbol: _FcFontMatch
Undefined symbol: _FcFreeTypeCharIndex
Undefined symbol: _FcInitBringUptoDate
Undefined symbol: _FcPatternAddBool
Undefined symbol: _FcPatternAddDouble
Undefined symbol: _FcPatternAddInteger
Undefined symbol: _FcPatternAddString
Undefined symbol: _FcPatternCreate
Undefined symbol: _FcPatternDel
Undefined symbol: _FcPatternDestroy
Undefined symbol: _FcPatternDuplicate
Undefined symbol: _FcPatternGet
Undefined symbol: _FcPatternGetBool
Undefined symbol: _FcPatternGetFTFace
Undefined symbol: _FcPatternGetInteger
Undefined symbol: _FcPatternGetString Any suggestions? Thanks, -Rich
... View more
May 27, 2024
08:55 PM
Hi gang; I have used Cairo on Windows for SDK development and it works great. However, I am struggling to get it set up on a Mac in order to compile a Mac version. I am wondering if someone can help getting it to work. These are the steps I've done: 1 - Installed MacPorts 2 - Installed Cairo through MacPorts by going to this website: https://ports.macports.org/port/cairo/ and entering the sudo command in my terminal. 3 - Confirmed Cairo is installed by typing "port contents cairo". It is installed in my /opt/local/lib/ folder. 4 - In the Xcode project navigator, under "Search Paths", I added the Cairo folder entries under "Header Search Paths": /opt/local/lib/ /opt/local/lib/cairo /opt/local/include I also added the path here as well for my cairo.h file and added the include to my .cpp file: #include <cairo.h> 5 - In the Xcode project navigator, under "Linking", I added "-libcairo.a" entry under "Other Linking Flags" But when I compile, I get ld: library not found for -libcairo.a clang: error: linker command failed with exit code 1 (use -v to see invocation) Did I miss a step? I find it to be an extremely complicated set up to get this to work. It also doesn't help that I am not good with Macs (nor do I particularly like them). Any help or advice would be highly appreciated. Thanks, Richard
... View more
May 10, 2024
10:13 PM
1 Upvote
Hi gang; So I need to create a Null layer from within my plugin, and link a point parameter to it. I've never done this before but my understanding is that it needs to be done via Javascript. I thought I had the creation part done but it crashes upon execution. This is what I have: AEGP_SuiteHandler suites(in_data->pica_basicP);
A_Boolean outAvailablePB;
AEGP_MemHandle outResultPH;
AEGP_MemHandle outErrorStringPH;
const char* javascriptCode =
"var comp = app.project.activeItem;\r\n"
"comp.layers.addNull();\r\n";
ERR(suites.UtilitySuite4()->AEGP_IsScriptingAvailable(&outAvailablePB));
ERR(suites.UtilitySuite4()->AEGP_ExecuteScript(NULL, javascriptCode, true, &outResultPH, &outErrorStringPH));
A_char* result = NULL;
ERR(suites.MemorySuite1()->AEGP_LockMemHandle(outResultPH, reinterpret_cast<void**>(&result)));
ERR(suites.MemorySuite1()->AEGP_FreeMemHandle(outResultPH));
ERR(suites.MemorySuite1()->AEGP_FreeMemHandle(outErrorStringPH)); Any suggestions as to what is wrong here? I haven't done the linking part but I have a question about that too. Is that a separate javascript command that must be sent after creating the Null or can it be combined together with the Null creation? Thanks in advance. Richard
... View more
Mar 16, 2024
08:22 PM
Yeah, I will run some tests to see what's going on. I suppose one good way to test is to see if the ram usage skyrockets when I select the checkout layer and it does 100 checkouts. I will test that and also try again to do the checkouts and checkins in the same loop iteration, despite it not having worked for me yet. Rich
... View more
Mar 16, 2024
08:48 AM
Hi guys; I have solved it. For some reason, the checkout in SmartRender can be in a loop but the final checkin, should not. If I place the final checkin after my main program loop, it works correctly. This eliminates the Node received more checkout requests than expected. error and works as it should. I am not entirely sure why and I will do more testing but I wanted to post it. As always, I really appreciate both your help and I wouldn't have solved it without better understanding how the IDL works. -Richard
... View more
Mar 15, 2024
07:21 PM
Hi Shachar & James; Thanks for your explanations. I now understand that the IDL doesn't have to match the param ID. I am getting conflicted info though because James says I should checkin with the param ID in SmartRender but Shachar, you say to check in with the IDL. So factoring in your suggestions, this should be the correct structure? // Let's define an IDL outside of the parameter index list so that it's unique and without conflict:
#define IDL 32768
// Now in pre-render we use unique IDL + i to save 100 instances of the checkout frame time (These are the idls used: 32768 + i = range of 32768 to 32868)
for (int i = 0; i < 100; i++)
{
ERR(extraP->cb->checkout_layer(in_dataP->effect_ref,
SKELETON_CHECKOUTLAYER,
IDL + i,
&req,
i * in_dataP->time_step,
in_dataP->time_step,
in_dataP->time_scale,
&checkoutLayer));
UnionLRect(&checkoutLayer.result_rect, &extraP->output->result_rect);
UnionLRect(&checkoutLayer.max_result_rect, &extraP->output->max_result_rect);
} Finally, in SmartRender we should be able to access it like so. I also confirmed with the docs and you should use the IDL here, not the param index: for (i = 0; i < 100; i++)
{
// Check out
ERR(extraP->cb->checkout_layer_pixels(in_data->effect_ref, IDL + i, &checkoutLayer));
// Check In
ERR2(extraP->cb->checkin_layer_pixels(in_data->effect_ref, IDL + i));
} But alas, this still reports an error and crashes: Node received more checkout requests than expected. In ENUMS, I only have one SKELETON_CHECKOUT param, not 100 of them. Similarly in ParamsSetup. Sorry guys, this one is taking me a bit longer to grasp. Please bear with me. What is wrong with it? -Richard
... View more
Mar 14, 2024
06:31 PM
1 Upvote
Hi gang; I would love some guidance here. As we know, there are two ways to check out a layer. One is the old-fashioned way like so: AEFX_CLR_STRUCT(checkoutLayer);
ERR(PF_CHECKOUT_PARAM(in_data,
SKELETON_CHECKOUTLAYER,
in_data->current_time,
in_data->time_step,
in_data->time_scale,
&checkoutColorLayer));
ERR(PF_CHECKIN_PARAM(in_data, &checkoutLayer)); The other, is the method used for SmartRender plugins where you check them out in PreRender like so: ERR(extraP->cb->checkout_layer(in_dataP->effect_ref,
SKELETON_CHECKOUTLAYER,
SKELETON_CHECKOUTLAYER,
&req,
in_dataP->current_time,
in_dataP->time_step,
in_dataP->time_scale,
&in_result));
UnionLRect(&in_result.result_rect, &extraP->output->result_rect);
UnionLRect(&in_result.max_result_rect, &extraP->output->max_result_rect); And then when we are ready to use it in SmartRender, we call it like this: ERR(extraP->cb->checkout_layer_pixels(in_data->effect_ref, SKELETON_CHECKOUTLAYER, &checkoutLayer));
// And once finished:
ERR2(extraP->cb->checkin_layer_pixels(in_data->effect_ref, SKELETON_CHECKOUTLAYER)); Now, with the old fashioned method, it was easy to seek through the time during rendertime and grab whichever frame we wanted. With the SmartRender method, it's trickier because we need to get those frames beforehand in the PreRender function and store them in checkout_idl. This thread kind of discusses it but I still need clarification as my attempts haven't worked: https://community.adobe.com/t5/after-effects-discussions/checkout-previous-frame-in-smart-render/m-p/10943196#M104699 Here are my questions. Let's say I want to checkout a layer over 100 frames. Let's say 0-100: 1 - In the header file, under ENUMS, if my ENUM is called SKELETON_CHECKOUTLAYER, do I need 100 of these or just one? I assume 1 because I don't want 100 checkout layer parameters. And we will modify the ID anyway, not the index, right? 2 - In the ParamsSetup, similarly, we only want 1 instance of it. 3 - In Pre-Render, we would have something like the following: for (int i = 0; i < 100; i++)
{
ERR(extraP->cb->checkout_layer(in_dataP->effect_ref,
SKELETON_CHECKOUTLAYER,
SKELETON_CHECKOUTLAYER+i,
&req,
i * in_dataP->time_step,
in_dataP->time_step,
in_dataP->time_scale,
&checkoutColorLayer));
UnionLRect(&checkoutLayer.result_rect, &extraP->output->result_rect);
UnionLRect(&checkoutLayer.max_result_rect, &extraP->output->max_result_rect);
} This should store the checkout layer at time 0 through to 100. I do not increase the parameter index because we don't want 100 parameter checkouts. Then in SmartRender, I can call that particular time like so (where timeindex is the time of the checked out layer): ERR(extraP->cb->checkout_layer_pixels(in_data->effect_ref, SKELETON_CHECKOUTLAYER + timeindex, &checkoutColorLayer));
// And upon finishing:
ERR2(extraP->cb->checkin_layer_pixels(in_data->effect_ref, SKELETON_CHECKOUTLAYER + timeindex)); However, this is incorrect. I get a crash and an error: "Node received more checkout requests than expected." Any suggestions on what I'm doing wrong here? Thanks, -Richard
... View more
Mar 10, 2024
08:28 PM
Hi James & Shachar; As always, thank you for the helpful advice. Shachar - that was a very detailed and helpful reply. James, I though interate_geenric might have been capable of more than just pixel processing based on what the doc says: "Note: You can iterate over more than pixels." but I too had my doubts. I'll consider writing my own function. I agree that creating something that handles transform, rotation and scale isn't overly complicated but adding filtering to it, and then of course the motion blur capabilities is what really makes it daunting. -Richard
... View more
Mar 09, 2024
04:24 PM
1 Upvote
How would one go about using iterate_generic to draw multiple transform_world using multiple threads? xform_data is my struct of parameters. I am trying to deploy it as such: suites.Iterate8Suite1()->iterate_generic(
numThreads,
&xform_data,
MT_Xform
); PF_Err MT_Xform(void* refcon, A_long threadInd, A_long iterNum, A_long iterTotal)
{
// Use transform-world in here
data->p_suites->WorldTransformSuite1()->transform_world...
} But I am getting no speed increases at all. Any suggestions? Part of it is the lack of documentation, so any help is appreciated.
... View more
Mar 07, 2024
01:26 PM
Hi Shachar; Thanks for your suggestion. I tried the Transform effect and it works fast and fine. However, it is only one transform_world and my plugin also performs very well with only a few particles. So it seems to be more about the number of transform_world calls rather than the size of it. I went ahead and transplanted a very short snippet of code that essentially randomly drawns 500 20x20 transform_world rectangles across the screen, into the Shifter project. As before, the timings are around 150ms on the slow machines and close to 700 ms on the super-fast 64 core Threadripper. So I guess it doesn't have much to do with the rest of my code - as good of a suggestion as that was. I also did the same with the SDK_Noise project and got the same results. Since all evidence points to the increased number of cores as the culprit, perhaps my next step will be to implement multithreading and see if / how that makes a difference. As per James' note, it might make it worse, or it might make it better. But it is frustrating indeed that such a powerful machine produces the slowest results most likely due to the number of cores and I suppose the manner in which AE works. I still can't get over how lightning fast it was on a slow computer, running CS6! After I do that, if there's no improvement, I'm not sure what else I can do. Foregoing transform_world will open a huge can of worms in trying to manually do motion blur. 😐 -Richard
... View more
Mar 07, 2024
07:45 AM
Hi James! thanks for your thoughtful reply - it's interesting to hear your example and the speed benefit it gave. Yes, I've considered foregoing transform_world altogether but then the big problem is motion blur. The main reason for using it is to take care of that aspect. The thought of trying to manually code motion blur, for translation, rotation and scale, is... daunting, to say the least. And motion blur is a critical part of this. But I will give it more thought. Ungh. Regards, Rich
... View more
Mar 06, 2024
02:02 PM
So I've reduced my app to barely nothing - just the loop and transform_world display and the rendertimes are still around 600-700ms per frame on the Threadripper, while only around 150ms on the slow machines. I did at test and I changed the CPU affinity to only one, out of the 64 cores. So that it would only use core 0. The rendertimes then drop to 150-200 ms. So I am suspecting more and more that the number of cores is a culprit here. However, shouldn't transform_world be thread safe? -Richard
... View more
Mar 06, 2024
06:48 AM
Hi guys; Thanks for your replies. I tore the plug-in away bit by bit last night and it comes down to transform_world. That is what kills the performance. I turned on AE render timings and it's about 700 ms per frame. If I comment out the transform_world it about 20 ms per frame - as it should be. I should mention I was also able to put AE 2024 on the slow laptop and it works perfectly fine. So for some reason, this issue is specific to my Threadripper machine. I assume the 32 Cores is somehow involved here. I intend to eventually add MFR but the current plug-in without MFR works really well on the laptop with AE 2024 so it's not the lack of MFR that is hampering it. I also disabled MFR in AE and the performance issue is still there. This is a particle system to it is drawing a mere 500 particles per frame (creating 500 transform_worlds) and barely functioning on the Threadripper whereas all other much, much slower machines work just fine! I saw that my Threadripper has CPU Virtualization disabled and I thought that might have to do with AE's new AVX2 requirements but then I checked the laptop and it too has virtualization disabled. The only difference is aside from being really old, the laptop is only 4 cores. I'm at a loss especially because it seems to be specific only to the Threadripper - to that hardware. Are there any other hardware considerations that could be the culprit here? Richard
... View more
Mar 05, 2024
12:55 PM
1 Upvote
Hi gang; Let me preface by painting the big picture. I have a development machine which I do all my programming on. This is running a really old Intel chip (i7-4930K). I develop on AE 2020 and AE 2023. Unfortunately, the new AE requires AVX2 and my machine doesn't support it, so I cannot download AE 2024 and test it. I like developing on older tech because it guarrantees the slowest my plug-in would ever run. I decided to test my plugin on my work machine which is a best. It's a Ryzen Threadripper 3979X running AE 2024... and it crawls. It's really, really slow. I then went to test it on yet another slow machine I have (i7-3930K) and on a really old AE CS6 and it FLIES! Super fast. So my most powerful machine, with the newest AE version, is the slowest! Clearly, there is something off. I tried messing with various AE 2024 settings but nothing. It crawls. I do not have MFR implemented on my plugin but on my dev machine with AE 2023, it is still quite fast despite not supporting MFR. So I don't think that's the issue. It seems to be specific to my Threadripper, or AE 2024. But I can't test AE 2024 on any other machine due to the AVX2 issue (thanks Adobe). The only other thing I can imagine is the release mode vs debug mode. I am pretty sure I am compiling it in release mode and I believe if I wasn't, I wouldn't be able to run it on any other machine since it would report missing dependables, correct? So does anyone have any suggestions or ideas what could be happening again? To summarize, two really old machines running AE versions prior to 2024 are running my plugin super fast and well. My work machine, which is the fastest of all, with the latest AE, crawls when running it. All other plugins seem to run fine on it. Richard
... View more
Jan 29, 2024
06:55 AM
Any thoughts on this?
... View more
Jan 28, 2024
06:41 AM
1 Upvote
Hello there, I am developing a plug-in using AE SDK. And would like to use the GPU so I took the sample SDK\_Invert\_ProcAmp as a starting point. In this sample there are 3 GPU implementations: CUDA, OpenCL and Metal. One more thing to mention is that I have an Nvidia GPU in my PC. Now what I want to do is force the selection to be OpenCL but instead I get the CUDA selection forced. More specifically, in the method GPUDeviceSetup in the main cpp file (SDK\_Invert\_ProcAmp.cpp), line 270: if (extraP->input->what\_gpu == PF\_GPU\_Framework\_CUDA) {
... This field extraP->input->what\_gpu always has the CUDA option and it comes as input, which is invoked directly from the main switch case. You might suggest simply to neglect this value, delete code related to CUDA and Metal and just go on. Unfortunately this will not work, because there is a whole AE GPU utility that depends on this selection and is needed to be used in many parts of the plug-in. So how does one force the plug-in to use OpenCL, even if there is an Nvidia card available? Any tips are highly appreciated. Thanks!
... View more
Jan 18, 2024
07:47 AM
Any other suggestions from anyone about what GPU approach to best use for an all-compatible workflow? Checking the After Effects GPU requirements page here: https://helpx.adobe.com/after-effects/using/basics-gpu-after-effects.html They list CUDA, DirectX, OpenCL, and Metal. They do not mention OpenGL although the GLator seems to be an OpenGL-specific project. In my eyes, it seems like OpenCL and / or OpenGL would be fairly good cross-compatible API to use, despite the threat of Apple discontinuing which, from what I've read, seems to be possibly only in the far and distance future? Thanks, -Richard
... View more
Jan 10, 2024
03:00 PM
Just coming back to this with more questions. If OpenGL is on its way out according to Mac, why is the GLator project (which is built upon OpenGL) still included with the SDK? Should it not be if Apple is killing it off from their platform? Or does this suggest that it's still safe to develop plugins using OpenGL? If one wishes to use GPU acceleration that will be cross-compatible between Mac and PC, and not develop for three different GPU targets (CUDA, Metal, OpenCL), then is it safe to say that eithe OpenCL or OpenGL would be viable options? Thanks, Richard
... View more
Jan 05, 2024
10:16 PM
1 Upvote
Hi gang; I've got an Arbitrary custom parameter which I've assigned the flags (among others): PF_ParamFlag_CANNOT_TIME_VARY And PF_ParamFlag_COLLAPSE_TWIRLY; With the arb parameter, I understand these go within the function body like so: PF_ADD_ARBITRARY2("Custom Parameter",
UI_BOX_WIDTH,
UI_BOX_HEIGHT,
0,
PF_PUI_CONTROL | PF_PUI_DONT_ERASE_CONTROL | PF_ParamFlag_CANNOT_TIME_VARY | PF_ParamFlag_COLLAPSE_TWIRLY,
def.u.arb_d.dephault,
PARAM_DISK_ID,
ARB_REFCON); However, the keyframing icon still appears and the parameter twirl still defaults to open. CANNOT_TIME_VARY should make the parameter non-keyframable and COLLPASE_TWIRL should start the parameter closed. Are there different flags that should be used to achieve this with arbitrary parameters? Thanks, -Richard
... View more
Dec 07, 2023
07:12 PM
1 Upvote
Hi gang (Shachar) 😉 Over the last while I have (somewhat) blindly stumbled my way across making my own custom parameter using the Arbitrary parameter, with some additional help. Now that I've got it working, I wanted to duplicate it to be reused by other custom parameters. However, none of the UI SDK samples show how to use more than one and, since I don't fully understand the system yet, I am stuck. I checked the forum for similar posts and couldn't really find much help either. So I'll ask my questions and hopefully someone can help. When one creates a custom parameter like below, what else needs to be unique for each custom parameter? Obviously the ID which in this case is CUSTOMUI_DISK_ID. But what about ARB_REFCON? I'm not sure what that is used for - does it also need to be unique for each custom parameter? Finally, what about &def.u.arb_d.dephault? Does that also have to be unique for every arbitrary parameter? AEFX_CLR_STRUCT(def);
def.flags = PF_ParamFlag_SUPERVISE;
def.ui_flags = PF_PUI_CONTROL;
def.ui_width = UI_BOX_WIDTH;
def.ui_height = UI_BOX_HEIGHT;
ERR(CreateDefaultArb(in_data,
out_data,
&def.u.arb_d.dephault));
PF_ADD_ARBITRARY2("Custom UI",
UI_BOX_WIDTH,
UI_BOX_HEIGHT,
0,
PF_PUI_CONTROL | PF_PUI_DONT_ERASE_CONTROL,
def.u.arb_d.dephault,
CUSTOMUI_DISK_ID,
ARB_REFCON); Secondly, I see that in all the examples, each arbitrary parameter is followed by this code which I don't understand what it's for: if (!err) {
PF_CustomUIInfo ci;
AEFX_CLR_STRUCT(ci);
ci.events = PF_CustomEFlag_EFFECT;
ci.comp_ui_width = 0;
ci.comp_ui_height = 0;
ci.comp_ui_alignment = PF_UIAlignment_NONE;
ci.layer_ui_width = 0;
ci.layer_ui_height = 0;
ci.layer_ui_alignment = PF_UIAlignment_NONE;
ci.preview_ui_width = 0;
ci.preview_ui_height = 0;
ci.layer_ui_alignment = PF_UIAlignment_NONE;
err = (*(in_data->inter.register_ui))(in_data->effect_ref, &ci);
} If I have multiple arbitrary parameters, do I need multiple of the above following each one? Should these be unique for each unique arb? In the HandleArbitrary function, it calls the arb handling functions using ARB_REFCON so that leads me to believe each arbitrary parameter must have their own unique ARB_REFCON. If that is the case then I need to call each of my custom parameters in the handler function? Something like this? switch (extra->which_function) {
case PF_Arbitrary_NEW_FUNC:
if (extra->u.new_func_params.refconPV != ARB_REFCON) {
err = PF_Err_INTERNAL_STRUCT_DAMAGED;
}
else {
err = CreateDefaultArb(in_data,
out_data,
extra->u.new_func_params.arbPH);
}
break;
case PF_Arbitrary_NEW_FUNC:
if (extra->u.new_func_params.refconPV != ARB_REFCONTWO) {
err = PF_Err_INTERNAL_STRUCT_DAMAGED;
}
else {
err = CreateDefaultArb(in_data,
out_data,
extra->u.new_func_params.arbPH);
}
break;
... Anyway, I have more questions but maybe this is enough for now. Basically, any guidance / tips and tricks on how to set up multiple arbitrary parameters is welcome! Thanks!
... View more
Nov 15, 2023
09:41 AM
Hi Shachar! Thank you for your informative and helpful reply. That workflow you specified actually makes a lot of sense. By serializing, I'm assuming you mean converting the vector of ints or floats into a string, for example, so that all of it can be passed and held by the arb parameter in its entirety. Then in SmartRender I can grab it and convert it back to int / float and grab the value I need, at the time I need it for. Is this correct? Understood about reading it and drawing it out at the start of the panel call. Thanks, Rich
... View more