Looks good. Two notes:
- You explicitly call GetWindowLongPtrW(); you shouldn't need to do this, especially as you don't explicitly call the other wide-character overloads. Just call GetWindowLongPtr(). Needing to explicitly call the *W or *A variant of some Win32 function is usually a sign you're doing something tricky (this is not) or something wrong.
- Instead of passing 0 to GetWindowLongPtr (or SetWindowLongPtr), consider passing the constant GLWP_USERDATA. Passing a value >= 0 is asking to retrieve sizeof(LONG_PTR) worth of data from the "extra" memory you asked the API to allocate when you created the window style (via the cbWndExtra field)... which most people never do. If you've actually done that, great. But if you haven't done that, you're reading from and writing to garbage memory which is likely to crash you soon or later. Using GLWP_USERDATA is, in my experience, more common than manually bothering to allocate extra instance data.