Multi Tile Support via OSL Script: UDIM Mapping

I’ve written an OSL script that helps simplify bringing in UMID Textures tremendously. There are some Node Groups floating around that have been a huge help, but I find it limiting beyond a certain number of UMID patches and can be cumbersome to make changes to.

This script allows you to load an entire folder of textures with a single node. The textures need to be named according to UMID design, however. A good example is “texturename_UMID#.tif”

Here’s information on the script. To use the script:
1.) Use Cycles Render Engine
2.) Enable “Open Shading Language”
3.) Import a “Script” Shader and load up the OSL text

You have four parameters.
1.) Max UMID : Enter the max UMID patch number that your set of textures use. This caps a loop which scans for the textures.
2.) Folder : Specify Folder. Use Absolute or Relative Folder location. For instance, if there is a folder in the same directory as the .blend file named “diffuseTex” that holds a set of UMID Texture patches then type “//diffuseTex/” into the field.
3.) Name : Specify name of textures in folder preceding the UMID number. For instance if the images are “specTexture_1001.tif”, “specTexture_1002.tif” … “specTexture_1029.tif” then specify “specTexture_” in this field.
4.) Ext : Specify extension of files. Example would be to type “.tif” here

I’m sure there are optimizations that can be made to the code, but alas. It’s a start.

If you’re unacquainted with the power of UMID patches, I suggest googling to see how they are used in other programs. This is great because you can create one node for each channel (diffuse, spec, displacement, etc.) that feeds its own shader node.

**ONE CAVEAT: You must have an unused image texture node floating around in the node editor for this to work. Not sure why…but you don’t actually use it.




shader UDIM(
    string Folder = "tex",
    string texName = "tex",
    string texExt = ".tif",
    int maxUDIM = 1001,
    
    output point UV_out = point(0.0, 0.0, 0.0),
    output color image_col= 0
)


{
    //SETUP INITIAL UDIM PATCH NUMBER
    int UDIM = 1001;
    
    //SETUP LOOP THRU IMAGES
    int counter = maxUDIM - 1000;
    for (int i = 0; i < counter; i++) {


        //SETUP UV PATCH COORDINATES FROM UDIM NUMBER FOR MAPPING
        float uv_x = (UDIM - 1001) % 10 ;
        float uv_y = ((UDIM - 1001) - uv_x) / 10 ;
        //float uv_y_hundreds = ( uv_y / 10 );


        //GRAB TEXTURE FILE WITH GIVEN NAME AND FOLDER (RELATIVE TO BLENDER FILE LOCATION)
        string texUDIM = format("%d", UDIM);
        string texFile = concat(Folder,texName,"_",texUDIM,texExt);


        //SETUP UV Coordinates
        float u_coord = 0;
        float v_coord = 0;
        float w_coord = 0;
        point UV = point(0.0, 0.0, 0.0);
        getattribute("geom:uv", UV);
    
        UV_out = UV;  //Will output Object's UV Coords if needed for troubleshooting
    
        float uv_x2 = (uv_x + 1);
        float uv_y2 = (uv_y + 1);


        //IF current UV coords for shading are within respective UV PATCH AREA specified by UDIM NUMBER from Texture file 
        //then use the Texture.  texture() requires UV between 0-1.0, so we translate the UVs to fit in this area


        if ( ( (UV[0] >= uv_x) && (UV[0] <= uv_x2) ) && ( (UV[1] >= uv_y) && (UV[1] <= uv_y2) ) )
        {
            u_coord = UV[0] - uv_x;
            v_coord = UV[1] - uv_y;
            UV[0] = u_coord;
            UV[1] = v_coord;
            image_col += texture(texFile, UV[0], UV[1]);
        }
        
        UDIM += 1;
    }
}


Heyya I tried your script for one of my models…
I cant seem to get it work for me…
Can u provide some example file or something??
Its all pink here :stuck_out_tongue: