My guess would be that the last code you uploaded is crashing. This will take out the native USB when it happens - leaving the computer unable to tell the arduino to restart into bootloader via USB.
As you're uploading the code, right when it finishes compiling (when it's doing that 1200 baud reset thing), press reset on the board. The goal is to time it such that avrdude is trying to talk to it within about 2 seconds of resetting it, so that your bad code doesn't have a chance to run before you upload new code.
This is the price one pays for a native USB bootloader!
On the arduino's that don't have native USB (and instead use a separate usb-serial bridge), no matter what unholy code you upload to the microcontroller, you can't put it into a state where you can't upload different code to it, as a hardware reset is performed - but this comes at the cost of not being able to act as types of USB device other than a serial port (and, in the case of the genuine Uno/Mega, having a serial adapter that is much more fragile than the rest of the board). Native USB gives you that capability - but it's a pain to upload if you write code that crashes the microcontroller (for example, by writing off the end of an array).