Network Planning
Detailed Description
This is an example of how to use the WinProp API for network planning. The full example is distributed with the installation.#include <stdio.h> #include <string> #include <iostream> #include <cstring> #include "network_planning.h" #ifndef API_DATA_FOLDER #define API_DATA_FOLDER "../../api/winprop/data/" #endif // !API_DATA_FOLDER #define SERVICES_LTE 13 #define MAX_TRX 3 int main(int argc, char** argv) { /* ------------------ network planning parameters for LTE -------------------- */ double AntennaX[MAX_TRX] = { 5.920, 63.860, 63.400 }; double AntennaY[MAX_TRX] = { 6.240, -22.870, 12.610 }; char AntennaName[MAX_TRX][500] = { "Site 1", "Site 2", "Site 3" }; int MapIndex[MAX_TRX]; WinProp_Result *MaxThroughput = NULL, *MaxSNIR = NULL; WinProp_Result PropResults[MAX_TRX]; WinProp_Callback Callback; WinProp_Structure_Init_Callback(&Callback); WinProp_Antenna Antenna[MAX_TRX]; for (size_t i = 0; i < MAX_TRX; i++) { WinProp_Structure_Init_Antenna(&Antenna[i]); WinProp_Structure_Init_Result(&PropResults[i]); } WinProp_Carrier Carrier; WinProp_Structure_Init_Carrier(&Carrier); int Signal_for_MIMO = -1, Stream_for_MIMO = -1; char ProjectName[200]; double Frequency = 1800.0; int NrPredictionHeights = 1; double PredictionHeightsMulti[2] = { 1.5, 5.2}; int Error = 0; int ProjectHandle = 0; NrPredictionHeights = sizeof(PredictionHeightsMulti)/sizeof(PredictionHeightsMulti[0]); /* Open new network project based on .wst file */ if (Error == 0) { Error = WinProp_Net_Project_Open_WST(&ProjectHandle, API_DATA_FOLDER "airInterfaces/5G FDD.wst", NULL); } if (Error == 0) { Error = WinProp_Net_Project_Para_Get(ProjectHandle, NET_PARA_PROJECTNAME, NULL, NULL, ProjectName); } /* Set resolution for result matrix. */ if (Error == 0) { double ParaValue = 1.0; Error = WinProp_Net_Project_Para_Set(ProjectHandle, NET_PARA_RESOLUTION, &ParaValue, NULL, NULL); } /* Set size of area: Automatic mode. */ if (Error == 0) { int IntValue = 0; Error = WinProp_Net_Project_Para_Set(ProjectHandle, NET_PARA_AREA_MODE, NULL, &IntValue, NULL); } /* Set paths for additional output in WinProp file format. */ if (Error == 0) { Error = WinProp_Net_Project_Para_Set(ProjectHandle, NET_PARA_OUTPUT_WINPROP, NULL, NULL, API_DATA_FOLDER "output/network_planning"); } /* Compute wave propagation for three transmitters */ /* Init. antennas and results */ int maxTRX = MAX_TRX; int NrCarriers = 0; Error = WinProp_Net_Project_Para_Get(ProjectHandle, NET_PARA_CARRIERS, NULL, &NrCarriers, NULL); if (Error == 0) { if (NrCarriers < MAX_TRX) maxTRX = NrCarriers; } for (int Count = 0; Count < maxTRX; Count++) { /* Determine Carrier ID. */ int CarrID = 0; WinProp_Net_Carrier_Para_Get(ProjectHandle, Count, NET_PARA_CARRIER_INDEX, NULL, &CarrID, NULL); /* Determine frequency for antenna. */ WinProp_Net_Carrier_Para_Get(ProjectHandle, CarrID, NET_PARA_CARRIER_FREQ_DL, &Frequency, NULL, NULL); /* Set properties now. */ AntennaPropertiesSet(&Antenna[Count], AntennaX[Count], AntennaY[Count], 2.5, Frequency, AntennaName[Count], Count + 1); // Init of carrier settings WinProp_Structure_Init_Carrier(&Carrier); // set carrier properties Carrier.CarrierID = CarrID; Carrier.SystemID = Signal_for_MIMO; Carrier.MimoID = Stream_for_MIMO; CarrierPropertiesSet(&Antenna[Count], &Carrier); } /* Compute wave propagation for all antennas. */ if (Error == 0) { WavePropagation(maxTRX, Antenna, PropResults, NrPredictionHeights, PredictionHeightsMulti, API_DATA_FOLDER "indoor/IndoorVectordatabase.idb"); } // write propagation results to ascii files if (Error == 0) { for (int Count = 0; Count < maxTRX; Count++) { char PowerResultFile[600]; sprintf(PowerResultFile, API_DATA_FOLDER "output/network_planning/%s Power.txt",Antenna[Count].Name); write_ascii(&PropResults[Count], PowerResultFile); } } /* Now do network planning */ /* Add all propagation maps which have been computed before. */ if (Error == 0) { for (int Count = 0; Count< maxTRX; Count++) { if (Error == 0) { Error = WinProp_Net_PropagationMap_Add(ProjectHandle, &MapIndex[Count], &Antenna[Count], &PropResults[Count]); } } } if (Error == 0) { char HeightString[500]; sprintf(HeightString, "%s", ""); /* Generate string with height values, e.g. a string like "1.5 2.5 3.5". */ for (int Height = 0; Height<NrPredictionHeights; Height++) { /* Add current height to string. */ char thisHeightStr[50]; sprintf(thisHeightStr, "%.2f ", PredictionHeightsMulti[Height]); strcat(HeightString, thisHeightStr); } /* Send heights to WinProp API. */ Error = WinProp_Net_Project_Para_Set(ProjectHandle, NET_PARA_HEIGHT_MULTIPLE, NULL, NULL, HeightString); /* Start computation. */ if (Error == 0) { Callback.Percentage = CallbackProgress; Callback.Message = CallbackMessage; Callback.Error = CallbackError; Error = WinProp_Net_Project_Compute(ProjectHandle, &Callback); } } // ----------------------------------------------------------------------------- // Retrieve results // ----------------------------------------------------------------------------- /* As an example: retrieve max. throughput (kbps) per pixel. */ if (Error == 0) { Error = WinProp_Net_NetworkMap_Get(ProjectHandle, -1, NET_RESULT_MAX_THROUGHPUT, &MaxThroughput); } /* Write max. throughput result to ASCII file. */ if (Error == 0) { char NameForOutput[200]; sprintf(NameForOutput, API_DATA_FOLDER "output/network_planning/%s Max Throughput.txt", ProjectName); write_ascii(MaxThroughput, NameForOutput); } /* As another example: retrieve SNIR (dB) per pixel. */ if (Error == 0) { Error = WinProp_Net_NetworkMap_Get(ProjectHandle, -1, NET_RESULT_SNIR, &MaxSNIR); } /* Write max. throughput result to ASCII file. */ if (Error == 0) { char NameForOutput[200]; sprintf(NameForOutput, API_DATA_FOLDER "output/network_planning/%s Max SNIR.txt", ProjectName); write_ascii(MaxSNIR, NameForOutput); } // -------------------------------------------------------------------------- // Free Memory // -------------------------------------------------------------------------- /* Free propagation results. */ for (int Count = 0; Count < maxTRX; Count++) WinProp_FreeResult(&PropResults[Count]); /* Close network project. */ Error = WinProp_Net_Project_Close(ProjectHandle); return 0; } int _STD_CALL CallbackMessage(const char * Text) { if (Text == nullptr) return 0; std::cout << "\n" << Text; return(0); } int _STD_CALL CallbackError(const char * Text, int Error) { if (Text == nullptr) return 0; std::cout << "\n"; #ifdef __LINUX std::cout << "\033[31m" << "Error (" << Error << "): "; // highlight error in red color #else HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE); SetConsoleTextAttribute(hConsole, FOREGROUND_RED); std::cout << "Error (" << Error << "): "; #endif // __LINUX std::cout << Text; #ifdef __LINUX std::cout << "\033[0m"; // highlight error in red color #else SetConsoleTextAttribute(hConsole, FOREGROUND_RED | FOREGROUND_BLUE | FOREGROUND_GREEN); #endif // __LINUX return 0; } int _STD_CALL CallbackProgress(int value, const char* text) { char Line[200]; sprintf(Line, "\n%d%% %s", value, text); std::cout << Line; return(0); } // Helper functions void write_ascii(const WinProp_Result* Resultmatrix, const char* Filename) { FILE* OutputFile = fopen(Filename,"w"); if (OutputFile) { /* Loop through WinPropall pixels. */ for (int z = 0; z < Resultmatrix->NrHeights; z++) { double Coordinate_Z = Resultmatrix->Heights[z]; for (int x = 0; x < Resultmatrix->Columns; x++) { for (int y = 0; y < Resultmatrix->Lines; y++) { /* Compute real coordinates. */ double Coordinate_X = Resultmatrix->LowerLeftX + ((double)x + 0.5) * Resultmatrix->Resolution; double Coordinate_Y = Resultmatrix->LowerLeftY + ((double)y + 0.5) * Resultmatrix->Resolution; /* Check if pixel was computed or not */ if (Resultmatrix->Matrix[z][x][y] > -1000) fprintf(OutputFile, "%.2f\t%.2f\t%.2f\t%.2f\n", Coordinate_X, Coordinate_Y, Coordinate_Z, Resultmatrix->Matrix[z][x][y]); } } } /* Close file. */ fclose(OutputFile); } else printf("\nCould not open the File: %s for writing.\n",Filename); } void AntennaPropertiesSet( WinProp_Antenna *Antenna, double CoordinateX, double CoordinateY, double Height, double Frequency, const char *Name, int Id) { Antenna->Longitude_X = CoordinateX; Antenna->Latitude_Y = CoordinateY; Antenna->Height = Height; Antenna->Power = 20.0; Antenna->PowerMode = WINPROP_POWER_OUTPUT; Antenna->Frequency = Frequency; sprintf(Antenna->Name, "%s", Name); Antenna->Model = WINPROP_MODEL_COST231; Antenna->Id = Id; } void CarrierPropertiesSet(WinProp_Antenna *Antenna, const WinProp_Carrier *Carrier) { Antenna->Carriers.CarrierID = Carrier->CarrierID; Antenna->Carriers.SystemID = Carrier->SystemID; Antenna->Carriers.MimoID = Carrier->MimoID; } // Wave propagation void WavePropagation( int NumberAntennas, const WinProp_Antenna *Antenna, WinProp_Result *Result, int NrHeights, const double *Heights, const char* database) { int PredictionHandle; WinProp_Area Area; WinProp_Scenario Scenario; WinProp_Callback Callback; WinProp_Result *DummyResult; int Error, Count; WinProp_Legend Legend; WinProp_Additional WinPropMore; WinProp_Propagation_Results OutputResults; // init Error = 0; PredictionHandle = 0; WinProp_Structure_Init_Area(&Area); WinProp_Structure_Init_Scenario(&Scenario); WinProp_Structure_Init_Callback(&Callback); WinProp_Structure_Init_Legend(&Legend); WinProp_Structure_Init_Additional(&WinPropMore); WinProp_Structure_Init_Propagation_Results(&OutputResults); // Open scenario Scenario.Scenario = WINPROP_SCENARIO_INDOOR; sprintf(Scenario.VectorDatabase, "%s", database); Callback.Percentage = CallbackProgress; Callback.Message = CallbackMessage; Callback.Error = CallbackError; /* Open new project. */ if (Error == 0) { Error = WinProp_Open(&PredictionHandle, &Scenario, &Callback); } /* Define area */ if (Error == 0) { /* Defintion of area. */ Area.Heights = (double*)malloc(sizeof(double) * NrHeights); if (Area.Heights != nullptr) { Area.NrHeights = NrHeights; for (int C = 0; C < NrHeights; C++) Area.Heights[C] = Heights[C]; } Area.LowerLeftX = -4.680001; Area.LowerLeftY = -44.200001; Area.UpperRightX = 101.399999; Area.UpperRightY = 42.799999; Area.Resolution = 1.0; } /* Write additional results */ WinPropMore.OutputResults = &OutputResults; sprintf(OutputResults.ResultPath, "%s", API_DATA_FOLDER "output/network_planning"); // Output data directory OutputResults.FieldStrength = 1; // ------------------------------------------------------------------------ // Compute wave propagation // ------------------------------------------------------------------------ for (Count = 0; Count < NumberAntennas; Count++) { if (Error == 0) { DummyResult = NULL; Error = WinProp_Predict(PredictionHandle, &Antenna[Count], &Area, NULL, 0, NULL, &WinPropMore, &DummyResult, NULL, NULL, NULL, NULL, NULL, NULL); if (Error == 0) { /* Copy result. */ WinProp_CopyResult(&Result[Count], DummyResult); } else { /* Error during prediction. Print error message. */ printf("\n\nSimulation returned with Error %d\n\n",Error); } } } // Free memory if (Area.Heights) free(Area.Heights); // Close project WinProp_Close(PredictionHandle); }