OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
68 if (*currentDescriptorEnd == 'x') { | 68 if (*currentDescriptorEnd == 'x') { |
69 if (result.foundDescriptor()) | 69 if (result.foundDescriptor()) |
70 return false; | 70 return false; |
71 result.scaleFactor = charactersToFloat(currentDescriptorStart, descr
iptorLength, &isValid); | 71 result.scaleFactor = charactersToFloat(currentDescriptorStart, descr
iptorLength, &isValid); |
72 if (!isValid || result.scaleFactor < 0) | 72 if (!isValid || result.scaleFactor < 0) |
73 return false; | 73 return false; |
74 } else if (RuntimeEnabledFeatures::pictureSizesEnabled() && *currentDesc
riptorEnd == 'w') { | 74 } else if (RuntimeEnabledFeatures::pictureSizesEnabled() && *currentDesc
riptorEnd == 'w') { |
75 if (result.foundDescriptor()) | 75 if (result.foundDescriptor()) |
76 return false; | 76 return false; |
77 result.resourceWidth = charactersToInt(currentDescriptorStart, descr
iptorLength, &isValid); | 77 result.resourceWidth = charactersToInt(currentDescriptorStart, descr
iptorLength, &isValid); |
78 if (!isValid || result.resourceWidth < 0) | 78 if (!isValid || result.resourceWidth <= 0) |
79 return false; | 79 return false; |
80 } | 80 } |
81 } | 81 } |
82 if (isEmptyDescriptor) | 82 if (isEmptyDescriptor) |
83 result.scaleFactor = 1.0; | 83 result.scaleFactor = 1.0; |
84 return result.foundDescriptor(); | 84 return result.foundDescriptor(); |
85 } | 85 } |
86 | 86 |
87 // http://www.whatwg.org/specs/web-apps/current-work/multipage/embedded-content-
1.html#processing-the-image-candidates | 87 // http://www.whatwg.org/specs/web-apps/current-work/multipage/embedded-content-
1.html#processing-the-image-candidates |
88 template<typename CharType> | 88 template<typename CharType> |
(...skipping 26 matching lines...) Expand all Loading... |
115 } else { | 115 } else { |
116 // 7. Collect a sequence of characters that are not "," (U+002C) cha
racters, and let that be descriptors. | 116 // 7. Collect a sequence of characters that are not "," (U+002C) cha
racters, and let that be descriptors. |
117 skipWhile<CharType, isHTMLSpace<CharType> >(position, attributeEnd); | 117 skipWhile<CharType, isHTMLSpace<CharType> >(position, attributeEnd); |
118 const CharType* descriptorsStart = position; | 118 const CharType* descriptorsStart = position; |
119 skipUntil<CharType, isComma<CharType> >(position, attributeEnd); | 119 skipUntil<CharType, isComma<CharType> >(position, attributeEnd); |
120 const CharType* descriptorsEnd = position; | 120 const CharType* descriptorsEnd = position; |
121 if (!parseDescriptors(descriptorsStart, descriptorsEnd, result)) | 121 if (!parseDescriptors(descriptorsStart, descriptorsEnd, result)) |
122 continue; | 122 continue; |
123 } | 123 } |
124 | 124 |
125 imageCandidates.append(ImageCandidate(attribute, imageURLStart - attribu
teStart, imageURLEnd - imageURLStart, result)); | 125 ASSERT(imageURLEnd > attributeStart); |
| 126 unsigned imageURLStartingPosition = imageURLStart - attributeStart; |
| 127 ASSERT(imageURLEnd > imageURLStart); |
| 128 unsigned imageURLLength = imageURLEnd - imageURLStart; |
| 129 imageCandidates.append(ImageCandidate(attribute, imageURLStartingPositio
n, imageURLLength, result, ImageCandidate::SrcsetOrigin)); |
126 // 11. Return to the step labeled splitting loop. | 130 // 11. Return to the step labeled splitting loop. |
127 } | 131 } |
128 } | 132 } |
129 | 133 |
130 static void parseImageCandidatesFromSrcsetAttribute(const String& attribute, Vec
tor<ImageCandidate>& imageCandidates) | 134 static void parseImageCandidatesFromSrcsetAttribute(const String& attribute, Vec
tor<ImageCandidate>& imageCandidates) |
131 { | 135 { |
132 if (attribute.isNull()) | 136 if (attribute.isNull()) |
133 return; | 137 return; |
134 | 138 |
135 if (attribute.is8Bit()) | 139 if (attribute.is8Bit()) |
136 parseImageCandidatesFromSrcsetAttribute<LChar>(attribute, attribute.char
acters8(), attribute.length(), imageCandidates); | 140 parseImageCandidatesFromSrcsetAttribute<LChar>(attribute, attribute.char
acters8(), attribute.length(), imageCandidates); |
137 else | 141 else |
138 parseImageCandidatesFromSrcsetAttribute<UChar>(attribute, attribute.char
acters16(), attribute.length(), imageCandidates); | 142 parseImageCandidatesFromSrcsetAttribute<UChar>(attribute, attribute.char
acters16(), attribute.length(), imageCandidates); |
139 } | 143 } |
140 | 144 |
141 static ImageCandidate pickBestImageCandidate(float deviceScaleFactor, int effect
iveSize, Vector<ImageCandidate>& imageCandidates) | 145 static ImageCandidate pickBestImageCandidate(float deviceScaleFactor, int effect
iveSize, Vector<ImageCandidate>& imageCandidates) |
142 { | 146 { |
| 147 bool ignoreSrc = false; |
143 if (imageCandidates.isEmpty()) | 148 if (imageCandidates.isEmpty()) |
144 return ImageCandidate(); | 149 return ImageCandidate(); |
145 | 150 |
146 // http://picture.responsiveimages.org/#normalize-source-densities | 151 // http://picture.responsiveimages.org/#normalize-source-densities |
147 for (Vector<ImageCandidate>::iterator it = imageCandidates.begin(); it != im
ageCandidates.end(); ++it) { | 152 for (Vector<ImageCandidate>::iterator it = imageCandidates.begin(); it != im
ageCandidates.end(); ++it) { |
148 if (it->scaleFactor() < 0) | 153 if (it->resourceWidth() > 0) { |
149 it->setScaleFactor((float)it->resourceWidth() / (float)effectiveSize
); | 154 it->setScaleFactor((float)it->resourceWidth() / (float)effectiveSize
); |
| 155 ignoreSrc = true; |
| 156 } |
150 } | 157 } |
151 | 158 |
152 std::stable_sort(imageCandidates.begin(), imageCandidates.end(), compareBySc
aleFactor); | 159 std::stable_sort(imageCandidates.begin(), imageCandidates.end(), compareBySc
aleFactor); |
153 | 160 |
154 unsigned i; | 161 unsigned i; |
155 for (i = 0; i < imageCandidates.size() - 1; ++i) { | 162 for (i = 0; i < imageCandidates.size() - 1; ++i) { |
156 if (imageCandidates[i].scaleFactor() >= deviceScaleFactor) | 163 if ((imageCandidates[i].scaleFactor() >= deviceScaleFactor) && (!ignoreS
rc || !imageCandidates[i].srcOrigin())) |
157 break; | 164 break; |
158 } | 165 } |
159 | 166 |
160 float winningScaleFactor = imageCandidates[i].scaleFactor(); | 167 float winningScaleFactor = imageCandidates[i].scaleFactor(); |
161 unsigned winner = i; | 168 unsigned winner = i; |
162 // 16. If an entry b in candidates has the same associated ... pixel density
as an earlier entry a in candidates, | 169 // 16. If an entry b in candidates has the same associated ... pixel density
as an earlier entry a in candidates, |
163 // then remove entry b | 170 // then remove entry b |
164 while ((i > 0) && (imageCandidates[--i].scaleFactor() == winningScaleFactor)
) | 171 while ((i > 0) && (imageCandidates[--i].scaleFactor() == winningScaleFactor)
) |
165 winner = i; | 172 winner = i; |
166 | 173 |
(...skipping 10 matching lines...) Expand all Loading... |
177 } | 184 } |
178 | 185 |
179 ImageCandidate bestFitSourceForImageAttributes(float deviceScaleFactor, int effe
ctiveSize, const String& srcAttribute, const String& srcsetAttribute) | 186 ImageCandidate bestFitSourceForImageAttributes(float deviceScaleFactor, int effe
ctiveSize, const String& srcAttribute, const String& srcsetAttribute) |
180 { | 187 { |
181 DescriptorParsingResult defaultResult; | 188 DescriptorParsingResult defaultResult; |
182 defaultResult.scaleFactor = 1.0; | 189 defaultResult.scaleFactor = 1.0; |
183 | 190 |
184 if (srcsetAttribute.isNull()) { | 191 if (srcsetAttribute.isNull()) { |
185 if (srcAttribute.isNull()) | 192 if (srcAttribute.isNull()) |
186 return ImageCandidate(); | 193 return ImageCandidate(); |
187 return ImageCandidate(srcAttribute, 0, srcAttribute.length(), defaultRes
ult); | 194 return ImageCandidate(srcAttribute, 0, srcAttribute.length(), defaultRes
ult, ImageCandidate::SrcOrigin); |
188 } | 195 } |
189 | 196 |
190 Vector<ImageCandidate> imageCandidates; | 197 Vector<ImageCandidate> imageCandidates; |
191 | 198 |
192 parseImageCandidatesFromSrcsetAttribute(srcsetAttribute, imageCandidates); | 199 parseImageCandidatesFromSrcsetAttribute(srcsetAttribute, imageCandidates); |
193 | 200 |
194 if (!srcAttribute.isEmpty()) | 201 if (!srcAttribute.isEmpty()) |
195 imageCandidates.append(ImageCandidate(srcAttribute, 0, srcAttribute.leng
th(), defaultResult)); | 202 imageCandidates.append(ImageCandidate(srcAttribute, 0, srcAttribute.leng
th(), defaultResult, ImageCandidate::SrcOrigin)); |
196 | 203 |
197 return pickBestImageCandidate(deviceScaleFactor, effectiveSize, imageCandida
tes); | 204 return pickBestImageCandidate(deviceScaleFactor, effectiveSize, imageCandida
tes); |
198 } | 205 } |
199 | 206 |
200 String bestFitSourceForImageAttributes(float deviceScaleFactor, int effectiveSiz
e, const String& srcAttribute, ImageCandidate& srcsetImageCandidate) | 207 String bestFitSourceForImageAttributes(float deviceScaleFactor, int effectiveSiz
e, const String& srcAttribute, ImageCandidate& srcsetImageCandidate) |
201 { | 208 { |
202 DescriptorParsingResult defaultResult; | 209 DescriptorParsingResult defaultResult; |
203 defaultResult.scaleFactor = 1.0; | 210 defaultResult.scaleFactor = 1.0; |
204 | 211 |
205 if (srcsetImageCandidate.isEmpty()) | 212 if (srcsetImageCandidate.isEmpty()) |
206 return srcAttribute; | 213 return srcAttribute; |
207 | 214 |
208 Vector<ImageCandidate> imageCandidates; | 215 Vector<ImageCandidate> imageCandidates; |
209 imageCandidates.append(srcsetImageCandidate); | 216 imageCandidates.append(srcsetImageCandidate); |
210 | 217 |
211 if (!srcAttribute.isEmpty()) | 218 if (!srcAttribute.isEmpty()) |
212 imageCandidates.append(ImageCandidate(srcAttribute, 0, srcAttribute.leng
th(), defaultResult)); | 219 imageCandidates.append(ImageCandidate(srcAttribute, 0, srcAttribute.leng
th(), defaultResult, ImageCandidate::SrcOrigin)); |
213 | 220 |
214 return pickBestImageCandidate(deviceScaleFactor, effectiveSize, imageCandida
tes).toString(); | 221 return pickBestImageCandidate(deviceScaleFactor, effectiveSize, imageCandida
tes).toString(); |
215 } | 222 } |
216 | 223 |
217 } | 224 } |
OLD | NEW |