I would like to know why the following shows an empty dialog box:
testvar="hello" & zenity --info --text "${testvar}"
While this works:
testvar="hello"; zenity --info --text "${testvar}"
The & does not concatenate commands. It runs the preceding command in a subshell in the background and immediately returns control to the foreground shell.
Given a variation on your scenario:
testvar="hello" & echo "testvar=$testvar"
the assignment is run in a subshell and therefore cannot affect the parent, which continues immediately with the next command, echo.
The semicolon, ;, is a command separator and can be considered equivalent to a newline.
For more interest consider these further variations:
a=apple; a=avocado & echo "a=$a"
a=apple; ( a=avocado; echo "## a=$a" ) & sleep 2; echo "a=$a"
Finally just a nitpick to point out that although these are variables, none of them are necessarily environment variables. (You can list those with env.)