X3DH derives a shared secret using Alice' static identity and fresh ephemeral with Bob's static identity and semi-ephemeral (and optionally, if available a one-time ephemeral).
Alice sends Bob her static identity and a fresh ephemeral along with her encrypted messages. Bob can complete the handshake and read messages Alice sent him. All messages so far may be recoveredcompromised if Bob's static and semi-ephemeral keys have been compromised and the Bob didn't have any one-time ephemeral keys left. Bob may respond and introduce his owna fresh ephemeral key. All messages after this point are safe even if Bob's static key and semi-ephemeral were compromised.
Notice how the hash-ratchet is deriving per-message keys independent to the dh-ratchet, so it does not wait for any round trips as it derives multiple message keys.
For more information you may see the X3DH and Double Ratchet specifications.