Data Validation, Complex, based on another sheet - google-sheets

Sample sheet here.
Have 2 sheets; DataTemplate stores the validation keys and DataValidation is the sheet that should include data validation based on said keys.
Eg: DataValidation!B11:E17 is validated against DataTemplate!B11:E17 (please see sample)
Sample validation requirements:
IF coressponding DataTemplate value == -500 then Cell must be blank
IF coressponding DataTemplate value == -200 then Cell must be blank or positive number
IF coressponding DataTemplate value > 0 then Cell must be a number between 0..1 OR a string in [ "A", "B", "C" ]
I've attemped this with formulae like below but other than very simple validation available on the net, I've not been able to make anything work.
=SWITCH(INDIRECT("DataTemplate!D11:E17"),-500,ISBLANK(D11),-200,OR(ISNUMBER(D11),ISBLANK(D11),OR(ISNUMBER(D11),IFERROR(MATCH(D11,SPLIT("A,B,C",","),FALSE),FALSE)>0)
EDIT; solved thanks to Jeremy Kahan (below).
My issue was, I was trying to apply Conditional Formatting rules to Conditional Validation, but apparently they are quite different in terms of their application (I do believe). Eg: you can directly access cells in other sheets, you write a normal formula for the top left cell of the range you are applying to. My actual validation formula is given below.
=SWITCH(WorkArrivals!D11,
-500,ISBLANK(D11),
-400,ISBLANK(D11),
-200,AND(NOT(ISBLANK(D11)),OR(AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|absent|sick|annual|family|domtravel|inttravel|"))))),
-100,OR(ISBLANK(D11),AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|domtravel|inttravel|")))),
AND(NOT(ISBLANK(D11)),OR(AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|absent|sick|annual|family|domtravel|inttravel|")))))
)
Tips:
No way to validate NOT(ISBLANK()) as (it appears) validation is triggered when data is entered ONLY.
Similar to Conditional Formatting, it appears that the whole (applied) range is validated and NOT just the cell that was updated. There is a (background active progress bar) lag (~2s for range(1000 rows, 15 cols) - so use with caution on large ranges. #Google could make this smarter ?

Solved thanks to Jeremy Kahan (below). For the benefit of other users;
My issue was, I was trying to apply Conditional Formatting rules to Conditional Validation, but apparently they are quite different in terms of their application (I do believe). Eg: you can directly access cells in other sheets, you write a normal formula for the top left cell of the range you are applying to. My actual validation formula is given below.
=SWITCH(WorkArrivals!D11,
-500,ISBLANK(D11),
-400,ISBLANK(D11),
-200,AND(NOT(ISBLANK(D11)),OR(AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|absent|sick|annual|family|domtravel|inttravel|"))))),
-100,OR(ISBLANK(D11),AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|domtravel|inttravel|")))),
AND(NOT(ISBLANK(D11)),OR(AND(ISNUMBER(D11),D11>0,D11<1),NOT(ISERROR(SEARCH("|"&D11&"|","|absent|sick|annual|family|domtravel|inttravel|")))))
)
Tips:
No way to validate NOT(ISBLANK()) as (it appears) validation is triggered when data is entered ONLY.
Similar to Conditional Formatting, it appears that the whole (applied) range is validated and NOT just the cell that was updated. There is a (background active progress bar) lag (~2s for range(1000 rows, 15 cols) - so use with caution on large ranges. #Google could make this smarter ?

Related

Google Sheets Conditional Formatting on Individual Cells

I've tried searching low, high, and deep within the crevices of the internet to find a possible solution to this, but have had no luck. My main goal is to highlight individual cells based on a couple criteria. I have a google sheet that tracks jobs based on input from employees. My conditions are:
Date must be before today
Cell must be empty (no input from that day)
Only the cell that is empty should be highlighted
https://docs.google.com/spreadsheets/d/10W9O55QQ31acOj5SyKcE0CXx8S78MZQtY-sRaIKgB7c/edit?usp=sharing
The goal of this is to make cells that did not receive any data stand out. The current formula I have is
=AND(ARRAYFORMULA(ISBLANK($B3:$D3)), ARRAYFORMULA(ISBLANK($I3:$K3)), $A3<TODAY())
But this is only highlighting the entire row, and when a cell in that row is filled, it no longer highlights that row. The yellow row is today's date. Any help in solving this is greatly appreciated!
It's not 100% clear what should be happening with the merged Column E:H. But from the limited data and assigned colors I see in your sheet, try swapping out your current "pink" custom CF rule with this one:
=AND($A3<TODAY(), OR(AND(COLUMN(B3)<=4, B3=""), AND(COLUMN(B3)>=9, B3=""), AND(COLUMN(B3)>4, COLUMN(B3)<9, OR(B3<>"", JOIN("",$B3:$K3)=""))))
You need to set a conditional format rule for each column
I believe here are the conditional format rules you need:
Apply To Range
Formula
A3:A
=AND(OR(ARRAYFORMULA(ISBLANK($B3:$D3)), ARRAYFORMULA(ISBLANK($I3:$K3))), $A3<TODAY()) *Note the OR
B3:B
=AND($A3<TODAY(), ISBLANK($B3))
C3:C
=AND($C3<TODAY(), ISBLANK($C3))
D3:D
=AND($D3<TODAY(), ISBLANK($D3))
I3:I
=AND($I3<TODAY(), ISBLANK($I3))
J3:J
=AND($J3<TODAY(), ISBLANK($J3))
K3:K
=AND($K3<TODAY(), ISBLANK($K3))
The key concept here is that within one rule you cannot specify specific ranges to apply the rule to. Part of the definition of the rule is the range that it applies to. You can have rules that take precedence over certain ranges, but you cannot have two ranges in one rule. You can test many ranges in one rule, but the formatting applies to the whole range the rule is applied to.
Make sure you have deleted previous rules before applying these to make sure they don't take precedence
Reference
Conditional Formatting

Is there a way to conditionally format data validated entries to change the values within the cells themselves?

I have an attendance sheet I'd like to edit that has data validation pertaining to credit applied towards the overall attendance percentage, with a 1 meaning the person was there, .5 for late, 0 for calling off appropriately, -0.5 for calling off late, and -1 for no call not showing. In attempting to equate these numbers to the words associated with them, I'm not seeing a way to either: A) Make this human-readable with the entry of a 0.5 inside of the box being changed to late, but also usable within attendance calculation, or B) be able to pseudo enumerate my list of words to associate them with numbers
I've attempted to use most of the data validation and conditional formatting options, but I'm unfamiliar with the custom code that could be run to make this a possibility.
This is a copy of the sheet: https://docs.google.com/spreadsheets/d/1IXZqySfbED2TCX-yo1aScupdof1WZXhdQ820zlqiMn8/edit?usp=sharing
Under the Attendance tab
paste in B2 and drag down:
=IFERROR(ARRAYFORMULA((SUM(IFERROR(VLOOKUP(TRANSPOSE(C2:2),
'Data Validation'!C:D, 2, 0))/COUNTA(C2:2))*1)))

Condition Formating, how to highlight a cell when it dosn't include text in a list

Good Day
I am wondering what custom formula i should use in condition formatting to highlight a cell when it doesn't include a "part name" i have in a list on sheet2
I want Cell A4:A1000 to turn orange when the text in the cell next to it "is not" on a list in Sheet 2 A2:A100
let me know what additional information you need... sorry
Im currently stuck with something like this....:
F4=indirect('Auto Fill'!A2:A343)
but i need it to not be on the list... which is something that's missing from this formula as well... so maybe:
F4= ISNOT indirect('Autofill'!A2:A343)
This is the inverse of your request - I'll leave it as an exercise to the reader how one would get the opposite.
Basically, you want check if the value of some cell is in the list of valid values. If you were computing this as a sheet value, you would use =COUNTIF. For conditional formatting, the same applies:
=COUNTIF({LOOKUP_RANGE_ABS_REF}, {VAL_TO_CHECK})
=COUNTIF($D$2:$D, B2)
Here's the formula in action:
Note that T-3000 and wheels are not in the "Part List" column, and thus do not match.
Comparing to different worksheet within same workbook
If the data to be compared against is not in the same worksheet, the range reference {LOOKUP_RANGE_ABS_REF} must be wrapped in a call to INDIRECT(), i.e.
=COUNTIF(INDIRECT("{OTHER_WORKSHEET_NAME}!{LOOKUP_RANGE_ABS_REF}"), {VAL_TO_CHECK})
=COUNTIF(INDIRECT("some sheet name!$A$2:$A"), B2)
As per official documentation,
Formulas can only reference the same sheet, using standard notation "(='sheetname'!cell)." To reference another sheet in the formula, use the INDIRECT function.
This is also noted in several other SO questions (albeit using different core formulas besides COUNTIF):
https://stackoverflow.com/a/25753889
https://stackoverflow.com/a/28910087
https://stackoverflow.com/a/36684815
https://stackoverflow.com/a/37634170
(I'm sure there are more.)
Missing from those answers is the caveat that the indirection you've just added is not robust to changes to the value of {OTHER_WORKSHEET_NAME}, e.g. you (or some other editor) changed the actual name of the worksheet.
Unlike traditional entered-on-the-worksheet formulas, there is no "run-time" reference link that will update the static text value you had to enter when you created the Conditional Format rule. This lack of reference-updating is actually one of the useful features of INDIRECT(), so don't expect it to ever change.
Furhtermore, the reference break will not be immediately evident. Any items that were added to your formatted range after the name change had their format computed using the broken reference, but any items added before the name changed will keep their current format. Only when the actual range that is wrapped by INDIRECT is edited will any pre-existing conditional formats be recomputed. Thus, you may not notice that the sheet was renamed until you add a new valid part to the list.
Quick kludge, import what you need (I gave it the name List) from sheet2 (you'll have to grant permission), Select ColumnA and apply a CF formula rule of:
=and(A1<>"",iserror(match(B1,IMPORTRANGE(" k e y ","List"),0)))

Glitchy Data Validation Custom Formula

=COUNTIF(IMPORTRANGE("[spreadsheet_id]", "$L:$L"), L2) <= 1
I'm using the above formula in my data validation rule to make sure all values are unique. The sheet referenced is a master list of different ranges combined (also using IMPORTRANGE) so I can check for uniqueness across multiple spreadsheets.
The formula is fine, but the validation does not work normally. I made sure I authorized access to the spreadsheet beforehand, but I've noticed some glitchy behavior. When I take that same formula and put it in a cell on the sheet and then resave the data validation rule, it somehow seems to get it working. But when I remove it again, it doesn't.
Is this normal behavior? Do I have to have a cell with the same formula on my sheet for it to work?

Exporting values of unchecked items in Google Forms checklist

Using Google Forms checkboxes to collect survey responses into a Sheets doc, I find that I can only get the values of checked lines to fill the spreadsheet.
I'm trying to get the unchecked CheckBox values to fill a different cell in the spreadsheet as well, has anyone found out a way to do this?
I'd appreciate any help!
I have a way with spreadsheet formulas.
The drawbacks are the necessities of
manual input of all possible options
copying and pasting a formula for each response (can be done in advance, but if not enough formulas are pasted for the number of responses, the sheet will break)
An ideal solution would automatically detect all possible responses, and could theoretically accept an infinite number of responses without breaking and needing maintenance.
With that said, he's an example of what I suggest:
Google Sheet
Google Form
All possible options on the form must be typed into cells A2:A
cells B2:B show comma+spaces if the corresponding cell in A2:A is not blank, with =arrayformula(if(isblank(A2:A),"",", ")). These commas and spaces are needed later in a concatenate().
Raw data from the Form Responses spreadsheet was brought into D2:E with =arrayformula('Form Responses 1'!A2:B)
G2:G holds the important formulas. They must be copied and pasted to each individual cell for each row.
First, all possible responses in $A$2:$B are filtered based on if the cell in column A can be found in the text in column E.
=filter($A$2:$B,arrayformula(iserror(search($A$2:$A,E2))))
Next, some error catching. I added an iferror() to catch a "N/A, no results found in filter evaluation", and an if(isblank(),"",) to catch if no timestamp is in column D meaning no response was recorded in this row.
=if(isblank(D2),"",iferror(filter($A$2:$B,arrayformula(iserror(search($A$2:$A,E2)))),""))
Finally, do a concatenate() to pull the values and the comma+spaces all into one string inside one cell.
=concatenate(if(isblank(D2),"",iferror(filter($A$2:$B,arrayformula(iserror(search($A$2:$A,E2)))),"")))
Oh, and if you don't like the comma+space being the last characters in the string, in J2:J I did a =arrayformula(iferror(left(H2:H,len(H2:H)-2),"")) which cuts off the last 2 characters of the string in column H.
If I come up with a better solution, I'll let you know. It's an interesting puzzle to solve.

Resources