The basic idea of dynamic branch prediction is that we can maintain a table containing a guess as to whether a branch should be taken on each instruction. The text gives one implementation; here's another.
The text's implementation is just based on the idea of having a lookup table containing a guess as to whether a branch should take place or not. The idea is that if you have to wait past the ID stage to determine whether a branch should be taken or not, but you can generate the target address on the ID stage, you can accelerate the process by passing the prediction bit in with the instruction and deciding whether to take the branch based on the prediction bit. If you guessed wrong, you flush the pipeline.
We can actually be more clever than that. Instead of looking up a bit containing a prediction of whether or not we will take a branch, we can look up both the prediction and the branch target. If we do that, we can do a branch prediction and even look up the target before we know whether we actually need to branch or not.