www.quadsoftware.com
FAQ  FAQ   Search  Search   Memberlist  Memberlist   Usergroups  Usergroups
Register  ::  Log in Log in to check your private messages


Post new topic  Reply to topic
 Creating a shadowmap using a script « View previous topic :: View next topic » 
Author Message
AD_Dennis
PostPosted: Thu Jul 31, 2008 12:30 am    Post subject: Creating a shadowmap using a script Reply with quote



Joined: 02 Apr 2008
Posts: 32

I am interested in writing a script to generate a shadow map for a terrain that cannot be loaded all at one time. To accomplish this I am planning to select one or more zones at a time, unswap them, and then use the shadowmap procedural tool, and reswap until the map has been generated for the entire terrain.

I looked at the script help file and did not see any way to select specific zones other than by name. In the current situation all zones have the same name since they were imported from a BT file.

Also, I did not see any way to access the shadowmap tool. Colormap and maskgenerator are there.

Are these two things possible?
Back to top
View user's profile Send private message
ALicu
PostPosted: Thu Jul 31, 2008 7:02 am    Post subject: Reply with quote



Joined: 12 Feb 2007
Posts: 1326

Hello,

You can access any Grome tool from from the scripts. here is the way to access the shadowmap tool:

Code:

   iEditorTool@ tool = gActivateTool("Terrain.Shadowmap");
   if(tool == null)
      return 1; // Error

   if(!tool.LoadPreset("My Lightmap"))
   {
      gDeactivateTool();
      gConOutErr("\r\nError loading My Lightmap preset for Shadowmap tool!");
      return 1;
   }


In the above code I've just activated the tool and loaded a preset. It is also possible to set the parameters yourself in the script but having a preset it is much easier.

Also before calling the above script you may want to automatically add a layer to apply the shadow map to. Here is the complete script to add the layer and apply the tool:

Code:



// Add a color layer with a specified name (if it doesn't exist).
int AppendLayer(string type, string layer_name)
{
   int layer_index = g_terrain_editor.FindLayer(type, layer_name);
   
   if(layer_index == -1)
   {
      layer_index = g_terrain_editor.AddLayer(-1, type, layer_name);
   }
   
   return layer_index;
}

int AssignMaterialLayerToSelection(string layer_name, string shading,
   string texture_path, uint tex_size, uint tile_x, uint tile_z)
{
   int layer_index = AppendLayer("Color", layer_name);
   if(layer_index == -1) return -1;
   
   // Prepare the material definition
   cPropertyTable table;
   table.SetProperty("material_name", shading);

   string str;
   
   table.SetProperty("texture_source", texture_path);

   str = tex_size;
   table.SetProperty("mask_size", str);
   table.SetProperty("mask_color", "0 0 0 0");
   
   str = tile_x; str += " "; str += tile_z; str += " "; str += "1";
   table.SetProperty("texture_scale", str);
   table.SetProperty("texture_offset", "0 0 0");
   table.SetProperty("texture_rot", "0 0 0");
   
   // Assign it to the selected zone.
   g_terrain_editor.AssignLayerToSelection(layer_index, "Color", table);

   return layer_index;
}

int main()
{
   gConOut("\r\n\r\nLightmap creation: start generation...");

   // Add the lightmap layer.

   // Base layer
   int lightmap_layer = AssignMaterialLayerToSelection("Lightmap", "Masked texture",
      "shadow.tga|/libraries/textures/misc", 512, 1, 1);
   if(lightmap_layer == -1) return 1;
   

   // Apply the shadowmap tool

   // Mark all the layers as not in use.
   g_terrain_editor.UseLayer(-1, "Color", false);

   // Mark our layer as in use.
   g_terrain_editor.UseLayer(lightmap_layer, "Color", true);
   
   iEditorTool@ tool = gActivateTool("Terrain.Shadowmap");
   if(tool == null)
      return 1;

   if(!tool.LoadPreset("My Lightmap"))
   {
      // Deactivate the tool
      gDeactivateTool();
      gConOutErr("\r\nError loading My Lightmap preset for Shadowmap tool!");
      return 1;
   }
   
   // Run the tool
   tool.Run();
   
   // Deactivate the tool
   gDeactivateTool();

   gConOut("\r\nLightmap creation: end generation.");

   return 0;
}




Now about the zone identification problem. I will modify the BT importer to create unique names for the imported zones. I can either have the zones with "BT Zone X Z" format or with "BT Zone N". Let me know what's the best choice for you. I will send you a link to the new BT plugin shortly.

In the next Grome update you will also have the possibility in a script to get the terrain project and browse all the zones. We also plan to add the possibility to change the name of a zone. We are continuously improving our scripting (expose more and more of Grome functionality) so please be patience with us on this area.

But in the mean time you can use the new BT plugin and I will update shortly.

Regards,
Adrian L.
Back to top
View user's profile Send private message
ALicu
PostPosted: Thu Jul 31, 2008 1:18 pm    Post subject: Reply with quote



Joined: 12 Feb 2007
Posts: 1326

Hi,

You can find the new BT importer (that creates unique zones names) here:

http://www.quadsoftware.com/storage/ImpBT.plug

If you are using RAW importer you can also get:

http://www.quadsoftware.com/storage/ImpRAW.plug

These updates will be part of the next Grome patch.

Regards,
Adrian L.
Back to top
View user's profile Send private message
AD_Dennis
PostPosted: Thu Jul 31, 2008 10:02 pm    Post subject: Reply with quote



Joined: 02 Apr 2008
Posts: 32

ALicu, wow. Such fast response! The modified importer will be very nice. I have a fairly large terrain already imported at BT. Is there a way to rename the tiles in the existing terrain?
Back to top
View user's profile Send private message
ALicu
PostPosted: Fri Aug 01, 2008 7:59 am    Post subject: Reply with quote



Joined: 12 Feb 2007
Posts: 1326

Hi Dennis, you can rename zones from the Grome UI as described here:

http://www.quadsoftware.com/forum/viewtopic.php?t=283&highlight=rename

But you would have to do it zone by zone.

See the modified plugins links above. Plase use version 1.20.20 with them.
Back to top
View user's profile Send private message
ALicu
PostPosted: Fri Aug 01, 2008 8:13 am    Post subject: Reply with quote



Joined: 12 Feb 2007
Posts: 1326

And here is a script framework you can use (with Grome 1.20.20) to process a grid of BT imported zones:

Code:


// ===============================================
// Grome Modeler - Quad software
//
// SwapProcess script
// This script scans a subset of zones, previously imported with the BT Importer plugin,
// tries to unswap the zones before applying a given toolchain on the terrain surfaces and swaps the zones back.
// A 3x3 terrain zone cluster is maintained around the "processed" terrain zone, so we can do a seam removal pass after the toolchain is applied
// thus keeping the borders consistent across the entire area to be modified.
//
// ===============================================


//Keep a table with node handles, which will be filled with the terrain zones from the resident area
//This table will be used to perform the selection operations required for the processing tasks
iNode@[] zones(9);
   
//The 3x3 zone resident area is determined by a Moore neighborhood around a center zone (which is processed)
int[] x_offset = {-1, 0, 1, -1, 0, 1, -1, 0, 1};
int[] z_offset = {-1, -1, -1, 0, 0, 0, 1, 1, 1};

// This routine assumes that we have at least one selected (unswapped) zone into the current scene, and activates
// a chain of tools, to be applied to the zone layers
void ProcessCurrentZone()
{
   // Run various tools
   // ...
}

//Check if we can find a terrain zone named "DTED_Zone_x_y"
void FindResidentZone(int k, int x, int z)
{
   string zone_name;
   
   zone_name = "BT Zone ";
   zone_name += x;
   zone_name += " ";
   zone_name += z;
   
   //Try to aquire the terrain zone node
   iNode@ node = gGetFirstNodeByName(zone_name);
   @zones[k] = @node;
}


// Script main entry point.
int main()
{
   gConOut("\r\n\r\nSwapProcess script...");
   gConOut("\r\n");

   //Remove all the heightmap layers from use
   g_terrain_editor.UseLayer(-1, "Heightmap", false);
   //Use the base layer for all qubsequent tool processing sessions
   g_terrain_editor.UseLayer(0, "Heightmap", true);

   int x,xx, z, k;
   
   //Area bounds (the toolchains will be spawned for each zone within the area bounds)
   int min_x, min_z, max_x, max_z;
   min_x = 0;
   min_z = 0;
   max_x = 8;
   max_z = 8;

   //Scan direction along the X axis
   int direction = 1;
   
   //Number of zones to be processed along the X axis
   int x_size = max_x - min_x + 1;
   
   for(z = min_z; z <= max_z; z++)
   {
      for(xx = 0; xx < x_size; xx++)
      {
         if(direction == 1)
            x = min_x + xx;
         else
            x = max_x - xx;
            
         //Fill the resident area
         gConOut("\r\nConstructing resident area...");
         for(k = 0; k < 9; k++)
         {
            if(zones[k] == null)
               FindResidentZone(k, x + x_offset[k], z + z_offset[k]);
         }
      
         gConOut("\r\nSelecting and unswapping resident area...");
         
         //Select the resident area and unswap the zones
         gDeselectAll();
         
         for(k = 0; k < 9; k++)
         {
            if(zones[k] != null)
               gSelectNode(zones[k]);
         }
         
         //Unswap the resident area
         gUnswapSelected();
               
         //if the center zone is valid, deselect the rest and process it
         if(zones[4] != null)
         {
         
               gConOut("\r\n Processing  center zone...");

               gDeselectAll();
               gSelectNode(zones[4]);
               
               //Run the desired tool chain on the current zone
               ProcessCurrentZone();            
         }
         
         gConOut("\r\nSelecting and swapping resident area trail...");
         
         //If we're not at the end of the current scan row, swap the zones on the column from the opposite side of the scan direction,
         //otherwise, swap the zones on the first row (the resident area will move downwards)
         gDeselectAll();
         if(xx < x_size - 1)
         {
            int column;
            if(direction == 1)
               column = 0;
            else
               column = 2;
               
            for(k = 0; k < 3; k++)
            {
               int index = k * 3 + column;
               if(zones[index] != null)
                  gSelectNode(zones[index]);
            }
            
            gConOut("\r\nShifting resident area horizontally...");
         
            //Shift the resident area to the next zone while keeping the zone table consistent
            for(k = 0; k < 3; k++)
            {
               @zones[k * 3 + column] = @zones[k * 3 + 1]; //middle column moves to last column, opposite to scan direction
               @zones[k * 3 + 1] = @zones[k * 3 + 2 - column]; //column on the scan dir moves to the middle column
               @zones[k * 3 + 2 - column] = null;
            }
         }
         else
         {
            for(k = 0; k < 3; k++)
            {
               if(zones[k] != null)
                  gSelectNode(zones[k]);
            }
            
            //Don't shift the resident area horizontally, as it will move downwards
         }
         
         gSwapSelected();
      }
      
      gConOut("\r\nShifting resident area vertically...");
      
      //Shift the resident area downwards
      for(k = 0; k < 3; k++)
      {
         @zones[k] = @zones[3 + k]; //Middle row moves to the first row
         @zones[3 + k] = @zones[6 + k]; //Last row moves to middle row
         @zones[6 + k] = null;
      }
      
      //Reverse the scan direction
      direction = -direction;
   }

   return 0;
}



This script parse the grid row by row and tries to do as little swap/unswap operations as possible. It keeps in memory only a resident area of 3 by 3 zones while processing the middle zone.

Put min_x, min_z, max_x and max_z to the number of your zones in the grid (in the above example I assumed 8 by 8 zones).

Let me know if you need more help.

Regards,
Adrian L.
Back to top
View user's profile Send private message
AD_Dennis
PostPosted: Sat Aug 02, 2008 7:38 pm    Post subject: Reply with quote



Joined: 02 Apr 2008
Posts: 32

Ok, thanks ALicu. This looks very helpful.
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic  Reply to topic Page 1 of 1

Jump to:  



You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Based on a template by Dustin Baccetti
Powered by phpBB © 2001, 2005 phpBB Group