GEX pattern to match the browser version string within the user agent string. $pattern = '#(?Version|' . $patternBrowser . ')[/ :]+(?[0-9.|a-zA-Z.]*)#'; // Attempt to find version strings in the user agent string. $matches = array(); if (preg_match_all($pattern, $userAgent, $matches)) { // Do we have both a Version and browser match? if (\count($matches['browser']) == 2) { // See whether Version or browser came first, and use the number accordingly. if (strripos($userAgent, 'Version') < strripos($userAgent, $patternBrowser)) { $this->browserVersion = $matches['version'][0]; } else { $this->browserVersion = $matches['version'][1]; } } elseif (\count($matches['browser']) > 2) { $key = array_search('Version', $matches['browser']); if ($key) { $this->browserVersion = $matches['version'][$key]; } } else { // We only have a Version or a browser so use what we have. $this->browserVersion = $matches['version'][0]; } } } // Mark this detection routine as run. $this->detection['browser'] = true; } /** * Method to detect the accepted response encoding by the client. * * @param string $acceptEncoding The client accept encoding string to parse. * * @return void * * @since 1.0 */ protected function detectEncoding($acceptEncoding) { // Parse the accepted encodings. $this->encodings = array_map('trim', (array) explode(',', $acceptEncoding)); // Mark this detection routine as run. $this->detection['acceptEncoding'] = true; } /** * Detects the client rendering engine in a user agent string. * * @param string $userAgent The user-agent string to parse. * * @return void * * @since 1.0 */ protected function detectEngine($userAgent) { if (stripos($userAgent, 'MSIE') !== false || stripos($userAgent, 'Trident') !== false) { // Attempt to detect the client engine -- starting with the most popular ... for now. $this->engine = self::TRIDENT; } elseif (stripos($userAgent, 'Edge') !== false || stripos($userAgent, 'EdgeHTML') !== false) { $this->engine = self::EDGE; } elseif (stripos($userAgent, 'Edg') !== false) { $this->engine = self::BLINK; } elseif (stripos($userAgent, 'Chrome') !== false) { $result = explode('/', stristr($userAgent, 'Chrome')); $version = explode(' ', $result[1]); if ($version[0] >= 28) { $this->engine = self::BLINK; } else { $this->engine = self::WEBKIT; } } elseif (stripos($userAgent, 'AppleWebKit') !== false || stripos($userAgent, 'blackberry') !== false) { if (stripos($userAgent, 'AppleWebKit') !== false) { $result = explode('/', stristr($userAgent, 'AppleWebKit')); $version = explode(' ', $result[1]); if ($version[0] === 537.36) { // AppleWebKit/537.36 is Blink engine specific, exception is Blink emulated IEMobile, Trident or Edge $this->engine = self::BLINK; } } // Evidently blackberry uses WebKit and doesn't necessarily report it. Bad RIM. $this->engine = self::WEBKIT; } elseif (stripos($userAgent, 'Gecko') !== false && stripos($userAgent, 'like Gecko') === false) { // We have to check for like Gecko because some other browsers spoof Gecko. $this->engine = self::GECKO; } elseif (stripos($userAgent, 'Opera') !== false || stripos($userAgent, 'Presto') !== false) { $version = false; if (preg_match('/Opera[\/| ]?([0-9.]+)/u', $userAgent, $match)) { $version = \floatval($match[1]); } if (preg_match('/Version\/([0-9.]+)/u', $userAgent, $match)) { if (\floatval($match[1]) >= 10) { $version = \floatval($match[1]); } } if ($version !== false && $version >= 15) { $this->engine = self::BLINK; } else { $this->engine = self::PRESTO; } } elseif (stripos($userAgent, 'KHTML') !== false) { // *sigh* $this->engine = self::KHTML; } elseif (stripos($userAgent, 'Amaya') !== false) { // Lesser known engine but it finishes off the major list from Wikipedia :-) $this->engine = self::AMAYA; } // Mark this detection routine as run. $this->detection['engine'] = true; } /** * Method to detect the accepted languages by the client. * * @param mixed $acceptLanguage The client accept language string to parse. * * @return void * * @since 1.0 */ protected function detectLanguage($acceptLanguage) { // Parse the accepted encodings. $this->languages = array_map('trim', (array) explode(',', $acceptLanguage)); // Mark this detection routine as run. $this->detection['acceptLanguage'] = true; } /** * Detects the client platform in a user agent string. * * @param string $userAgent The user-agent string to parse. * * @return void * * @since 1.0 */ protected function detectPlatform($userAgent) { // Attempt to detect the client platform. if (stripos($userAgent, 'Windows') !== false) { $this->platform = self::WINDOWS; // Let's look at the specific mobile options in the Windows space. if (stripos($userAgent, 'Windows Phone') !== false) { $this->mobile = true; $this->platform = self::WINDOWS_PHONE; } elseif (stripos($userAgent, 'Windows CE') !== false) { $this->mobile = true; $this->platform = self::WINDOWS_CE; } } elseif (stripos($userAgent, 'iPhone') !== false) { // Interestingly 'iPhone' is present in all iOS devices so far including iPad and iPods. $this->mobile = true; $this->platform = self::IPHONE; // Let's look at the specific mobile options in the iOS space. if (stripos($userAgent, 'iPad') !== false) { $this->platform = self::IPAD; } elseif (stripos($userAgent, 'iPod') !== false) { $this->platform = self::IPOD; } } elseif (stripos($userAgent, 'iPad') !== false) { // In case where iPhone is not mentioned in iPad user agent string $this->mobile = true; $this->platform = self::IPAD; } elseif (stripos($userAgent, 'iPod') !== false) { // In case where iPhone is not mentioned in iPod user agent string $this->mobile = true; $this->platform = self::IPOD; } elseif (preg_match('/macintosh|mac os x/i', $userAgent)) { // This has to come after the iPhone check because mac strings are also present in iOS devices. $this->platform = self::MAC; } elseif (stripos($userAgent, 'Blackberry') !== false) { $this->mobile = true; $this->platform = self::BLACKBERRY; } elseif (stripos($userAgent, 'Android') !== false) { $this->mobile = true; $this->platform = self::ANDROID; /** * Attempt to distinguish between Android phones and tablets * There is no totally foolproof method but certain rules almost always hold * Android 3.x is only used for tablets * Some devices and browsers encourage users to change their UA string to include Tablet. * Google encourages manufacturers to exclude the string Mobile from tablet device UA strings. * In some modes Kindle Android devices include the string Mobile but they include the string Silk. */ if (stripos($userAgent, 'Android 3') !== false || stripos($userAgent, 'Tablet') !== false || stripos($userAgent, 'Mobile') === false || stripos($userAgent, 'Silk') !== false) { $this->platform = self::ANDROIDTABLET; } } elseif (stripos($userAgent, 'Linux') !== false) { $this->platform = self::LINUX; } // Mark this detection routine as run. $this->detection['platform'] = true; } /** * Determines if the browser is a robot or not. * * @param string $userAgent The user-agent string to parse. * * @return void * * @since 1.0 */ protected function detectRobot($userAgent) { if (preg_match('/http|bot|bingbot|googlebot|robot|spider|slurp|crawler|curl|^$/i', $userAgent)) { $this->robot = true; } else { $this->robot = false; } $this->detection['robot'] = true; } /** * Fills internal array of headers * * @return void * * @since 1.3.0 */ protected function detectHeaders() { if (\function_exists('getallheaders')) { // If php is working under Apache, there is a special function $this->headers = getallheaders(); } else { // Else we fill headers from $_SERVER variable $this->headers = array(); foreach ($_SERVER as $name => $value) { if (substr($name, 0, 5) == 'HTTP_') { $this->headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value; } } } // Mark this detection routine as run. $this->detection['headers'] = true; } } Error