I created 10 x 10 TextBoxes and the user should input the words into the relevant TextBoxes for the position of the words. And I save everything into a textfile like this:
Then on WPF side , I read the textfile and populate the TextBoxes in a panel but the problem is that the crossword puzzle has down and across hints that lead you to the answer and each hint will have a number to indicate which is which. However I can't think of a way to link the number's puzzle number to the hints down and across number. This is how it looks like now:
Notice the numbers (I edited them in paint to visualize what I want) beside the across and down, I need that numbers to be displayed.
In my database, I stored the location of the file in a table, and the hints and answer in another table like this:
And this is the hints (across and down) and answer:
I am using Entity framework lambda expressions to retrieve the across and down.
Appreciate any help on this to link the assign the numbers to Across and Down from the puzzle.
This is my code to display the puzzle :
protected void Across()
{
IList<ModelSQL.puzzlecontent> lstAcross = daoPuzzleContent.GetAcross();
foreach (ModelSQL.puzzlecontent lista in lstAcross)
{
Label tbA = new Label();
tbA.Content = lista.Hint;
tbA.Width = Double.NaN;
tbA.BorderBrush = Brushes.CadetBlue;
tbA.BorderThickness = new Thickness(2);
stackPanel1.Width = Double.NaN;
stackPanel1.Children.Add(tbA);
words.Add(lista.Answer);
}
}
protected void AddPuzzle()
{
// foldername of the txt file.
// using (StreamReader reader = File.OpenText((@daoWordPuzzle.GetfileURL())))
string[] fileData = File.ReadAllLines(@"C:\Users\apr13mpsip\Desktop\OneOrganizer\OneOrganizer\WordPuzzle\educational.txt");
string[] lineValues;
int row = 0;
int col;
int hint = 1;
string[][] rowcol = new string[fileData.Length][];
foreach (string line in fileData)
{
lineValues = line.Split(new string[] { "," }, StringSplitOptions.None);
rowcol[row] = new string[lineValues.Length];
col = 0;
foreach (string value in lineValues)
{
rowcol[row][col] = value;
col++;
}
row++;
}
for (int i = 0; i < rowcol.GetLength(0) ; i++)
{
for (int j = 0; j < rowcol[i].GetLength(0) ; j++)
{
int iadd = i+1 < rowcol.GetLength(0) ? i+1 : 100;
int iminus = i-1 >= 0 ? i-1 : 100;
int jadd = j+1 < rowcol.GetLength(0) ? j+1 : 100;
int jminus = j-1 >= 0 ? j-1 : 100;
var self = rowcol[i][j]; // current value
var top = iminus == 100 ? "" : rowcol[iminus][j];
var bottom = iadd == 100 ? "" : rowcol[iadd][j];
var left = jminus == 100 ? "" : rowcol[i][jminus];
var right = jadd == 100 ? "" : rowcol[i][jadd];
//ACROSS HORIZONTAL
if (
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(right) && String.IsNullOrEmpty(bottom) && !String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(right) && String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && !String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left))
)
{
wordAcross = "";
for (int k = 0; k < 10; k++)
{
wordAcross += rowcol[i][k];
if (k == 9)
{
puzzlewordAcross.Add(wordAcross);
// print hello and live
}
}
}
//DOWN VERTICAL
if (
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(top) && !String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(left))
)
{
wordDown = "";
for (int k = 0; k < 10; k++)
{
wordDown += rowcol[k][j];
if (k == 9)
{
puzzlewordDown.Add(wordDown);
// print holy and leducated
}
}
}
//Check Top , Left , Bottom , Right value.
if (
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(top) && !String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && !String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(top) && !String.IsNullOrEmpty(right) && String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && !String.IsNullOrEmpty(top) && !String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(top) && String.IsNullOrEmpty(right) && !String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(left)) ||
(!String.IsNullOrEmpty(self) && String.IsNullOrEmpty(top) && !String.IsNullOrEmpty(right) && String.IsNullOrEmpty(bottom) && String.IsNullOrEmpty(left))
)
{
TextBox tbox = new TextBox();
tbox.Height = 50;
tbox.Width = 50;
tbox.Text = hint.ToString();
wrapPanel1.Children.Add(tbox);
tbox.GotFocus += (source, e) =>
{
if (!string.IsNullOrEmpty(tbox.Text))
{
string Str = tbox.Text.Trim();
double Num;
bool isNum = double.TryParse(Str, out Num);
if (isNum)
tbox.Text = "";
}
else
{
tbox.Text = "";
}
};
hint++;
}
else
{
TextBox tbox2 = new TextBox();
tbox2.Height = 50;
tbox2.Width = 50;
if (String.IsNullOrEmpty(self))
{
tbox2.Background = Brushes.Black;
tbox2.Focusable = false;
}
wrapPanel1.Children.Add(tbox2);
}// end of top bottom left right.
}
}
} // End of AddPuzzle()
Code to display Across and Down :
protected void Down()
{
IList<ModelSQL.puzzlecontent> lstDown = daoPuzzleContent.GetDown();
foreach (ModelSQL.puzzlecontent listd in lstDown)
{
Label tbD = new Label();
tbD.Content = listd.Hint;
tbD.Width = Double.NaN;
tbD.BorderBrush = Brushes.CadetBlue;
tbD.BorderThickness = new Thickness(2);
stackPanel2.Width = Double.NaN;
stackPanel2.Children.Add(tbD);
}
}
protected void Across()
{
IList<ModelSQL.puzzlecontent> lstAcross = daoPuzzleContent.GetAcross();
foreach (ModelSQL.puzzlecontent lista in lstAcross)
{
Label tbA = new Label();
tbA.Content = lista.Hint;
tbA.Width = Double.NaN;
tbA.BorderBrush = Brushes.CadetBlue;
tbA.BorderThickness = new Thickness(2);
stackPanel1.Width = Double.NaN;
stackPanel1.Children.Add(tbA);
words.Add(lista.Answer);
}
}
You may need to re-define your data model here because I think you have failed at the first hurdle - systems analysis. It catches us all out when we just want to write code and always means a big refactor.
Think about your domain here. Crossword puzzles. If we are a reading a newspaper puzzle and you dont know the answer to a clue, what do you say when you you ask a friend.
6 letters, clue is 'blah blah'
...followed by any letters that you already know.
Now we know that the puzzle needs to know how many letters in each answer and that each answer needs a clue. We also know that letters are hidden until you fill them out but we need to know the right answer at some point.
How does the puzzle present itself in the back of the paper? Clues are not written as 1,2,3 etc. They are 4 down, 1 across etc. Now we know that you need some position data stored.
You can achieve this is 2 ways.
1. Have each clue as its own entry complete with text
Clue '1' Direction 'Across' Position '1,1' Answer 'Hello' Description 'Greeting'
Work out the grid size from the entries and position letters accordingly. Pros: Easy to work with. All the information in one place Cons: Possible data corruption. This method can define 2 different letters in the same position.
2. Seperate Entries but answer text in grid
This is very similar to how you have it now but your seperate the text into a CSV grid as you demonstrate in the first screenshot. You then have entries for the clues as in method 1. but omit the 'Answer' field.
Your code will have to :
As for linking the clues to the entry text boxes. Set the Tooltip
property of each textbox
with descriptions of the clues that include the letter.
they got it right.
Finally (and this is probably the bit you want), add the correct number to the entry text box, you have to take advantage on WPF's layout pipeline. Dont just put a textbox in your grid, put another grid in! I'll show you how it should look in XAML, but you may want to generate it in code.
<Grid>
<TextBlock x:Name="TextBlock_NumberLabel"/>
<TextBox x:Name="TextBox_LetterEntry"/>
<Grid>
Use that instead of a plain textbox in any square where you want a number.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With