This method is only useful if you want to allow only weight based shipping methods. Additionally you can give free shipping option also.

We will use woocommerce_package_rates filter, to manipulate the shipping charge based on weight and pass it to woocommerce.

Add below code to you child themes function.php file

add_filter('woocommerce_package_rates', 'devnodes_custom_package_rates', 10, 2);
function devnodes_custom_package_rates($rates, $package)
{

    $weight = WC()->cart->get_cart_contents_weight();

    if ($weight > 5) { // if parcel is very big (>5Kg), then contact customer support
        foreach ($rates as $key => $rate) {
            unset($rates[$key]);
        }
    } else {
        //round the weight up to 0.5 slab
        $rounded_weight = ceil($weight * 2) / 2;

        foreach ($rates as $key => $rate) {
            if ($rates[$key]->label != 'Free shipping') {
                $rates[$key]->cost = $rounded_weight * $rates[$key]->cost;
            }
        }
    }

    return $rates;
}

The above code is very simple and self explanatory. In this filter hook we will multiply the total weight of the cart items and cost of the shipping method and then return $rates to woocommerce.

Now the WooCommerce uses $rates as final shipping cost and charges the customer the same.

If you want more advanced weight based shipping option method then you can check a free and open source plugin for woocommerce developed by us. This plugin is Fast and very light in resource usage at the same times delivers what it’s needed. FYI, This plugin is deployed in may of our customers production woocommerce stores.