Randomized objects with limits?

The Idea, is to create a almost empty terrain. It would have Hills, water, etc, already setup on it, but thats it.
I would like to find a way to make a script, maybe attached to the terrain itself, not sure where it would be attached, but the script would load when the level is generated, spawn diffrent things in set numbers, like spawn 50 trees, 20 rocks, etc, and randomly place them around the map. Problem is it would spawn anywhere, no limits, so trying to find a way to tell it to only spawn if the terrain is a certain hieght. The map is at 10y, water ways are at 0, and the hills/mountains are 50 plus there over hand/blending to the lower terrain.
Trying to find a way to make a script that would randomly generate a set of cords within say 100p of the edge so nothing over hangs/grows past the boundries, but to sample the height and if its at 100 or more away from the edge, and the height on the terrain is 10, place the tree, if not find somewhere else. I was using a invis marker, ploped down a cube, made it invisible, attached a script around the lines of

//var centerMark : Transform;
//var preFab : Transform;
//var numberTargets : int;
//var radius : float;

//function Start()
//{/
//var position :Vector3;
//var i : int;
//for(i = 0; i< numberTargets; i++)
//{
//position = Vector3(player.position.x + Random.Range(-radius,radius),0.0f,player.position.z + Random.Range(-radius,radius)); 
//position.y = Terrain.activeTerrain.SampleHeight(position) + Terrain.activeTerrain.transform.position+y; //I had a student move the terrain on me necessating adding the y position of the terrain
//var target = Instantiate(preFab, position, Quatenrion.identity);
//target.transform.position.y = target.transform.position.y + target.transform.collider.bounds.size.y/2; 
//}
//
//}

This sorta works, but then leaves a problem of it still spawns everywhere regardless of water, hill, etc, and since the player can place objects or prefabs down, sometimes it spawns inside other objects. Any ideas on a easy way to work this out?

Make a script where you set x and z boundaries.
Randomize x and z coordinates within these boundaries.
Cast a raycast down from that position and get the height from hit.point.y.
Use hit.point.normal to find out how steep the position is (you dont want to place trees on a steep mountain side i guess?).
Use this in a recursive function until it placed enough trees/stones.

Ok, Logicaly I can understand how that would work, but have no idea how to script that. Most of everything I try to ‘get’ variables from objects tells me it dosent exist or invalid format/type. So if I attach a script to the terrain itself, how can I tell it to Get the X/Z or what ever ones would be the width/length. And how do you use the Raycast? I am completly new to unity, never did scripting myself so trying to learn as I go. Could you show me a sample on how to do what you said and add some comments to explain what is doing what ?

var TerrainCollider : TerrainData;

function SpawnChecker()
{
var Test = TerrainCollider.size;
}

ok that seems to show the dimentions of the terrain its attached to, at least I can get them with a print(Test[0]);
So for finding the Range of the spawning of trees and such, would I assume that 0,0,0 is the center of the terrain? Or is one of the edges the center?

Would I be better doing a radius or a rand based on 0 - size, then check the raycast for hit?
The end would have it running every say 144secs in the game, its going to … maybe, be like 1sec = 10min in game, so atm if my math is right 144secs would be once a day in game.
I am not sure if should put them all together or split them up so one happens say midnight one at noon, or every few hours for the diffrent parts, but its supposed to spawn missing trees/rocks/debris, all trees are spawned as smaller trees, once a day would check for needed trees, once a day would grow trees/crops a little, and several timesa day will change the skybox. Thinking on lag issues, if would be better to put them all in run or seperate or would seperating the code running diffrent parts at diffrent times if that would make it more laggy/less efficent code then just doing it all at once

Use Random.Range(minX, maxX) and Random.Range(minZ, maxZ) to get your values.

Create a new vector: vector = new Vector3(randomX, 200, randomZ). 200 here is just som high Y values, set it to whatever you need.

RaycastHit hit;
if(Physics.Raycast(vector, Vector3.down, out hit, 205))
{
          //Get info in here from hit
          Vector3 worldPosition = hit.point;
          Vector3 worldNormal = hit.normal;
          //.....
}