I think the easiest way to do this is to have separate objects that do the "attack" collisions. Your character would probably use a rectangle for collisions normally in order to keep things smooth(as is taught in platforming tutorials). You can take the exact frames of animation for the attack, and quickly brush out(draw) the parts that would do the attack, and make that a separate sprite, but the same size and origin as the character. You would do this for each attack. Then, when the character does that attack, you spawn an object that uses that drawn out collider sprite(invisible but collideable, maybe drawn in debug mode). Then the characters can test collision for those objects only. The object would need to destroy itself upon finishing the animation. You could likely use a single object that just picks a different sprite based on the attack, and when it is created it would have a variable set(by the character object) that determines the strength of the attach.
I would keep one object for this, and each character would have "attack" sprites. The sprites would all be separate, and only a few frames depending on how long the attack lasts.
About creating the sprites for the attacks, you could easily do it with GMStudio's sprite editor. I would duplicate the sprite for the attack first. You might need to cut out frames that are part of the animation but not part of the actual collision portions of the attack, though how you manage that depends on where you create the object. If you do it right at the beginning of the attach, you won't be able to cut out the first frames because you need it to sync up, though the last frames you could cut out while the (example) fighter's fist is coming back, as that part would no longer do any damage. Then, you could easily use whatever drawing tools you like, squares, flood fills, whatever, for each frame of animation, making everything else transparent/empty, but the fist/staff/whatever be the same. You could also make those things any color you want(for debug purposes), but whatever parts that should collide need to be something, while the parts that don't should be transparent.
Last detail I mention, the sprites for this would need to use pixel perfect collision with this method. Normally we frown on pixel perfect collision, not only due to performance, but because it can make things jittery if you use it form locomotion in platformers, etc... But for this purpose, you need it for accuracy, and since it isn't actually being used for movement at any time, it won't create jitter. You are only using it to confirm collisions for attacks, and you likely only have a few characters going at a time, so performance isn't an issue. In fact, with modern computers, I would honestly say even with more extreme situations the performance is probably fine, though depending on your target PC specs you would want to do some tests before going ahead with it if you DO want extreme situations, especially if you are considering mobile or HTML5 exports.