Booking appointments with MySQLi and PHP
Code has to be readable

  if(isset($_POST['slots_booked'])) $slots_booked = mysqli_real_escape_string($link, $_POST['slots_booked']);


Going through this code I really have to focus to try to figure out what is happening, there is no 'flow'. Now add 7 of those and you got some serious reading ahead of you. You are using prepared statements so don't escape your values 2 times, prepared statements protect from sql injection.

Use meaningful english names

Database columns, variable names etc have to be in english and have to tell what they are responsible for.

  $booking_array = array(
  "slots_booked" =&gt; $slots_booked, // not entirely clear what this column stores
  "booking_date" =&gt; $booking_date,
  "name" =&gt; $name,
  "email" =&gt; $email,
  "Åkeri" =&gt; $akeri, // lets open up google translate
  "phone" =&gt; $phone,
  "typ" =&gt; $typ, // no idea what this column stores
  "fri" =&gt; $fri // no idea what this column stores
  );


As @Sumurai8 noted: $booking_array is not even used yet it takes up 30% of the code.

This one is just left there hanging. I suppose $slots_booked are an array of some slots? No idea what those slots represent. Variable name $explode will not help with understanding code it is used in.

 $explode = explode('|', $slots_booked);


Foreach does not start that bad. $explode is array of $slot's, it asks for renaming $explode to $slots. 

What kind values do you expect $slot's to have? Checking empty($slot) does not cut it? 

How short preparation of query is! Just 3 lines of code. It's great isn't it? Not necessarily. You sacrificed code's readability by making it so short. Each parameter should have proper placeholder name =&gt; :name, start =&gt; :start. I would recommend providing bindParam() with type you expect given param to have.

Here we are given another clue as to what $slot might be. It is start of bookings. Maybe instead of $slot something like $booking_start would be more understandable?

foreach($explode as $slot) {

    if(strlen($slot) &gt; 0) {

        $stmt = $link-&gt;prepare("INSERT INTO bookings (date, start, name, email, phone, typ, fri) VALUES (?, ?, ?, ?, ?, ?, ?)");
        $stmt-&gt;bind_param('sssssss', $booking_date, $slot, $name, $email, $phone, $typ, $fri);
        $stmt-&gt;execute();


    } // Close if

} // Close foreach


Below code is example in which way your code can go and be more readable. DB object was taken from here.

class Booking {
    public $start;
    public $name;
    public $akeri;
    public $email;
    public $phone;
    public $typ;
    public $fri;
    public $date;

    public function save() {
        $stmt = DB::prepare("INSERT INTO bookings (date, name) VALUES (:date, :name)");
        $stmt-&gt;bind_param(':date', $this-&gt;date);
        $stmt-&gt;bind_param(':name', $this-&gt;name);
        // rest of attributes
        $stmt-&gt;execute();
    }
}

$bookingDates = explode('|', $_POST['slots_booked']);
foreach($bookingDates as $bookingDate) {
    $booking = new Booking();
    $booking-&gt;name = $_POST['name'];
    // set rest of attributes

    $booking-&gt;save();
}


EDIT

Changed $bookingDetails to $bookingDates