private void placeT(theT _theT, int x, int y) { //Moves the enire T structure to a desired co-ordinate system placeWordHoriz2(_theT.horzW, x, y); placeWordVert2(_theT.vertW, x + _theT.horizIndex, y - _theT.vertIndex); }
/// <summary> /// Creates the most nested embedded Crossword puzzle from a string of words /// </summary> private void CreateCrossword() { //STEP1: Initialize a datatable with 100 rows X 100 columns for (int j = 0; j < 100; j++) { DataColumn dc = new DataColumn(j.ToString(), System.Type.GetType("System.String")); dt.Columns.Add(dc); } for (int i = 0; i < 100; i++) { DataRow dr = dt.NewRow(); dt.Rows.Add(dr); } //STEP2: generate a unique pattern of 2 word combination from a string array of words //Example output: //a1.Add("earth,planet"); //a1.Add("planet,space"); //a1.Add("space,mars"); //a1.Add("mars,jupiter"); //a1.Add("jupiter,mercury"); //a1.Add("mercury,galaxy"); List<string> a1 = new List<string>(); string t1 = ""; for (int u = 0; u < abb.Count(); u++) { if (t1 == "") { t1 = abb[u]; } else { t1 = t1 + "," + abb[u]; a1.Add(t1); t1 = abb[u]; } } //STEP3: Initial beginning coordinates in the grid int x = 2; int y = 10; foreach (string a in a1) { //STEP4: Check to see if a T is possible or not theT _T = DetectT(a.Split(',')[0], a.Split(',')[1]); if (_T != null) { //STEP4.1: We know a T is detected. Check which word already exists in the grid location d1 = findWord(a.Split(',')[0]); //vert word location d2 = findWord(a.Split(',')[1]); //horz word if (d1 != null && d2 != null) { //case 1: //If both the words are already in the grid dont do anything //A false combination which is rare to happen //TODO: Log it for weird cases, just in case } else { if (d1 == null && d2 == null) { //None of the words are present in the existing grid //So neither of the word can be joined yet if (l1.Count > 0) { //Few words already exist on the grid int maxDepth = 0; //Calculate the max depth of the puzzle, so far for (int yy = 0; yy < l1.Count; yy++) { if (maxDepth < l1[yy].y) { maxDepth = l1[yy].y; } } //Place the new pair, after a blank row placeT(_T, x, maxDepth + _T.vertW.Length + 1); } else { //The first 2 words coming on an empty grid placeT(_T, x, y); } } else if (d2 == null && d1 != null) { //One word already exists in the grid and another is new if (d1.hAlign == false) //the existing word is vertical { //Check if its possible to place the new word at all //Check if all the necessary spots are available bool couldPlaceIt = placeWordHoriz2(a.Split(',')[1], d1.x - _T.horizIndex, d1.y + _T.vertIndex); if (couldPlaceIt == false) //Sorry can not place it with its pair { //try to place it with all other existing words in the grid for (int u1 = 0; u1 < (l1.Count - 1); u1++) { theT _newT = new theT(); if (l1[u1].hAlign == true) { //existing word is already horiz alligned _newT = DetectT(a.Split(',')[1], l1[u1].word); } else { //existing word on the grid is vert alligned _newT = DetectT(l1[u1].word, a.Split(',')[1]); } if (_newT != null) { location d11 = l1[u1]; if (d11.hAlign == true) //existing word is horizontal { bool couldPlaceIt2 = placeWordVert2(a.Split(',')[1], l1[u1].x + _newT.horizIndex, l1[u1].y - _newT.vertIndex); if (couldPlaceIt2) break; } else { bool couldPlaceIt2 = placeWordHoriz2(a.Split(',')[1], l1[u1].x - _newT.horizIndex, l1[u1].y + _newT.vertIndex); if (couldPlaceIt2) break; } } } } } else //existing word is horizontal { //Repeat the same steps as done for vertical in the if-loop bool couldPlaceIt = placeWordVert2(a.Split(',')[1], d1.x + _T.horizIndex, d1.y - _T.vertIndex); if (couldPlaceIt == false) { //try to place it with other existing words in the grid for (int u1 = 0; u1 < (l1.Count - 1); u1++) { theT _newT = new theT(); if (l1[u1].hAlign == true) { //existing word is already horiz alligned _newT = DetectT(a.Split(',')[1], l1[u1].word); } else { //existing word on the grid is vert alligned _newT = DetectT(l1[u1].word, a.Split(',')[1]); } if (_newT != null) { location d11 = l1[u1]; if (d11.hAlign == true) //existing word is horizontal { bool couldPlaceIt2 = placeWordVert2(a.Split(',')[1], l1[u1].x + _newT.horizIndex, l1[u1].y - _newT.vertIndex); if (couldPlaceIt2) break; } else { bool couldPlaceIt2 = placeWordHoriz2(a.Split(',')[1], l1[u1].x - _newT.horizIndex, l1[u1].y + _newT.vertIndex); if (couldPlaceIt2) break; } } } } } } } } else //No T detected { //STEP4.2: see if the incoming horizontal word forms a T with any other already existing words in the grid string incomingHWord = a.Split(',')[1]; //try to place it with other existing words in the grid for (int u1 = 0; u1 < (l1.Count - 1); u1++) { theT _newT = new theT(); if (l1[u1].hAlign == true) { //existing word is already horiz alligned _newT = DetectT(incomingHWord, l1[u1].word); } else { //existing word on the grid is vert alligned _newT = DetectT(l1[u1].word, incomingHWord); } if (_newT != null) { location d11 = l1[u1]; if (d11.hAlign == true) //existing word is horizontal { bool couldPlaceIt2 = placeWordVert2(a.Split(',')[1], l1[u1].x + _newT.horizIndex, l1[u1].y - _newT.vertIndex); if (couldPlaceIt2) break; } else { bool couldPlaceIt2 = placeWordHoriz2(a.Split(',')[1], l1[u1].x - _newT.horizIndex, l1[u1].y + _newT.vertIndex); if (couldPlaceIt2) break; } } } } } //Delete any empty 2 or more consecutive rows to improve readability DeleteEmptyRows(); dataGridView1.AutoSize = true; dataGridView1.DataSource = dt; }
/// <summary> /// Takes two words as inputs, the first parameter is vertical word and the other is horizontal /// If there are more than 1 common letters between the 2 words, the intersection runs on the leftmost letter of the /// horizantal word. Returns an object of theT /// </summary> /// <param name="Vword1"></param> /// <param name="Hword2"></param> /// <returns></returns> private theT DetectT(string Vword1, string Hword2) { //If there's atleast a single common letter, a T found theT _theT = new theT(); char[] h1 = Vword1.ToCharArray(); char[] h2 = Hword2.ToCharArray(); //There can be more than 1 common letters between any 2 words char[] h1h2 = h1.Intersect(h2).ToArray(); int oldIndex = 0; //HWord2 index string x = ""; if (h1h2.Count() > 0) { for (int i = 0; i < h1h2.Count(); i++) { int index = Hword2.IndexOf(h1h2[i]); if (i == 0) { oldIndex = index; x = h1h2[i].ToString(); } else if (oldIndex > index) { //Pick the left most index of the horizantal word oldIndex = index; x = h1h2[i].ToString(); } } int i2 = Vword1.IndexOfAny(x.ToCharArray()); //Vword1 Index char c = x.ToCharArray()[0]; //The intersecting character //Populate the T object _theT.horizIndex = oldIndex; _theT.horzW = Hword2; _theT.vertIndex = i2; _theT.vertW = Vword1; _theT.intersection = c; return _theT; } //No T formation possible. Not a single character/letter in common return null; }