Media_handle_upload with custom upload folder?

If I’m not mistaken, then it should be possible. You want to use media_handle_upload(), which calls wp_handle_upload() to handle the file upload. wp_handle_upload() on itself won’t be helpful, especially because it is pretty much just a wrapper for _wp_handle_upload(). It’s not the end yet, because inside _wp_handle_upload() the function wp_upload_dir() is called, where we find the hook upload_dir:

/**
 * Filters the uploads directory data.
 *
 * @since 2.0.0
 *
 * @param array $uploads Array of upload directory data with keys of 'path',
 *                       'url', 'subdir, 'basedir', and 'error'.
 */
$uploads = apply_filters( 'upload_dir', $cache[ $key ] );

The upload_dir filter can be used to alter the upload path. For this we need a function:

function wpse_custom_upload_dir( $dir_data ) {
    // $dir_data already you might want to use
    $custom_dir="custom";
    return [
        'path' => $dir_data[ 'basedir' ] . "https://wordpress.stackexchange.com/" . $custom_dir,
        'url' => $dir_data[ 'url' ] . "https://wordpress.stackexchange.com/" . $custom_dir,
        'subdir' => "https://wordpress.stackexchange.com/" . $custom_dir,
        'basedir' => $dir_data[ 'error' ],
        'error' => $dir_data[ 'error' ],
    ];
}

Then you can make use of it like this:

// changing the directory
add_filter( 'upload_dir', 'wpse_custom_upload_dir' );
// uploading
$upload = media_handle_upload( 'some_upload', $post_id );
// remove so it doesn't apply to all uploads
remove_filter( 'upload_dir', 'wpse_custom_upload_dir' );

All of this is more or less exemplary, but I’m sure you get the drift. For further details please take a look into the documentation pages I linked, there you can go through the source code as well.