Question Logic in class breaking binding

ConsKa

Well-known member
Joined
Dec 11, 2020
Messages
140
Programming Experience
Beginner
So after a bit of a wrangle I managed to write some code that would allow me to read a text file, split it and place it into an array and then bind that array to text boxes - it isn't great, as there are 60 entries in the Array, and splitting them into the textboxes was a pain - but it works. I am able to populate all text boxes with the correct data from a text file and the numbers in the text file do not change - it is always 60.

C#:
List<string> Entries = new List<string>();

string DS1 = fn.CombinedName("DataSet1.txt");

            if (File.Exists(DS1))
            {
                var lines = File.ReadAllLines(DS1);
                
                Entries= lines.SelectMany(x => x.Split(new[]
                {
                    ','
                }, StringSplitOptions.None)).ToList();
            
            }            
TimeKeeper.DataContext = this;

I was then able to bind a text box to the output in xaml like so:

C#:
Text="{Binding Entries [0]}"
Text="{Binding Entries [5]}"

This is all in a grid called TimeKeeper.

There are 5 entries per line, so 0 & 5 is the first of x and then the second of x.

So trying to follow the proper course, rather than have that in my Main Window code, I created a class, and put the logic in the class.

C#:
public class DataCollection
    {
        public List<string> Populate { get; set; }
        FileName fn = new FileName();

        public List<string> Entries()
        {
            string DS1 = fn.CombinedName("DataSet1.txt");

            if (File.Exists(DS1))
            {
                var lines = File.ReadAllLines(DS1);
                
                Populate = lines.SelectMany(x => x.Split(new[]
                {
                    ','
                }, StringSplitOptions.None)).ToList();
            }
            return Populate;
        }
    }

Then in the main window

C#:
List<string> Entries = new List<string>();

private void Reload()
        {
            DataCollection dc = new DataCollection();
            dc.Entries();

            Entries = dc.Populate;

            TimeKeeper.DataContext = Entries;
        }

Using breakpoints, I can see that Entries has 60 entries, as it is supposed to have, and the binding is the same - I just don't know why it isn't working. I tried

C#:
TimerKeeper.DataContext = this;

as it was previously, but that didn't work either.

Am I missing something that I now need to bind this after moving the logic to a class?
 
Odd naming property Populate and a method Entries, should probably be opposite.

Binding is for {DataContext}.Entries so the object you set as DataContext is expected to have a Entries property.
If using the List as DataContext you can do {Binding [0]}
 
Odd naming property Populate and a method Entries, should probably be opposite.

Binding is for {DataContext}.Entries so the object you set as DataContext is expected to have a Entries property.
If using the List as DataContext you can do {Binding [0]}
Thanks, will try it - tried it, it works - thanks. I think I understand why as well, simply I have already defined the List onto the TimeKeeper so I don't need to redefine it again in the binding, as it knows it is already there.

My naming conventions usually fall apart as I attempt different things to try and find solutions, and things get moved around and then renamed because the thing here is not there and I need a new thing here....I usually go back and re-name stuff once I get it all working so I can follow what a little easier when I read it in a month.
 
Out of curiosity: why are you combining all the lines from your data set into a single one dimensional array of 60 items, but presenting the data as 12 rows of 5 items?

Does the data in the file already come as 12 lines of 5 comma separated items?

What is the significance of the 5 columns and the 12 rows? Would this data be better presented in a data grid or a list view?
 
Out of curiosity: why are you combining all the lines from your data set into a single one dimensional array of 60 items, but presenting the data as 12 rows of 5 items?

Does the data in the file already come as 12 lines of 5 comma separated items?

What is the significance of the 5 columns and the 12 rows? Would this data be better presented in a data grid or a list view?
I created the file as 12 lines of 5 comma separated items. The file initially is 12 lines of 4 commas alone - all blank.

Items are added and removed, but not necessarily in order. So item 1, is there, item 2 is removed, item 3 is there. I need it to load in the same order, including the blank. By using the comma delimited file I was able to include blanks. I wasn't sure I could do that using any other method?

The 5 columns in the text file each correspond to a TextBox on the UI, for which there are 12 rows of 5 textboxes, these are populated by the user - and one by logic - these are 12 'saved' spaces each with a corresponding button. so that the user can recall the data from one of the twelve saved spaces without having to enter all the data again and the logic will be applied to that choice adding the logic to the previous logic result.

There are also 12 buttons on the other end of the UI so that the user can remove an item, should they reach 12 and need to add a new more up to date item - but they do not have to remove them in order, so can pick item 7 out of 12 and that will create a blank in the file at row 7.
 
So a row of 5 items doesn't have any real significance other than your UI also happened to have 5 items per row. And there being 12 rows also has no real significance other than your UI also happened to have 12 rows.
 
So a row of 5 items doesn't have any real significance other than your UI also happened to have 5 items per row. And there being 12 rows also has no real significance other than your UI also happened to have 12 rows.
Well the UI is dictated by the data being collected - Unique ID, job code, name, description, time.

The 12 was really down to how many I could fit on a form comfortably and that a user could keep a handle on and find what they were looking for easily.
 
You can quickly progress with a class with those properties and setting up a grid like this: ListView with a GridView - The complete WPF tutorial
One of the functionalities that I do not currently know how to replicate in WPF was that in WinForms the form size was changed at a press of a button (Maximise / Minimise). At default it only shows the recall buttons and 1 text box (the Unique ID) and the data entry boxes - as that is how it is used most of the time.

The rest were effectively invisible until you maximised the form, at which point the rest of the form could be seen. Just to keep it small and concise.

I am assuming that if I use a Grid View I would have code that limits the Grid view to one column and then upon maximise it would show the rest of the columns.

Which might not be a bad idea given that another functionality was minimising the size of the form when it was working - which I have replicated in WPF by hiding the main form and opening a secondary form of the required minimised size.
 
For editing the DataGrid control is probably a better fit, but the link was just a pointer for defining a structured class instead of anonymous strings in a list.
 
For editing the DataGrid control is probably a better fit, but the link was just a pointer for defining a structured class instead of anonymous strings in a list.

I also considered a Dictionary based on a response that @Skydiver gave in a different thread in relation to a Data Grid question.

That I think might serve my purposes. One step at a time though lol
 
Considering that our OP wants to be able to edit the field values (it's why on the other threads he was talking about hooking 60 different textboxes in WinForms), I think that the DataGrid is more appropriate than the ListView's GridView.

Here's a tutorial from the same place regarding using the DataGrid:
 
Considering that our OP wants to be able to edit the field values (it's why on the other threads he was talking about hooking 60 different textboxes in WinForms), I think that the DataGrid is more appropriate than the ListView's GridView.

Here's a tutorial from the same place regarding using the DataGrid:
Thanks.

Can you store blanks in both of these, not near VS to test - but I will do later.

One of the reasons I was doing it the way I was, is due to the fact that I need to load the data when the app is started. So as to avoid losing a days work, it would write to the text file each time you pressed the 'enter' button. Given the speed that it reads and writes to a text file this isn't really an issue (the data size is tiny).

There was also the issue of having more than 12 items - I was using a convoluted process of writing two text files then deleting from one file, so that when combined I had all entries no matter the number created as DataSetOne has a max of 12 lines.

I will have to read to see how I can get this process to merge into a DataGrid or even a List View.
 
If you put in a blank into the cell, the property bound behind it will have an empty string stored in it. It's up to your code which stores your data back into your text file to ensure that you also make note of that fact when when you serialize your data. Serialization and deserialization would all be a non-issue if you persisted your data as JSON as @Sheepings has already recommended in the past (recall that a JSON file is a text a file, after all), but as I recall you insisted that it had to be a text file and somehow you settled on a comma separated file, but I don't quite recall the reasons for it.
 
Seems very unlikely of me to insist on using something while being advised otherwise - I generally tend to follow the advice given on here in regard to coding - and I may have missed it, but it is the first time I have heard of storing the data in a JSON file. I will have a look at storing in a JSON file and the advantages of that.
 
Back
Top Bottom