completely rewrote all the code