18e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project/* 2dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * Copyright (C) 2007, 2010 Rob Buis <buis@kde.org> 3dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * 4dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * This library is free software; you can redistribute it and/or 5dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * modify it under the terms of the GNU Library General Public 6dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * License as published by the Free Software Foundation; either 7dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * version 2 of the License, or (at your option) any later version. 8dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * 9dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * This library is distributed in the hope that it will be useful, 10dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * but WITHOUT ANY WARRANTY; without even the implied warranty of 11dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * Library General Public License for more details. 13dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * 14dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * You should have received a copy of the GNU Library General Public License 15dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * along with this library; see the file COPYING.LIB. If not, write to 16dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 17dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch * Boston, MA 02110-1301, USA. 18dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch */ 198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "config.h" 21f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if ENABLE(SVG) 238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SVGViewSpec.h" 248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Document.h" 26f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch#include "SVGNames.h" 278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SVGParserUtilities.h" 288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SVGSVGElement.h" 298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SVGTransformable.h" 308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectnamespace WebCore { 328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 33f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch// Animated property definitions 34f05b935882198ccf7d81675736e3aeb089c5113aBen MurdochDEFINE_ANIMATED_RECT(SVGViewSpec, SVGNames::viewBoxAttr, ViewBox, viewBox) 35f05b935882198ccf7d81675736e3aeb089c5113aBen MurdochDEFINE_ANIMATED_PRESERVEASPECTRATIO(SVGViewSpec, SVGNames::preserveAspectRatioAttr, PreserveAspectRatio, preserveAspectRatio) 36f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 37e14391e94c850b8bd03680c23b38978db68687a8John ReckSVGViewSpec::SVGViewSpec(SVGElement* contextElement) 385ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen : m_contextElement(contextElement) 398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid SVGViewSpec::setTransform(const String& transform) 438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 446b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner SVGTransformable::parseTransformAttribute(m_transform, transform); 458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 47545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdochvoid SVGViewSpec::setViewBoxString(const String& viewBoxStr) 488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 49545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch FloatRect viewBox; 50545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch const UChar* c = viewBoxStr.characters(); 51545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch const UChar* end = c + viewBoxStr.length(); 52545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch if (!parseViewBox(m_contextElement->document(), c, end, viewBox, false)) 53545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch return; 54545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch setViewBoxBaseValue(viewBox); 558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid SVGViewSpec::setPreserveAspectRatioString(const String& preserve) 588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 59d0825bca7fe65beaee391d30da42e937db621564Steve Block SVGPreserveAspectRatio::parsePreserveAspectRatio(this, preserve); 608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid SVGViewSpec::setViewTargetString(const String& viewTargetString) 638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_viewTargetString = viewTargetString; 658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectSVGElement* SVGViewSpec::viewTarget() const 688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 69cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block return static_cast<SVGElement*>(m_contextElement->document()->getElementById(m_viewTargetString)); 708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 720bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdochstatic const UChar svgViewSpec[] = {'s', 'v', 'g', 'V', 'i', 'e', 'w'}; 738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const UChar viewBoxSpec[] = {'v', 'i', 'e', 'w', 'B', 'o', 'x'}; 748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const UChar preserveAspectRatioSpec[] = {'p', 'r', 'e', 's', 'e', 'r', 'v', 'e', 'A', 's', 'p', 'e', 'c', 't', 'R', 'a', 't', 'i', 'o'}; 758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const UChar transformSpec[] = {'t', 'r', 'a', 'n', 's', 'f', 'o', 'r', 'm'}; 768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const UChar zoomAndPanSpec[] = {'z', 'o', 'o', 'm', 'A', 'n', 'd', 'P', 'a', 'n'}; 778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const UChar viewTargetSpec[] = {'v', 'i', 'e', 'w', 'T', 'a', 'r', 'g', 'e', 't'}; 788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectbool SVGViewSpec::parseViewSpec(const String& viewSpec) 808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project const UChar* currViewSpec = viewSpec.characters(); 828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project const UChar* end = currViewSpec + viewSpec.length(); 838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end) 858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 874576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (!skipString(currViewSpec, end, svgViewSpec, WTF_ARRAY_LENGTH(svgViewSpec))) 888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 90cad810f21b803229eb11403f9209855525a25d57Steve Block if (currViewSpec >= end || *currViewSpec != '(') 918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project while (currViewSpec < end && *currViewSpec != ')') { 958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (*currViewSpec == 'v') { 964576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (skipString(currViewSpec, end, viewBoxSpec, WTF_ARRAY_LENGTH(viewBoxSpec))) { 978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != '(') 988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 100545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch FloatRect viewBox; 101545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch if (!parseViewBox(m_contextElement->document(), currViewSpec, end, viewBox, false)) 1028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 103545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch setViewBoxBaseValue(viewBox); 1048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != ')') 1058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1074576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang } else if (skipString(currViewSpec, end, viewTargetSpec, WTF_ARRAY_LENGTH(viewTargetSpec))) { 1088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != '(') 1098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project const UChar* viewTargetStart = ++currViewSpec; 1118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project while (currViewSpec < end && *currViewSpec != ')') 1128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end) 1148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project setViewTargetString(String(viewTargetStart, currViewSpec - viewTargetStart)); 1168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else 1188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else if (*currViewSpec == 'z') { 1204576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (!skipString(currViewSpec, end, zoomAndPanSpec, WTF_ARRAY_LENGTH(zoomAndPanSpec))) 1218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != '(') 1238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!parseZoomAndPan(currViewSpec, end)) 1268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != ')') 1288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else if (*currViewSpec == 'p') { 1314576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (!skipString(currViewSpec, end, preserveAspectRatioSpec, WTF_ARRAY_LENGTH(preserveAspectRatioSpec))) 1328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != '(') 1348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 136d0825bca7fe65beaee391d30da42e937db621564Steve Block bool result = false; 137d0825bca7fe65beaee391d30da42e937db621564Steve Block setPreserveAspectRatioBaseValue(SVGPreserveAspectRatio::parsePreserveAspectRatio(currViewSpec, end, false, result)); 138d0825bca7fe65beaee391d30da42e937db621564Steve Block if (!result) 1398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != ')') 1418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else if (*currViewSpec == 't') { 1444576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (!skipString(currViewSpec, end, transformSpec, WTF_ARRAY_LENGTH(transformSpec))) 1458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != '(') 1478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1496b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner SVGTransformable::parseTransformAttribute(m_transform, currViewSpec, end, SVGTransformable::DoNotClearList); 1508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != ')') 1518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else 1548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec < end && *currViewSpec == ';') 1578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project currViewSpec++; 1588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (currViewSpec >= end || *currViewSpec != ')') 1618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 1628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return true; 1648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif // ENABLE(SVG) 169