/// <summary> /// Generates a spherical projection of the noise map. /// </summary> /// <param name="south">The clip region to the south.</param> /// <param name="north">The clip region to the north.</param> /// <param name="west">The clip region to the west.</param> /// <param name="east">The clip region to the east.</param> public static double[,] GenerateSpherical(ModuleBase module, int width, int height, double south, double north, double west, double east, bool isNormalized = true, int scale = 0) { int ucWidth = width + UC_BORDER * 2; int ucHeight = height + UC_BORDER * 2; double[,] data = new double[ucWidth, ucHeight]; if (east <= west || north <= south) { throw new ArgumentException("Invalid east/west or north/south combination"); } if (module == null) { throw new ArgumentNullException("Generator is null"); } double loe = east - west; double lae = north - south; double xd = loe / ((double)(width - UC_BORDER)); double yd = lae / ((double)(height - UC_BORDER)); double clo = west; List <ParallelProcessHelper> processValues = new List <ParallelProcessHelper>(); // Create parallel process helpers with the values for each sample for (int x = 0; x < ucWidth; x++) { double cla = south; for (int y = 0; y < ucHeight; y++) { processValues.Add(new ParallelProcessHelper(x, y, cla, clo)); cla += yd; } clo += xd; } // now that we have each sample calculated, run through and fetch the noise // Parallelism should be set somwhere from 1 to Processor Count / 2. var rangePartitioner = Partitioner.Create(0, processValues.Count); Parallel.ForEach(rangePartitioner, new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, range => { for (int i = range.Item1; i < range.Item2; i++) { ParallelProcessHelper processHelper = processValues[i]; double sample = GenerateSphericalPoint(module, processHelper.innerValue, processHelper.outerValue, scale); if (isNormalized) { sample = (sample + 1) / 2; } data[processHelper.x, processHelper.y] = sample; } }); return(data); }
/// <summary> /// Generates a cylindrical projection of the noise map. Result will be buffered with extra data /// </summary> /// <param name="angleMin">The maximum angle of the clip region.</param> /// <param name="angleMax">The minimum angle of the clip region.</param> /// <param name="heightMin">The minimum height of the clip region.</param> /// <param name="heightMax">The maximum height of the clip region.</param> public static double[,] GenerateCylindrical(ModuleBase module, int width, int height, double angleMin, double angleMax, double heightMin, double heightMax, bool isNormalized = true, int scale = 0) { int ucWidth = width + UC_BORDER * 2; int ucHeight = height + UC_BORDER * 2; double[,] data = new double[ucWidth, ucHeight]; if (angleMax <= angleMin || heightMax <= heightMin) { throw new ArgumentException("Invalid angle or height parameters"); } if (module == null) { throw new ArgumentNullException("Generator is null"); } double ae = angleMax - angleMin; double he = heightMax - heightMin; double xd = ae / ((double)(width - UC_BORDER)); double yd = he / ((double)(height - UC_BORDER)); double ca = angleMin; List <ParallelProcessHelper> processValues = new List <ParallelProcessHelper>(); for (int x = 0; x < ucWidth; x++) { double ch = heightMin; for (int y = 0; y < ucHeight; y++) { processValues.Add(new ParallelProcessHelper(x, y, ca, ch)); ch += yd; } ca += xd; } var rangePartitioner = Partitioner.Create(0, processValues.Count); Parallel.ForEach(rangePartitioner, new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, range => { for (int i = range.Item1; i < range.Item2; i++) { ParallelProcessHelper processHelper = processValues[i]; double sample = GenerateCylindricalPoint(module, processHelper.innerValue, processHelper.outerValue, scale); if (isNormalized) { sample = (sample + 1) / 2; } data[processHelper.x, processHelper.y] = sample; } }); return(data); }