I want to get data out of a specific cell in a DBGrid ? How can I do this in Delphi 7 ? I know with a Stringgrid it was easy you only used StringGrid1.Cells[2,1] if you wanted to show to row 2 column 1, but is there any way to accomplish this with a DBGrid ?
The TDBGrid doesn't contain any data; that comes from the connected TDataSet. So to retrieve information, you read the database itself. The current row in the DBGrid is the current record (row) in the DataSet, and the column is the TField connected to the column in that row.
So if you want to read from the third column in the grid, and that column is attached to a field named 'Customer' in the dataset, you'd just read that field:
Customer := DBGrid1.DataSource.DataSet.FieldByName('Customer').AsString;
Or, of course better (since you should have access to the dataset directly in your code):
Customer := CustomerTable.FieldByName('Customer').AsString;
Related
We use a sheet to look up information. There are 936 rows and will get more as time goes on, however the query returns a blank result (as it should) after row 600, how do i change what the search/lookup area so it will search the whole table on a separate sheet and return the results?
=IFERROR(IF($D$5=""," ",INDEX(allvehicles2,(MATCH($D$5,indexes2,0)),7))," ")
Tried to alter the selection and even moving to another sheet but would not return the results.
If you are able to, try using Tables with the XLOOKUP function.
It simplifies the formula and the table will automatically grow as data is added to it.
This ensures that the formula will use all the data.
Make sure that the data you are using to lookup against is continuous.
That is no empty rows or columns.
Ensure that it has headings.
Turn it into a table by selecting it and pressing Ctrl + T.
You can change the name of your table by selecting the data and not the headers.
Then use the Name box to change the name.
Then use the XLOOKUP function, with the lookup_array and return_array values each being a column in the table. If the value is not found, an empty string will be returned.
Formula structure
=XLOOKUP(lookup_value, lookup_array, return_array, [if_not_found])
Example formula based on the screenshot
=XLOOKUP(A2,MyTableName[Key],MyTableName[Value 6],"")
My spreadsheet is collecting data from a form
On another tab I'm showing the responses that match "Lesson day" with "Today's date" (in the example, all the lessons are showed).
As you can see, the "e-mail" field is filled out only once.
Is there a way to automatically fill the "e-mail" field in the second tab? Maybe matching the "Student Code" with the "e-mail" fields in the first tab?
I've tried the MATCH() function but it returns only the position. I feel like I need to combine MATCH() with other functions but I have no idea about where to start
EDIT: Having the email adresses on another column would work too.
SOmething like: if the "Student Code" in the 2 tabs matches, show the email adress for that "Student code"
try:
=ARRAYFORMULA(IFNA(VLOOKUP(D4:D, FILTER({form!E2:E, form!G2:G}, form!G2:G<>""), 2, 0)))
change form to match the sheet name of your form sheet
As suggested, I created an auxiliary table (just called Sheet7) and getting closer to the desired result
In A column I used
=UNIQUE(Lessons!E:E)
In column B I used
=INDEX(Lessons!A:M, MATCH(A2,Lessons!E:E,0),7)
Then, on my second spreadsheet, I could get all the e-mail adress using the following formula
=INDEX(Sheet7!A:B, MATCH(D4,Sheet7!A:A,0),2)
I've tried to use ArrayFormula on the auxiliary table
ARRAYFORMULA(if(A2:A="",,INDEX(Lessons!A:M, MATCH(A2:A,Lessons!E:E,0),7)))
But it doesn't work. It shows only the email adress matched from the cell A2, ignoring A3, A4,...
A different approach:
Make an extra column in your form responses sheet called "Student E-mail".(In this example it is column "I")
In row 2 of that column, write the following formula:
=ARRAYFORMULA(IF(ISBLANK(G2:G),VLOOKUP(F2:F,INDIRECT("F$2:G"&ROW(I2:I),TRUE),2),G2:G))
Use that column for the emails in your other tab (hide the original email column)
Update:
Using array formula, you don't have to manually drag & drop. And it keeps going as new rows are added.
Usually MATCH is combined with INDEX
You should build an auxiliary table with one column for names and another for ee-mails.
To build the auxiliary table from the collected data you could use something like this
=UNIQUE(FILTER({Lessons!E:E,Lessons!G:G},LEN(Lessons!G:G)))
The above is better than using a formula for each column as this prevent having mismatching data.
INDEX / MATCH usually doesn't return the "expected" results in an ARRAYFORMULA. Instead use VLOOKUP.
NOTES:
Please bear in mind that every time that you edit a value the formula will be recalculated. If you have a lot of formulas (like when doing a fill down to copy a formula to all the cells in a column) or having an ARRAYFORMULA with open ended references i.e. G2:G this could affect your spreadsheet performance.
If you go for using an ARRAYFORMULA, use ARRAY_CONSTRAIN to limit the number of rows returned by your formula.
Related
How to map values between columns in worksheets
I have a flat file and used conditional split to filter the record into a single row. For example, RecordType == "2" retrieves single row with record having multiple columns say A,B,C,D and E. I want to pass the result of Column C value to a variable. And then to use it to update the table like:
Update tablename
Set A = that variable
Where A is null
Could you please help me in find out the solution.
I would not use the variable but use a Ole DB Command object.
You set the connection.
Then add your SQL from above:
Update tablename Set A = ? Where A is null
The map to Col C.
However, what I might guess you are trying to do is add a column to your other record set that has the detail but no key.
I would use a script component to do this:
Similar to this example:
Importing Grouped Report Data to Database
I use three component to save same data : TDBGRid, TDatasource and a MessageTable.
I set the edition mode for my DBGrid
MessageDBGrid.Options := MessageDBGrid.Options + [dgEditing];
My question is simple but i can't do that : how can display a DBGrid without any row ? At start, i need to display juste the header for fields.
There is no way to display a DBGrid with zero rows. It will always have one data row, even for an empty table, and even with no datasource assigned it shows an empty row (that is one column wide).
See, for instance, this DBGrid, dropped on a new, blank VCL form in a new, empty VCL application with no other controls:
I have a DBLookupComboBox that is wired to a database query. That part is working fine. When I run the program the DBLookupComboBox is populated with the results of the query. I'd like to to see the DBLookupComboBox populated with the first item "Please Select" when the program first runs or when a new item action is initiated. (See below image)
Also, if I'm loading a previously saved database record that had selected Index 2 "Quick Elimination" how would I get the DBLookupComboBox to display that selected entry?
Yes, "Please Select" is index 0 and it is retreived as part of the query.
You could try this (I know you've probably solved it by now, as you asked over 2 years ago), but in case anyone else was interested...
dbluLookup.KeyValue := dbluLookup.ListSource.DataSet.FieldByName(dbluLookup.KeyField).Value;
That simply sets KeyValue to the first record in the ListSource dataset, which should be the row 'Please Select'.
My guess would be that the value of the underlying table field is NULL rather than zero, which tells the DBComboBox that no value has yet been selected and it displays accordingly.
If the value in the table were zero, I thinkg the text in the edit field of the combo would be selected to indicate that, but I may recall this incorrectly.
Anyway, just check for Field1.IsNull (or IsEmpty) and then set it to zero. It does mean that you can no longer distinguish between an "unknown value" (NULL) and "no selected value" (zero), unless you prevent the zero value from making it back into the table...
One way of doing this would be to add 'Please select' to the underlying table from which you are selecting, where the key to this tuple would be 0. Then when you display the combobox and the value of the connected field is 0, 'Please select' would be displayed. Of course, you have to make sure that this value is never selected!
The DBLookupComboBox displays by default the ListField(s) whose KeyField in the ListSource matches the DataField in the DataSource. So, to ensure to display some value for the DataField being NULL, you have to provide a KeyField of NULL in the ListSource. But one could imagine not wanting a NULL value in the underlaying table associated to the ListSource.
One way to circumvent this is to add the NULL value to the dataset behind the ListSource with a UNION SELECT. That should work just fine, since that dataset does not have to be editable.
Now, to assure this special dataset is only available when you are adding a new record to the dataset associated to the DataSource, manage the query for ListSource.DataSet in DataSource.OnStateChange. When DataSource.State = dsInsert, then update ListSource.DataSet.
Modification for Steve Childs answer in TwwDBLookupCombo, InfoPower component
cboFilterTravel1.LookupValue := cboFilterTravel1.LookupTable.FieldByName(cboFilterTravel1.LookupField).Value;
Thanks Steve It's works for me