ViewportMetaData.cpp (3699B)
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #include "ViewportMetaData.h" 8 9 #include "nsCRT.h" 10 #include "nsContentUtils.h" 11 12 using namespace mozilla; 13 using namespace mozilla::dom; 14 15 /* 16 * Helper function for ViewportMetaData::ProcessViewportInfo. 17 * 18 * Handles a single key=value pair. If it corresponds to a valid viewport 19 * attribute, add it to the document header data. No validation is done on the 20 * value itself (this is done at display time). 21 */ 22 static void ProcessViewportToken(ViewportMetaData& aData, 23 const nsAString& token) { 24 /* Iterators. */ 25 nsAString::const_iterator tip, tail, end; 26 token.BeginReading(tip); 27 tail = tip; 28 token.EndReading(end); 29 30 /* Move tip to the '='. */ 31 while ((tip != end) && (*tip != '=')) { 32 ++tip; 33 } 34 35 /* If we didn't find an '=', punt. */ 36 if (tip == end) { 37 return; 38 } 39 40 /* Extract the key and value. */ 41 const nsAString& key = nsContentUtils::TrimWhitespace<nsCRT::IsAsciiSpace>( 42 Substring(tail, tip), true); 43 const nsAString& value = nsContentUtils::TrimWhitespace<nsCRT::IsAsciiSpace>( 44 Substring(++tip, end), true); 45 46 /* Check for known keys. If we find a match, insert the appropriate 47 * information into the document header. */ 48 RefPtr<nsAtom> key_atom = NS_Atomize(key); 49 if (key_atom == nsGkAtoms::height) { 50 aData.mHeight.Assign(value); 51 } else if (key_atom == nsGkAtoms::width) { 52 aData.mWidth.Assign(value); 53 } else if (key_atom == nsGkAtoms::initial_scale) { 54 aData.mInitialScale.Assign(value); 55 } else if (key_atom == nsGkAtoms::minimum_scale) { 56 aData.mMinimumScale.Assign(value); 57 } else if (key_atom == nsGkAtoms::maximum_scale) { 58 aData.mMaximumScale.Assign(value); 59 } else if (key_atom == nsGkAtoms::user_scalable) { 60 aData.mUserScalable.Assign(value); 61 } else if (key_atom == nsGkAtoms::viewport_fit) { 62 aData.mViewportFit.Assign(value); 63 } else if (key_atom == nsGkAtoms::interactive_widget) { 64 aData.mInteractiveWidgetMode.Assign(value); 65 } 66 } 67 68 #define IS_SEPARATOR(c) \ 69 (((c) == '=') || ((c) == ',') || ((c) == ';') || ((c) == '\t') || \ 70 ((c) == '\n') || ((c) == '\r')) 71 72 ViewportMetaData::ViewportMetaData(const nsAString& aViewportInfo) { 73 /* Iterators. */ 74 nsAString::const_iterator tip, tail, end; 75 aViewportInfo.BeginReading(tip); 76 tail = tip; 77 aViewportInfo.EndReading(end); 78 79 /* Read the tip to the first non-separator character. */ 80 while ((tip != end) && (IS_SEPARATOR(*tip) || nsCRT::IsAsciiSpace(*tip))) { 81 ++tip; 82 } 83 84 /* Read through and find tokens separated by separators. */ 85 while (tip != end) { 86 /* Synchronize tip and tail. */ 87 tail = tip; 88 89 /* Advance tip past non-separator characters. */ 90 while ((tip != end) && !IS_SEPARATOR(*tip)) { 91 ++tip; 92 } 93 94 /* Allow white spaces that surround the '=' character */ 95 if ((tip != end) && (*tip == '=')) { 96 ++tip; 97 98 while ((tip != end) && nsCRT::IsAsciiSpace(*tip)) { 99 ++tip; 100 } 101 102 while ((tip != end) && 103 !(IS_SEPARATOR(*tip) || nsCRT::IsAsciiSpace(*tip))) { 104 ++tip; 105 } 106 } 107 108 /* Our token consists of the characters between tail and tip. */ 109 ProcessViewportToken(*this, Substring(tail, tip)); 110 111 /* Skip separators. */ 112 while ((tip != end) && (IS_SEPARATOR(*tip) || nsCRT::IsAsciiSpace(*tip))) { 113 ++tip; 114 } 115 } 116 } 117 118 #undef IS_SEPARATOR