form_datetime_local()

function form_datetime_local(string $name, ?string $value = null, array $attributes = []): string

Description

Generates an HTML datetime-local input field with a native browser date and time picker. The input combines date and time selection in a single control and always submits in ISO 8601 format (YYYY-MM-DDTHH:MM).

Browser Display vs Submitted Format: Browsers display datetime-local inputs according to user locale, but always submit in consistent ISO 8601 format (YYYY-MM-DDTHH:MM) that your PHP code can rely on.

Demonstration

Below is the native HTML5 date and time input rendered by form_datetime_local():

The following helper functions handle bidirectional conversion between MySQL DATETIME values and HTML datetime-local inputs. Use them whenever loading values from the database or preparing form submissions for storage.

PHP
function mysql_to_datetime_local(?string $mysql_datetime): string {
  if (empty($mysql_datetime) || $mysql_datetime === '0000-00-00 00:00:00') {
    return '';
  }

  return str_replace(' ', 'T', substr($mysql_datetime, 0, 16));
}

function datetime_local_to_mysql(?string $datetime_local): string {
  if (empty($datetime_local)) {
    return '';
  }

  return str_replace('T', ' ', $datetime_local) . ':00';
}

Parameters

ParameterTypeDescriptionDefaultRequired
$name string The name attribute for the input element N/A Yes
$value string|null The datetime value in YYYY-MM-DDTHH:MM format null No
$attributes array Additional HTML attributes as key-value pairs [] No

Return Value

TypeDescription
stringThe generated HTML datetime-local input element

Understanding the Attributes Array

The $attributes array accepts standard HTML input attributes. For datetime-local inputs, these are particularly useful:

AttributeDescriptionExample Value
min Earliest selectable datetime (YYYY-MM-DDTHH:MM) '2025-01-01T09:00'
max Latest selectable datetime (YYYY-MM-DDTHH:MM) '2025-12-31T17:00'
step Time interval in seconds 900 (15 minutes)
required Field must have a value ['required' => true]
readonly Prevent user editing ['readonly' => true]
disabled Disable the input ['disabled' => true]

Boolean Attributes: Pass true for boolean attributes like required, readonly, or disabled. This generates clean HTML5 syntax: <input required>

Example #1: Basic DateTime-Local Input

PHP
public function create(): void {
    $data['form_location'] = BASE_URL . 'events/submit';
    $this->view('event_form', $data);
}

View file:

View File
<?php
echo form_open($form_location);
echo form_label('Event Start');
echo form_datetime_local('event_start');
echo form_submit('submit', 'Schedule Event');
echo form_close();
?>

Output:

HTML
<input type="datetime-local" name="event_start">

Example #2: DateTime-Local Input with Value and Constraints

PHP
public function create(): void {
    $data['event_start'] = post('event_start', true);
    
    // Business hours constraints: Mon-Fri, 9 AM - 5 PM, starting next week
    $data['min_datetime'] = date('Y-m-d', strtotime('next monday')) . 'T09:00';
    $data['max_datetime'] = date('Y-m-d', strtotime('next friday')) . 'T17:00';
    
    $data['form_location'] = BASE_URL . 'events/submit';
    $this->view('event_form', $data);
}

View file:

View File
<?php
echo form_open($form_location);
echo form_label('Event Start');
$attributes = [
    'min' => $min_datetime,
    'max' => $max_datetime,
    'step' => 1800, // 30-minute intervals
    'required' => true
];
echo form_datetime_local('event_start', $event_start, $attributes);
echo form_submit('submit', 'Schedule Event');
echo form_close();
?>

The example above demonstrates the standard Trongate pattern for form repopulation with datetime constraints. Users can only select datetimes within business hours next week, in 30-minute intervals.

Form Repopulation: After validation errors, use post('field_name', true) in the controller to fetch the submitted value. This returns an empty string if no value was submitted.

Example #3: Storing DateTime-Local in Database

PHP
public function create(): void {
    $data['appointment_time'] = post('appointment_time', true);
    $data['form_location'] = BASE_URL . 'appointments/submit';
    $this->view('appointment_form', $data);
}

public function submit(): void {
    $this->validation->set_rules('patient_name', 'patient name', 'required');
    $this->validation->set_rules('appointment_time', 'appointment time', 'required|valid_datetime_local');
    
    if ($this->validation->run() === true) {
        $data['patient_name'] = post('patient_name', true);
        
        // Convert from YYYY-MM-DDTHH:MM to YYYY-MM-DD HH:MM:SS
        $datetime_from_form = post('appointment_time', true);
        $data['appointment_time'] = str_replace('T', ' ', $datetime_from_form) . ':00';
        
        $this->db->insert($data, 'appointments');
        set_flashdata('Appointment scheduled successfully');
        redirect('appointments/manage');
    } else {
        $this->create();
    }
}

The example above shows the required conversion when storing datetime-local values. The form submits 2025-12-27T14:30, which must be converted to 2025-12-27 14:30:00 for MySQL's DATETIME column.

Format Conversion: Replace the "T" with a space and append ":00" for seconds. This converts the ISO 8601 datetime-local format to MySQL's DATETIME format.

Example #4: Complete Create/Update Pattern with DateTime Conversion

PHP
public function create(): void {
    $update_id = segment(3, 'int');
    
    if ($update_id > 0 && REQUEST_TYPE === 'GET') {
        // Editing existing record
        $record = $this->db->get_where($update_id, 'events');
        $data['event_title'] = $record->event_title;
        
        // Convert from YYYY-MM-DD HH:MM:SS to YYYY-MM-DDTHH:MM
        $datetime_from_db = $record->event_start;
        $data['event_start'] = str_replace(' ', 'T', substr($datetime_from_db, 0, 16));
    } else {
        // New record or validation error
        $data['event_title'] = post('event_title', true);
        $data['event_start'] = post('event_start', true);
    }
    
    $data['form_location'] = BASE_URL . 'events/submit/' . $update_id;
    $this->view('event_form', $data);
}

public function submit(): void {
    $update_id = segment(3, 'int');
    
    $this->validation->set_rules('event_title', 'event title', 'required');
    $this->validation->set_rules('event_start', 'event start', 'required|valid_datetime_local');
    
    if ($this->validation->run() === true) {
        $data['event_title'] = post('event_title', true);
        
        // Convert for database storage
        $datetime_from_form = post('event_start', true);
        $data['event_start'] = str_replace('T', ' ', $datetime_from_form) . ':00';
        
        if ($update_id > 0) {
            $this->db->update($update_id, $data, 'events');
            set_flashdata('Event updated successfully');
        } else {
            $this->db->insert($data, 'events');
            set_flashdata('Event created successfully');
        }
        
        redirect('events/manage');
    } else {
        $this->create();
    }
}

The example above demonstrates bidirectional conversion: when loading from the database, remove seconds and replace space with "T". When saving to the database, replace "T" with space and add ":00".

Model Helper Methods: For applications with many datetime-local fields, consider creating reusable conversion methods in your model to keep controllers clean and conversions consistent.