1 /* 2 * Copyright (C) 2006 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.internal.util; 18 19 import android.graphics.Bitmap; 20 import android.graphics.BitmapFactory; 21 import android.graphics.Bitmap.CompressFormat; 22 import android.net.Uri; 23 import android.util.Base64; 24 import android.util.Xml; 25 26 import org.xmlpull.v1.XmlPullParser; 27 import org.xmlpull.v1.XmlPullParserException; 28 import org.xmlpull.v1.XmlSerializer; 29 30 import java.io.ByteArrayOutputStream; 31 import java.io.IOException; 32 import java.io.InputStream; 33 import java.io.OutputStream; 34 import java.net.ProtocolException; 35 import java.util.ArrayList; 36 import java.util.HashMap; 37 import java.util.HashSet; 38 import java.util.Iterator; 39 import java.util.List; 40 import java.util.Map; 41 import java.util.Set; 42 43 /** {@hide} */ 44 public class XmlUtils { 45 skipCurrentTag(XmlPullParser parser)46 public static void skipCurrentTag(XmlPullParser parser) 47 throws XmlPullParserException, IOException { 48 int outerDepth = parser.getDepth(); 49 int type; 50 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT 51 && (type != XmlPullParser.END_TAG 52 || parser.getDepth() > outerDepth)) { 53 } 54 } 55 56 public static final int convertValueToList(CharSequence value, String[] options, int defaultValue)57 convertValueToList(CharSequence value, String[] options, int defaultValue) 58 { 59 if (null != value) { 60 for (int i = 0; i < options.length; i++) { 61 if (value.equals(options[i])) 62 return i; 63 } 64 } 65 66 return defaultValue; 67 } 68 69 public static final boolean convertValueToBoolean(CharSequence value, boolean defaultValue)70 convertValueToBoolean(CharSequence value, boolean defaultValue) 71 { 72 boolean result = false; 73 74 if (null == value) 75 return defaultValue; 76 77 if (value.equals("1") 78 || value.equals("true") 79 || value.equals("TRUE")) 80 result = true; 81 82 return result; 83 } 84 85 public static final int convertValueToInt(CharSequence charSeq, int defaultValue)86 convertValueToInt(CharSequence charSeq, int defaultValue) 87 { 88 if (null == charSeq) 89 return defaultValue; 90 91 String nm = charSeq.toString(); 92 93 // XXX This code is copied from Integer.decode() so we don't 94 // have to instantiate an Integer! 95 96 int value; 97 int sign = 1; 98 int index = 0; 99 int len = nm.length(); 100 int base = 10; 101 102 if ('-' == nm.charAt(0)) { 103 sign = -1; 104 index++; 105 } 106 107 if ('0' == nm.charAt(index)) { 108 // Quick check for a zero by itself 109 if (index == (len - 1)) 110 return 0; 111 112 char c = nm.charAt(index + 1); 113 114 if ('x' == c || 'X' == c) { 115 index += 2; 116 base = 16; 117 } else { 118 index++; 119 base = 8; 120 } 121 } 122 else if ('#' == nm.charAt(index)) 123 { 124 index++; 125 base = 16; 126 } 127 128 return Integer.parseInt(nm.substring(index), base) * sign; 129 } 130 convertValueToUnsignedInt(String value, int defaultValue)131 public static int convertValueToUnsignedInt(String value, int defaultValue) { 132 if (null == value) { 133 return defaultValue; 134 } 135 136 return parseUnsignedIntAttribute(value); 137 } 138 parseUnsignedIntAttribute(CharSequence charSeq)139 public static int parseUnsignedIntAttribute(CharSequence charSeq) { 140 String value = charSeq.toString(); 141 142 long bits; 143 int index = 0; 144 int len = value.length(); 145 int base = 10; 146 147 if ('0' == value.charAt(index)) { 148 // Quick check for zero by itself 149 if (index == (len - 1)) 150 return 0; 151 152 char c = value.charAt(index + 1); 153 154 if ('x' == c || 'X' == c) { // check for hex 155 index += 2; 156 base = 16; 157 } else { // check for octal 158 index++; 159 base = 8; 160 } 161 } else if ('#' == value.charAt(index)) { 162 index++; 163 base = 16; 164 } 165 166 return (int) Long.parseLong(value.substring(index), base); 167 } 168 169 /** 170 * Flatten a Map into an output stream as XML. The map can later be 171 * read back with readMapXml(). 172 * 173 * @param val The map to be flattened. 174 * @param out Where to write the XML data. 175 * 176 * @see #writeMapXml(Map, String, XmlSerializer) 177 * @see #writeListXml 178 * @see #writeValueXml 179 * @see #readMapXml 180 */ writeMapXml(Map val, OutputStream out)181 public static final void writeMapXml(Map val, OutputStream out) 182 throws XmlPullParserException, java.io.IOException { 183 XmlSerializer serializer = new FastXmlSerializer(); 184 serializer.setOutput(out, "utf-8"); 185 serializer.startDocument(null, true); 186 serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true); 187 writeMapXml(val, null, serializer); 188 serializer.endDocument(); 189 } 190 191 /** 192 * Flatten a List into an output stream as XML. The list can later be 193 * read back with readListXml(). 194 * 195 * @param val The list to be flattened. 196 * @param out Where to write the XML data. 197 * 198 * @see #writeListXml(List, String, XmlSerializer) 199 * @see #writeMapXml 200 * @see #writeValueXml 201 * @see #readListXml 202 */ writeListXml(List val, OutputStream out)203 public static final void writeListXml(List val, OutputStream out) 204 throws XmlPullParserException, java.io.IOException 205 { 206 XmlSerializer serializer = Xml.newSerializer(); 207 serializer.setOutput(out, "utf-8"); 208 serializer.startDocument(null, true); 209 serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true); 210 writeListXml(val, null, serializer); 211 serializer.endDocument(); 212 } 213 214 /** 215 * Flatten a Map into an XmlSerializer. The map can later be read back 216 * with readThisMapXml(). 217 * 218 * @param val The map to be flattened. 219 * @param name Name attribute to include with this list's tag, or null for 220 * none. 221 * @param out XmlSerializer to write the map into. 222 * 223 * @see #writeMapXml(Map, OutputStream) 224 * @see #writeListXml 225 * @see #writeValueXml 226 * @see #readMapXml 227 */ writeMapXml(Map val, String name, XmlSerializer out)228 public static final void writeMapXml(Map val, String name, XmlSerializer out) 229 throws XmlPullParserException, java.io.IOException { 230 writeMapXml(val, name, out, null); 231 } 232 233 /** 234 * Flatten a Map into an XmlSerializer. The map can later be read back 235 * with readThisMapXml(). 236 * 237 * @param val The map to be flattened. 238 * @param name Name attribute to include with this list's tag, or null for 239 * none. 240 * @param out XmlSerializer to write the map into. 241 * @param callback Method to call when an Object type is not recognized. 242 * 243 * @see #writeMapXml(Map, OutputStream) 244 * @see #writeListXml 245 * @see #writeValueXml 246 * @see #readMapXml 247 * 248 * @hide 249 */ writeMapXml(Map val, String name, XmlSerializer out, WriteMapCallback callback)250 public static final void writeMapXml(Map val, String name, XmlSerializer out, 251 WriteMapCallback callback) throws XmlPullParserException, java.io.IOException { 252 253 if (val == null) { 254 out.startTag(null, "null"); 255 out.endTag(null, "null"); 256 return; 257 } 258 259 out.startTag(null, "map"); 260 if (name != null) { 261 out.attribute(null, "name", name); 262 } 263 264 writeMapXml(val, out, callback); 265 266 out.endTag(null, "map"); 267 } 268 269 /** 270 * Flatten a Map into an XmlSerializer. The map can later be read back 271 * with readThisMapXml(). This method presumes that the start tag and 272 * name attribute have already been written and does not write an end tag. 273 * 274 * @param val The map to be flattened. 275 * @param out XmlSerializer to write the map into. 276 * 277 * @see #writeMapXml(Map, OutputStream) 278 * @see #writeListXml 279 * @see #writeValueXml 280 * @see #readMapXml 281 * 282 * @hide 283 */ writeMapXml(Map val, XmlSerializer out, WriteMapCallback callback)284 public static final void writeMapXml(Map val, XmlSerializer out, 285 WriteMapCallback callback) throws XmlPullParserException, java.io.IOException { 286 if (val == null) { 287 return; 288 } 289 290 Set s = val.entrySet(); 291 Iterator i = s.iterator(); 292 293 while (i.hasNext()) { 294 Map.Entry e = (Map.Entry)i.next(); 295 writeValueXml(e.getValue(), (String)e.getKey(), out, callback); 296 } 297 } 298 299 /** 300 * Flatten a List into an XmlSerializer. The list can later be read back 301 * with readThisListXml(). 302 * 303 * @param val The list to be flattened. 304 * @param name Name attribute to include with this list's tag, or null for 305 * none. 306 * @param out XmlSerializer to write the list into. 307 * 308 * @see #writeListXml(List, OutputStream) 309 * @see #writeMapXml 310 * @see #writeValueXml 311 * @see #readListXml 312 */ writeListXml(List val, String name, XmlSerializer out)313 public static final void writeListXml(List val, String name, XmlSerializer out) 314 throws XmlPullParserException, java.io.IOException 315 { 316 if (val == null) { 317 out.startTag(null, "null"); 318 out.endTag(null, "null"); 319 return; 320 } 321 322 out.startTag(null, "list"); 323 if (name != null) { 324 out.attribute(null, "name", name); 325 } 326 327 int N = val.size(); 328 int i=0; 329 while (i < N) { 330 writeValueXml(val.get(i), null, out); 331 i++; 332 } 333 334 out.endTag(null, "list"); 335 } 336 writeSetXml(Set val, String name, XmlSerializer out)337 public static final void writeSetXml(Set val, String name, XmlSerializer out) 338 throws XmlPullParserException, java.io.IOException { 339 if (val == null) { 340 out.startTag(null, "null"); 341 out.endTag(null, "null"); 342 return; 343 } 344 345 out.startTag(null, "set"); 346 if (name != null) { 347 out.attribute(null, "name", name); 348 } 349 350 for (Object v : val) { 351 writeValueXml(v, null, out); 352 } 353 354 out.endTag(null, "set"); 355 } 356 357 /** 358 * Flatten a byte[] into an XmlSerializer. The list can later be read back 359 * with readThisByteArrayXml(). 360 * 361 * @param val The byte array to be flattened. 362 * @param name Name attribute to include with this array's tag, or null for 363 * none. 364 * @param out XmlSerializer to write the array into. 365 * 366 * @see #writeMapXml 367 * @see #writeValueXml 368 */ writeByteArrayXml(byte[] val, String name, XmlSerializer out)369 public static final void writeByteArrayXml(byte[] val, String name, 370 XmlSerializer out) 371 throws XmlPullParserException, java.io.IOException { 372 373 if (val == null) { 374 out.startTag(null, "null"); 375 out.endTag(null, "null"); 376 return; 377 } 378 379 out.startTag(null, "byte-array"); 380 if (name != null) { 381 out.attribute(null, "name", name); 382 } 383 384 final int N = val.length; 385 out.attribute(null, "num", Integer.toString(N)); 386 387 StringBuilder sb = new StringBuilder(val.length*2); 388 for (int i=0; i<N; i++) { 389 int b = val[i]; 390 int h = b>>4; 391 sb.append(h >= 10 ? ('a'+h-10) : ('0'+h)); 392 h = b&0xff; 393 sb.append(h >= 10 ? ('a'+h-10) : ('0'+h)); 394 } 395 396 out.text(sb.toString()); 397 398 out.endTag(null, "byte-array"); 399 } 400 401 /** 402 * Flatten an int[] into an XmlSerializer. The list can later be read back 403 * with readThisIntArrayXml(). 404 * 405 * @param val The int array to be flattened. 406 * @param name Name attribute to include with this array's tag, or null for 407 * none. 408 * @param out XmlSerializer to write the array into. 409 * 410 * @see #writeMapXml 411 * @see #writeValueXml 412 * @see #readThisIntArrayXml 413 */ writeIntArrayXml(int[] val, String name, XmlSerializer out)414 public static final void writeIntArrayXml(int[] val, String name, 415 XmlSerializer out) 416 throws XmlPullParserException, java.io.IOException { 417 418 if (val == null) { 419 out.startTag(null, "null"); 420 out.endTag(null, "null"); 421 return; 422 } 423 424 out.startTag(null, "int-array"); 425 if (name != null) { 426 out.attribute(null, "name", name); 427 } 428 429 final int N = val.length; 430 out.attribute(null, "num", Integer.toString(N)); 431 432 for (int i=0; i<N; i++) { 433 out.startTag(null, "item"); 434 out.attribute(null, "value", Integer.toString(val[i])); 435 out.endTag(null, "item"); 436 } 437 438 out.endTag(null, "int-array"); 439 } 440 441 /** 442 * Flatten a long[] into an XmlSerializer. The list can later be read back 443 * with readThisLongArrayXml(). 444 * 445 * @param val The long array to be flattened. 446 * @param name Name attribute to include with this array's tag, or null for 447 * none. 448 * @param out XmlSerializer to write the array into. 449 * 450 * @see #writeMapXml 451 * @see #writeValueXml 452 * @see #readThisIntArrayXml 453 */ writeLongArrayXml(long[] val, String name, XmlSerializer out)454 public static final void writeLongArrayXml(long[] val, String name, XmlSerializer out) 455 throws XmlPullParserException, java.io.IOException { 456 457 if (val == null) { 458 out.startTag(null, "null"); 459 out.endTag(null, "null"); 460 return; 461 } 462 463 out.startTag(null, "long-array"); 464 if (name != null) { 465 out.attribute(null, "name", name); 466 } 467 468 final int N = val.length; 469 out.attribute(null, "num", Integer.toString(N)); 470 471 for (int i=0; i<N; i++) { 472 out.startTag(null, "item"); 473 out.attribute(null, "value", Long.toString(val[i])); 474 out.endTag(null, "item"); 475 } 476 477 out.endTag(null, "long-array"); 478 } 479 480 /** 481 * Flatten a double[] into an XmlSerializer. The list can later be read back 482 * with readThisDoubleArrayXml(). 483 * 484 * @param val The double array to be flattened. 485 * @param name Name attribute to include with this array's tag, or null for 486 * none. 487 * @param out XmlSerializer to write the array into. 488 * 489 * @see #writeMapXml 490 * @see #writeValueXml 491 * @see #readThisIntArrayXml 492 */ writeDoubleArrayXml(double[] val, String name, XmlSerializer out)493 public static final void writeDoubleArrayXml(double[] val, String name, XmlSerializer out) 494 throws XmlPullParserException, java.io.IOException { 495 496 if (val == null) { 497 out.startTag(null, "null"); 498 out.endTag(null, "null"); 499 return; 500 } 501 502 out.startTag(null, "double-array"); 503 if (name != null) { 504 out.attribute(null, "name", name); 505 } 506 507 final int N = val.length; 508 out.attribute(null, "num", Integer.toString(N)); 509 510 for (int i=0; i<N; i++) { 511 out.startTag(null, "item"); 512 out.attribute(null, "value", Double.toString(val[i])); 513 out.endTag(null, "item"); 514 } 515 516 out.endTag(null, "double-array"); 517 } 518 519 /** 520 * Flatten a String[] into an XmlSerializer. The list can later be read back 521 * with readThisStringArrayXml(). 522 * 523 * @param val The String array to be flattened. 524 * @param name Name attribute to include with this array's tag, or null for 525 * none. 526 * @param out XmlSerializer to write the array into. 527 * 528 * @see #writeMapXml 529 * @see #writeValueXml 530 * @see #readThisIntArrayXml 531 */ writeStringArrayXml(String[] val, String name, XmlSerializer out)532 public static final void writeStringArrayXml(String[] val, String name, XmlSerializer out) 533 throws XmlPullParserException, java.io.IOException { 534 535 if (val == null) { 536 out.startTag(null, "null"); 537 out.endTag(null, "null"); 538 return; 539 } 540 541 out.startTag(null, "string-array"); 542 if (name != null) { 543 out.attribute(null, "name", name); 544 } 545 546 final int N = val.length; 547 out.attribute(null, "num", Integer.toString(N)); 548 549 for (int i=0; i<N; i++) { 550 out.startTag(null, "item"); 551 out.attribute(null, "value", val[i]); 552 out.endTag(null, "item"); 553 } 554 555 out.endTag(null, "string-array"); 556 } 557 558 /** 559 * Flatten a boolean[] into an XmlSerializer. The list can later be read back 560 * with readThisBooleanArrayXml(). 561 * 562 * @param val The boolean array to be flattened. 563 * @param name Name attribute to include with this array's tag, or null for 564 * none. 565 * @param out XmlSerializer to write the array into. 566 * 567 * @see #writeMapXml 568 * @see #writeValueXml 569 * @see #readThisIntArrayXml 570 */ writeBooleanArrayXml(boolean[] val, String name, XmlSerializer out)571 public static final void writeBooleanArrayXml(boolean[] val, String name, XmlSerializer out) 572 throws XmlPullParserException, java.io.IOException { 573 574 if (val == null) { 575 out.startTag(null, "null"); 576 out.endTag(null, "null"); 577 return; 578 } 579 580 out.startTag(null, "boolean-array"); 581 if (name != null) { 582 out.attribute(null, "name", name); 583 } 584 585 final int N = val.length; 586 out.attribute(null, "num", Integer.toString(N)); 587 588 for (int i=0; i<N; i++) { 589 out.startTag(null, "item"); 590 out.attribute(null, "value", Boolean.toString(val[i])); 591 out.endTag(null, "item"); 592 } 593 594 out.endTag(null, "boolean-array"); 595 } 596 597 /** 598 * Flatten an object's value into an XmlSerializer. The value can later 599 * be read back with readThisValueXml(). 600 * 601 * Currently supported value types are: null, String, Integer, Long, 602 * Float, Double Boolean, Map, List. 603 * 604 * @param v The object to be flattened. 605 * @param name Name attribute to include with this value's tag, or null 606 * for none. 607 * @param out XmlSerializer to write the object into. 608 * 609 * @see #writeMapXml 610 * @see #writeListXml 611 * @see #readValueXml 612 */ writeValueXml(Object v, String name, XmlSerializer out)613 public static final void writeValueXml(Object v, String name, XmlSerializer out) 614 throws XmlPullParserException, java.io.IOException { 615 writeValueXml(v, name, out, null); 616 } 617 618 /** 619 * Flatten an object's value into an XmlSerializer. The value can later 620 * be read back with readThisValueXml(). 621 * 622 * Currently supported value types are: null, String, Integer, Long, 623 * Float, Double Boolean, Map, List. 624 * 625 * @param v The object to be flattened. 626 * @param name Name attribute to include with this value's tag, or null 627 * for none. 628 * @param out XmlSerializer to write the object into. 629 * @param callback Handler for Object types not recognized. 630 * 631 * @see #writeMapXml 632 * @see #writeListXml 633 * @see #readValueXml 634 */ writeValueXml(Object v, String name, XmlSerializer out, WriteMapCallback callback)635 private static final void writeValueXml(Object v, String name, XmlSerializer out, 636 WriteMapCallback callback) throws XmlPullParserException, java.io.IOException { 637 String typeStr; 638 if (v == null) { 639 out.startTag(null, "null"); 640 if (name != null) { 641 out.attribute(null, "name", name); 642 } 643 out.endTag(null, "null"); 644 return; 645 } else if (v instanceof String) { 646 out.startTag(null, "string"); 647 if (name != null) { 648 out.attribute(null, "name", name); 649 } 650 out.text(v.toString()); 651 out.endTag(null, "string"); 652 return; 653 } else if (v instanceof Integer) { 654 typeStr = "int"; 655 } else if (v instanceof Long) { 656 typeStr = "long"; 657 } else if (v instanceof Float) { 658 typeStr = "float"; 659 } else if (v instanceof Double) { 660 typeStr = "double"; 661 } else if (v instanceof Boolean) { 662 typeStr = "boolean"; 663 } else if (v instanceof byte[]) { 664 writeByteArrayXml((byte[])v, name, out); 665 return; 666 } else if (v instanceof int[]) { 667 writeIntArrayXml((int[])v, name, out); 668 return; 669 } else if (v instanceof long[]) { 670 writeLongArrayXml((long[])v, name, out); 671 return; 672 } else if (v instanceof double[]) { 673 writeDoubleArrayXml((double[])v, name, out); 674 return; 675 } else if (v instanceof String[]) { 676 writeStringArrayXml((String[])v, name, out); 677 return; 678 } else if (v instanceof boolean[]) { 679 writeBooleanArrayXml((boolean[])v, name, out); 680 return; 681 } else if (v instanceof Map) { 682 writeMapXml((Map)v, name, out); 683 return; 684 } else if (v instanceof List) { 685 writeListXml((List) v, name, out); 686 return; 687 } else if (v instanceof Set) { 688 writeSetXml((Set) v, name, out); 689 return; 690 } else if (v instanceof CharSequence) { 691 // XXX This is to allow us to at least write something if 692 // we encounter styled text... but it means we will drop all 693 // of the styling information. :( 694 out.startTag(null, "string"); 695 if (name != null) { 696 out.attribute(null, "name", name); 697 } 698 out.text(v.toString()); 699 out.endTag(null, "string"); 700 return; 701 } else if (callback != null) { 702 callback.writeUnknownObject(v, name, out); 703 return; 704 } else { 705 throw new RuntimeException("writeValueXml: unable to write value " + v); 706 } 707 708 out.startTag(null, typeStr); 709 if (name != null) { 710 out.attribute(null, "name", name); 711 } 712 out.attribute(null, "value", v.toString()); 713 out.endTag(null, typeStr); 714 } 715 716 /** 717 * Read a HashMap from an InputStream containing XML. The stream can 718 * previously have been written by writeMapXml(). 719 * 720 * @param in The InputStream from which to read. 721 * 722 * @return HashMap The resulting map. 723 * 724 * @see #readListXml 725 * @see #readValueXml 726 * @see #readThisMapXml 727 * #see #writeMapXml 728 */ 729 @SuppressWarnings("unchecked") readMapXml(InputStream in)730 public static final HashMap<String, ?> readMapXml(InputStream in) 731 throws XmlPullParserException, java.io.IOException 732 { 733 XmlPullParser parser = Xml.newPullParser(); 734 parser.setInput(in, null); 735 return (HashMap<String, ?>) readValueXml(parser, new String[1]); 736 } 737 738 /** 739 * Read an ArrayList from an InputStream containing XML. The stream can 740 * previously have been written by writeListXml(). 741 * 742 * @param in The InputStream from which to read. 743 * 744 * @return ArrayList The resulting list. 745 * 746 * @see #readMapXml 747 * @see #readValueXml 748 * @see #readThisListXml 749 * @see #writeListXml 750 */ readListXml(InputStream in)751 public static final ArrayList readListXml(InputStream in) 752 throws XmlPullParserException, java.io.IOException 753 { 754 XmlPullParser parser = Xml.newPullParser(); 755 parser.setInput(in, null); 756 return (ArrayList)readValueXml(parser, new String[1]); 757 } 758 759 760 /** 761 * Read a HashSet from an InputStream containing XML. The stream can 762 * previously have been written by writeSetXml(). 763 * 764 * @param in The InputStream from which to read. 765 * 766 * @return HashSet The resulting set. 767 * 768 * @throws XmlPullParserException 769 * @throws java.io.IOException 770 * 771 * @see #readValueXml 772 * @see #readThisSetXml 773 * @see #writeSetXml 774 */ readSetXml(InputStream in)775 public static final HashSet readSetXml(InputStream in) 776 throws XmlPullParserException, java.io.IOException { 777 XmlPullParser parser = Xml.newPullParser(); 778 parser.setInput(in, null); 779 return (HashSet) readValueXml(parser, new String[1]); 780 } 781 782 /** 783 * Read a HashMap object from an XmlPullParser. The XML data could 784 * previously have been generated by writeMapXml(). The XmlPullParser 785 * must be positioned <em>after</em> the tag that begins the map. 786 * 787 * @param parser The XmlPullParser from which to read the map data. 788 * @param endTag Name of the tag that will end the map, usually "map". 789 * @param name An array of one string, used to return the name attribute 790 * of the map's tag. 791 * 792 * @return HashMap The newly generated map. 793 * 794 * @see #readMapXml 795 */ readThisMapXml(XmlPullParser parser, String endTag, String[] name)796 public static final HashMap<String, ?> readThisMapXml(XmlPullParser parser, String endTag, 797 String[] name) throws XmlPullParserException, java.io.IOException { 798 return readThisMapXml(parser, endTag, name, null); 799 } 800 801 /** 802 * Read a HashMap object from an XmlPullParser. The XML data could 803 * previously have been generated by writeMapXml(). The XmlPullParser 804 * must be positioned <em>after</em> the tag that begins the map. 805 * 806 * @param parser The XmlPullParser from which to read the map data. 807 * @param endTag Name of the tag that will end the map, usually "map". 808 * @param name An array of one string, used to return the name attribute 809 * of the map's tag. 810 * 811 * @return HashMap The newly generated map. 812 * 813 * @see #readMapXml 814 * @hide 815 */ readThisMapXml(XmlPullParser parser, String endTag, String[] name, ReadMapCallback callback)816 public static final HashMap<String, ?> readThisMapXml(XmlPullParser parser, String endTag, 817 String[] name, ReadMapCallback callback) 818 throws XmlPullParserException, java.io.IOException 819 { 820 HashMap<String, Object> map = new HashMap<String, Object>(); 821 822 int eventType = parser.getEventType(); 823 do { 824 if (eventType == parser.START_TAG) { 825 Object val = readThisValueXml(parser, name, callback); 826 map.put(name[0], val); 827 } else if (eventType == parser.END_TAG) { 828 if (parser.getName().equals(endTag)) { 829 return map; 830 } 831 throw new XmlPullParserException( 832 "Expected " + endTag + " end tag at: " + parser.getName()); 833 } 834 eventType = parser.next(); 835 } while (eventType != parser.END_DOCUMENT); 836 837 throw new XmlPullParserException( 838 "Document ended before " + endTag + " end tag"); 839 } 840 841 /** 842 * Read an ArrayList object from an XmlPullParser. The XML data could 843 * previously have been generated by writeListXml(). The XmlPullParser 844 * must be positioned <em>after</em> the tag that begins the list. 845 * 846 * @param parser The XmlPullParser from which to read the list data. 847 * @param endTag Name of the tag that will end the list, usually "list". 848 * @param name An array of one string, used to return the name attribute 849 * of the list's tag. 850 * 851 * @return HashMap The newly generated list. 852 * 853 * @see #readListXml 854 */ readThisListXml(XmlPullParser parser, String endTag, String[] name)855 public static final ArrayList readThisListXml(XmlPullParser parser, String endTag, 856 String[] name) throws XmlPullParserException, java.io.IOException { 857 return readThisListXml(parser, endTag, name, null); 858 } 859 860 /** 861 * Read an ArrayList object from an XmlPullParser. The XML data could 862 * previously have been generated by writeListXml(). The XmlPullParser 863 * must be positioned <em>after</em> the tag that begins the list. 864 * 865 * @param parser The XmlPullParser from which to read the list data. 866 * @param endTag Name of the tag that will end the list, usually "list". 867 * @param name An array of one string, used to return the name attribute 868 * of the list's tag. 869 * 870 * @return HashMap The newly generated list. 871 * 872 * @see #readListXml 873 */ readThisListXml(XmlPullParser parser, String endTag, String[] name, ReadMapCallback callback)874 private static final ArrayList readThisListXml(XmlPullParser parser, String endTag, 875 String[] name, ReadMapCallback callback) 876 throws XmlPullParserException, java.io.IOException { 877 ArrayList list = new ArrayList(); 878 879 int eventType = parser.getEventType(); 880 do { 881 if (eventType == parser.START_TAG) { 882 Object val = readThisValueXml(parser, name, callback); 883 list.add(val); 884 //System.out.println("Adding to list: " + val); 885 } else if (eventType == parser.END_TAG) { 886 if (parser.getName().equals(endTag)) { 887 return list; 888 } 889 throw new XmlPullParserException( 890 "Expected " + endTag + " end tag at: " + parser.getName()); 891 } 892 eventType = parser.next(); 893 } while (eventType != parser.END_DOCUMENT); 894 895 throw new XmlPullParserException( 896 "Document ended before " + endTag + " end tag"); 897 } 898 899 /** 900 * Read a HashSet object from an XmlPullParser. The XML data could previously 901 * have been generated by writeSetXml(). The XmlPullParser must be positioned 902 * <em>after</em> the tag that begins the set. 903 * 904 * @param parser The XmlPullParser from which to read the set data. 905 * @param endTag Name of the tag that will end the set, usually "set". 906 * @param name An array of one string, used to return the name attribute 907 * of the set's tag. 908 * 909 * @return HashSet The newly generated set. 910 * 911 * @throws XmlPullParserException 912 * @throws java.io.IOException 913 * 914 * @see #readSetXml 915 */ readThisSetXml(XmlPullParser parser, String endTag, String[] name)916 public static final HashSet readThisSetXml(XmlPullParser parser, String endTag, String[] name) 917 throws XmlPullParserException, java.io.IOException { 918 return readThisSetXml(parser, endTag, name, null); 919 } 920 921 /** 922 * Read a HashSet object from an XmlPullParser. The XML data could previously 923 * have been generated by writeSetXml(). The XmlPullParser must be positioned 924 * <em>after</em> the tag that begins the set. 925 * 926 * @param parser The XmlPullParser from which to read the set data. 927 * @param endTag Name of the tag that will end the set, usually "set". 928 * @param name An array of one string, used to return the name attribute 929 * of the set's tag. 930 * 931 * @return HashSet The newly generated set. 932 * 933 * @throws XmlPullParserException 934 * @throws java.io.IOException 935 * 936 * @see #readSetXml 937 * @hide 938 */ readThisSetXml(XmlPullParser parser, String endTag, String[] name, ReadMapCallback callback)939 private static final HashSet readThisSetXml(XmlPullParser parser, String endTag, String[] name, 940 ReadMapCallback callback) throws XmlPullParserException, java.io.IOException { 941 HashSet set = new HashSet(); 942 943 int eventType = parser.getEventType(); 944 do { 945 if (eventType == parser.START_TAG) { 946 Object val = readThisValueXml(parser, name, callback); 947 set.add(val); 948 //System.out.println("Adding to set: " + val); 949 } else if (eventType == parser.END_TAG) { 950 if (parser.getName().equals(endTag)) { 951 return set; 952 } 953 throw new XmlPullParserException( 954 "Expected " + endTag + " end tag at: " + parser.getName()); 955 } 956 eventType = parser.next(); 957 } while (eventType != parser.END_DOCUMENT); 958 959 throw new XmlPullParserException( 960 "Document ended before " + endTag + " end tag"); 961 } 962 963 /** 964 * Read an int[] object from an XmlPullParser. The XML data could 965 * previously have been generated by writeIntArrayXml(). The XmlPullParser 966 * must be positioned <em>after</em> the tag that begins the list. 967 * 968 * @param parser The XmlPullParser from which to read the list data. 969 * @param endTag Name of the tag that will end the list, usually "list". 970 * @param name An array of one string, used to return the name attribute 971 * of the list's tag. 972 * 973 * @return Returns a newly generated int[]. 974 * 975 * @see #readListXml 976 */ readThisIntArrayXml(XmlPullParser parser, String endTag, String[] name)977 public static final int[] readThisIntArrayXml(XmlPullParser parser, 978 String endTag, String[] name) 979 throws XmlPullParserException, java.io.IOException { 980 981 int num; 982 try { 983 num = Integer.parseInt(parser.getAttributeValue(null, "num")); 984 } catch (NullPointerException e) { 985 throw new XmlPullParserException( 986 "Need num attribute in byte-array"); 987 } catch (NumberFormatException e) { 988 throw new XmlPullParserException( 989 "Not a number in num attribute in byte-array"); 990 } 991 parser.next(); 992 993 int[] array = new int[num]; 994 int i = 0; 995 996 int eventType = parser.getEventType(); 997 do { 998 if (eventType == parser.START_TAG) { 999 if (parser.getName().equals("item")) { 1000 try { 1001 array[i] = Integer.parseInt( 1002 parser.getAttributeValue(null, "value")); 1003 } catch (NullPointerException e) { 1004 throw new XmlPullParserException( 1005 "Need value attribute in item"); 1006 } catch (NumberFormatException e) { 1007 throw new XmlPullParserException( 1008 "Not a number in value attribute in item"); 1009 } 1010 } else { 1011 throw new XmlPullParserException( 1012 "Expected item tag at: " + parser.getName()); 1013 } 1014 } else if (eventType == parser.END_TAG) { 1015 if (parser.getName().equals(endTag)) { 1016 return array; 1017 } else if (parser.getName().equals("item")) { 1018 i++; 1019 } else { 1020 throw new XmlPullParserException( 1021 "Expected " + endTag + " end tag at: " 1022 + parser.getName()); 1023 } 1024 } 1025 eventType = parser.next(); 1026 } while (eventType != parser.END_DOCUMENT); 1027 1028 throw new XmlPullParserException( 1029 "Document ended before " + endTag + " end tag"); 1030 } 1031 1032 /** 1033 * Read a long[] object from an XmlPullParser. The XML data could 1034 * previously have been generated by writeLongArrayXml(). The XmlPullParser 1035 * must be positioned <em>after</em> the tag that begins the list. 1036 * 1037 * @param parser The XmlPullParser from which to read the list data. 1038 * @param endTag Name of the tag that will end the list, usually "list". 1039 * @param name An array of one string, used to return the name attribute 1040 * of the list's tag. 1041 * 1042 * @return Returns a newly generated long[]. 1043 * 1044 * @see #readListXml 1045 */ readThisLongArrayXml(XmlPullParser parser, String endTag, String[] name)1046 public static final long[] readThisLongArrayXml(XmlPullParser parser, 1047 String endTag, String[] name) 1048 throws XmlPullParserException, java.io.IOException { 1049 1050 int num; 1051 try { 1052 num = Integer.parseInt(parser.getAttributeValue(null, "num")); 1053 } catch (NullPointerException e) { 1054 throw new XmlPullParserException("Need num attribute in long-array"); 1055 } catch (NumberFormatException e) { 1056 throw new XmlPullParserException("Not a number in num attribute in long-array"); 1057 } 1058 parser.next(); 1059 1060 long[] array = new long[num]; 1061 int i = 0; 1062 1063 int eventType = parser.getEventType(); 1064 do { 1065 if (eventType == parser.START_TAG) { 1066 if (parser.getName().equals("item")) { 1067 try { 1068 array[i] = Long.parseLong(parser.getAttributeValue(null, "value")); 1069 } catch (NullPointerException e) { 1070 throw new XmlPullParserException("Need value attribute in item"); 1071 } catch (NumberFormatException e) { 1072 throw new XmlPullParserException("Not a number in value attribute in item"); 1073 } 1074 } else { 1075 throw new XmlPullParserException("Expected item tag at: " + parser.getName()); 1076 } 1077 } else if (eventType == parser.END_TAG) { 1078 if (parser.getName().equals(endTag)) { 1079 return array; 1080 } else if (parser.getName().equals("item")) { 1081 i++; 1082 } else { 1083 throw new XmlPullParserException("Expected " + endTag + " end tag at: " + 1084 parser.getName()); 1085 } 1086 } 1087 eventType = parser.next(); 1088 } while (eventType != parser.END_DOCUMENT); 1089 1090 throw new XmlPullParserException("Document ended before " + endTag + " end tag"); 1091 } 1092 1093 /** 1094 * Read a double[] object from an XmlPullParser. The XML data could 1095 * previously have been generated by writeDoubleArrayXml(). The XmlPullParser 1096 * must be positioned <em>after</em> the tag that begins the list. 1097 * 1098 * @param parser The XmlPullParser from which to read the list data. 1099 * @param endTag Name of the tag that will end the list, usually "double-array". 1100 * @param name An array of one string, used to return the name attribute 1101 * of the list's tag. 1102 * 1103 * @return Returns a newly generated double[]. 1104 * 1105 * @see #readListXml 1106 */ readThisDoubleArrayXml(XmlPullParser parser, String endTag, String[] name)1107 public static final double[] readThisDoubleArrayXml(XmlPullParser parser, String endTag, 1108 String[] name) throws XmlPullParserException, java.io.IOException { 1109 1110 int num; 1111 try { 1112 num = Integer.parseInt(parser.getAttributeValue(null, "num")); 1113 } catch (NullPointerException e) { 1114 throw new XmlPullParserException("Need num attribute in double-array"); 1115 } catch (NumberFormatException e) { 1116 throw new XmlPullParserException("Not a number in num attribute in double-array"); 1117 } 1118 parser.next(); 1119 1120 double[] array = new double[num]; 1121 int i = 0; 1122 1123 int eventType = parser.getEventType(); 1124 do { 1125 if (eventType == parser.START_TAG) { 1126 if (parser.getName().equals("item")) { 1127 try { 1128 array[i] = Double.parseDouble(parser.getAttributeValue(null, "value")); 1129 } catch (NullPointerException e) { 1130 throw new XmlPullParserException("Need value attribute in item"); 1131 } catch (NumberFormatException e) { 1132 throw new XmlPullParserException("Not a number in value attribute in item"); 1133 } 1134 } else { 1135 throw new XmlPullParserException("Expected item tag at: " + parser.getName()); 1136 } 1137 } else if (eventType == parser.END_TAG) { 1138 if (parser.getName().equals(endTag)) { 1139 return array; 1140 } else if (parser.getName().equals("item")) { 1141 i++; 1142 } else { 1143 throw new XmlPullParserException("Expected " + endTag + " end tag at: " + 1144 parser.getName()); 1145 } 1146 } 1147 eventType = parser.next(); 1148 } while (eventType != parser.END_DOCUMENT); 1149 1150 throw new XmlPullParserException("Document ended before " + endTag + " end tag"); 1151 } 1152 1153 /** 1154 * Read a String[] object from an XmlPullParser. The XML data could 1155 * previously have been generated by writeStringArrayXml(). The XmlPullParser 1156 * must be positioned <em>after</em> the tag that begins the list. 1157 * 1158 * @param parser The XmlPullParser from which to read the list data. 1159 * @param endTag Name of the tag that will end the list, usually "string-array". 1160 * @param name An array of one string, used to return the name attribute 1161 * of the list's tag. 1162 * 1163 * @return Returns a newly generated String[]. 1164 * 1165 * @see #readListXml 1166 */ readThisStringArrayXml(XmlPullParser parser, String endTag, String[] name)1167 public static final String[] readThisStringArrayXml(XmlPullParser parser, String endTag, 1168 String[] name) throws XmlPullParserException, java.io.IOException { 1169 1170 int num; 1171 try { 1172 num = Integer.parseInt(parser.getAttributeValue(null, "num")); 1173 } catch (NullPointerException e) { 1174 throw new XmlPullParserException("Need num attribute in string-array"); 1175 } catch (NumberFormatException e) { 1176 throw new XmlPullParserException("Not a number in num attribute in string-array"); 1177 } 1178 parser.next(); 1179 1180 String[] array = new String[num]; 1181 int i = 0; 1182 1183 int eventType = parser.getEventType(); 1184 do { 1185 if (eventType == parser.START_TAG) { 1186 if (parser.getName().equals("item")) { 1187 try { 1188 array[i] = parser.getAttributeValue(null, "value"); 1189 } catch (NullPointerException e) { 1190 throw new XmlPullParserException("Need value attribute in item"); 1191 } catch (NumberFormatException e) { 1192 throw new XmlPullParserException("Not a number in value attribute in item"); 1193 } 1194 } else { 1195 throw new XmlPullParserException("Expected item tag at: " + parser.getName()); 1196 } 1197 } else if (eventType == parser.END_TAG) { 1198 if (parser.getName().equals(endTag)) { 1199 return array; 1200 } else if (parser.getName().equals("item")) { 1201 i++; 1202 } else { 1203 throw new XmlPullParserException("Expected " + endTag + " end tag at: " + 1204 parser.getName()); 1205 } 1206 } 1207 eventType = parser.next(); 1208 } while (eventType != parser.END_DOCUMENT); 1209 1210 throw new XmlPullParserException("Document ended before " + endTag + " end tag"); 1211 } 1212 1213 /** 1214 * Read a boolean[] object from an XmlPullParser. The XML data could 1215 * previously have been generated by writeBooleanArrayXml(). The XmlPullParser 1216 * must be positioned <em>after</em> the tag that begins the list. 1217 * 1218 * @param parser The XmlPullParser from which to read the list data. 1219 * @param endTag Name of the tag that will end the list, usually "string-array". 1220 * @param name An array of one string, used to return the name attribute 1221 * of the list's tag. 1222 * 1223 * @return Returns a newly generated boolean[]. 1224 * 1225 * @see #readListXml 1226 */ readThisBooleanArrayXml(XmlPullParser parser, String endTag, String[] name)1227 public static final boolean[] readThisBooleanArrayXml(XmlPullParser parser, String endTag, 1228 String[] name) throws XmlPullParserException, java.io.IOException { 1229 1230 int num; 1231 try { 1232 num = Integer.parseInt(parser.getAttributeValue(null, "num")); 1233 } catch (NullPointerException e) { 1234 throw new XmlPullParserException("Need num attribute in string-array"); 1235 } catch (NumberFormatException e) { 1236 throw new XmlPullParserException("Not a number in num attribute in string-array"); 1237 } 1238 parser.next(); 1239 1240 boolean[] array = new boolean[num]; 1241 int i = 0; 1242 1243 int eventType = parser.getEventType(); 1244 do { 1245 if (eventType == parser.START_TAG) { 1246 if (parser.getName().equals("item")) { 1247 try { 1248 array[i] = Boolean.valueOf(parser.getAttributeValue(null, "value")); 1249 } catch (NullPointerException e) { 1250 throw new XmlPullParserException("Need value attribute in item"); 1251 } catch (NumberFormatException e) { 1252 throw new XmlPullParserException("Not a number in value attribute in item"); 1253 } 1254 } else { 1255 throw new XmlPullParserException("Expected item tag at: " + parser.getName()); 1256 } 1257 } else if (eventType == parser.END_TAG) { 1258 if (parser.getName().equals(endTag)) { 1259 return array; 1260 } else if (parser.getName().equals("item")) { 1261 i++; 1262 } else { 1263 throw new XmlPullParserException("Expected " + endTag + " end tag at: " + 1264 parser.getName()); 1265 } 1266 } 1267 eventType = parser.next(); 1268 } while (eventType != parser.END_DOCUMENT); 1269 1270 throw new XmlPullParserException("Document ended before " + endTag + " end tag"); 1271 } 1272 1273 /** 1274 * Read a flattened object from an XmlPullParser. The XML data could 1275 * previously have been written with writeMapXml(), writeListXml(), or 1276 * writeValueXml(). The XmlPullParser must be positioned <em>at</em> the 1277 * tag that defines the value. 1278 * 1279 * @param parser The XmlPullParser from which to read the object. 1280 * @param name An array of one string, used to return the name attribute 1281 * of the value's tag. 1282 * 1283 * @return Object The newly generated value object. 1284 * 1285 * @see #readMapXml 1286 * @see #readListXml 1287 * @see #writeValueXml 1288 */ readValueXml(XmlPullParser parser, String[] name)1289 public static final Object readValueXml(XmlPullParser parser, String[] name) 1290 throws XmlPullParserException, java.io.IOException 1291 { 1292 int eventType = parser.getEventType(); 1293 do { 1294 if (eventType == parser.START_TAG) { 1295 return readThisValueXml(parser, name, null); 1296 } else if (eventType == parser.END_TAG) { 1297 throw new XmlPullParserException( 1298 "Unexpected end tag at: " + parser.getName()); 1299 } else if (eventType == parser.TEXT) { 1300 throw new XmlPullParserException( 1301 "Unexpected text: " + parser.getText()); 1302 } 1303 eventType = parser.next(); 1304 } while (eventType != parser.END_DOCUMENT); 1305 1306 throw new XmlPullParserException( 1307 "Unexpected end of document"); 1308 } 1309 readThisValueXml(XmlPullParser parser, String[] name, ReadMapCallback callback)1310 private static final Object readThisValueXml(XmlPullParser parser, String[] name, 1311 ReadMapCallback callback) throws XmlPullParserException, java.io.IOException { 1312 final String valueName = parser.getAttributeValue(null, "name"); 1313 final String tagName = parser.getName(); 1314 1315 //System.out.println("Reading this value tag: " + tagName + ", name=" + valueName); 1316 1317 Object res; 1318 1319 if (tagName.equals("null")) { 1320 res = null; 1321 } else if (tagName.equals("string")) { 1322 String value = ""; 1323 int eventType; 1324 while ((eventType = parser.next()) != parser.END_DOCUMENT) { 1325 if (eventType == parser.END_TAG) { 1326 if (parser.getName().equals("string")) { 1327 name[0] = valueName; 1328 //System.out.println("Returning value for " + valueName + ": " + value); 1329 return value; 1330 } 1331 throw new XmlPullParserException( 1332 "Unexpected end tag in <string>: " + parser.getName()); 1333 } else if (eventType == parser.TEXT) { 1334 value += parser.getText(); 1335 } else if (eventType == parser.START_TAG) { 1336 throw new XmlPullParserException( 1337 "Unexpected start tag in <string>: " + parser.getName()); 1338 } 1339 } 1340 throw new XmlPullParserException( 1341 "Unexpected end of document in <string>"); 1342 } else if ((res = readThisPrimitiveValueXml(parser, tagName)) != null) { 1343 // all work already done by readThisPrimitiveValueXml 1344 } else if (tagName.equals("int-array")) { 1345 res = readThisIntArrayXml(parser, "int-array", name); 1346 name[0] = valueName; 1347 //System.out.println("Returning value for " + valueName + ": " + res); 1348 return res; 1349 } else if (tagName.equals("long-array")) { 1350 res = readThisLongArrayXml(parser, "long-array", name); 1351 name[0] = valueName; 1352 //System.out.println("Returning value for " + valueName + ": " + res); 1353 return res; 1354 } else if (tagName.equals("double-array")) { 1355 res = readThisDoubleArrayXml(parser, "double-array", name); 1356 name[0] = valueName; 1357 //System.out.println("Returning value for " + valueName + ": " + res); 1358 return res; 1359 } else if (tagName.equals("string-array")) { 1360 res = readThisStringArrayXml(parser, "string-array", name); 1361 name[0] = valueName; 1362 //System.out.println("Returning value for " + valueName + ": " + res); 1363 return res; 1364 } else if (tagName.equals("boolean-array")) { 1365 res = readThisBooleanArrayXml(parser, "boolean-array", name); 1366 name[0] = valueName; 1367 //System.out.println("Returning value for " + valueName + ": " + res); 1368 return res; 1369 } else if (tagName.equals("map")) { 1370 parser.next(); 1371 res = readThisMapXml(parser, "map", name); 1372 name[0] = valueName; 1373 //System.out.println("Returning value for " + valueName + ": " + res); 1374 return res; 1375 } else if (tagName.equals("list")) { 1376 parser.next(); 1377 res = readThisListXml(parser, "list", name); 1378 name[0] = valueName; 1379 //System.out.println("Returning value for " + valueName + ": " + res); 1380 return res; 1381 } else if (tagName.equals("set")) { 1382 parser.next(); 1383 res = readThisSetXml(parser, "set", name); 1384 name[0] = valueName; 1385 //System.out.println("Returning value for " + valueName + ": " + res); 1386 return res; 1387 } else if (callback != null) { 1388 res = callback.readThisUnknownObjectXml(parser, tagName); 1389 name[0] = valueName; 1390 return res; 1391 } else { 1392 throw new XmlPullParserException("Unknown tag: " + tagName); 1393 } 1394 1395 // Skip through to end tag. 1396 int eventType; 1397 while ((eventType = parser.next()) != parser.END_DOCUMENT) { 1398 if (eventType == parser.END_TAG) { 1399 if (parser.getName().equals(tagName)) { 1400 name[0] = valueName; 1401 //System.out.println("Returning value for " + valueName + ": " + res); 1402 return res; 1403 } 1404 throw new XmlPullParserException( 1405 "Unexpected end tag in <" + tagName + ">: " + parser.getName()); 1406 } else if (eventType == parser.TEXT) { 1407 throw new XmlPullParserException( 1408 "Unexpected text in <" + tagName + ">: " + parser.getName()); 1409 } else if (eventType == parser.START_TAG) { 1410 throw new XmlPullParserException( 1411 "Unexpected start tag in <" + tagName + ">: " + parser.getName()); 1412 } 1413 } 1414 throw new XmlPullParserException( 1415 "Unexpected end of document in <" + tagName + ">"); 1416 } 1417 readThisPrimitiveValueXml(XmlPullParser parser, String tagName)1418 private static final Object readThisPrimitiveValueXml(XmlPullParser parser, String tagName) 1419 throws XmlPullParserException, java.io.IOException 1420 { 1421 try { 1422 if (tagName.equals("int")) { 1423 return Integer.parseInt(parser.getAttributeValue(null, "value")); 1424 } else if (tagName.equals("long")) { 1425 return Long.valueOf(parser.getAttributeValue(null, "value")); 1426 } else if (tagName.equals("float")) { 1427 return new Float(parser.getAttributeValue(null, "value")); 1428 } else if (tagName.equals("double")) { 1429 return new Double(parser.getAttributeValue(null, "value")); 1430 } else if (tagName.equals("boolean")) { 1431 return Boolean.valueOf(parser.getAttributeValue(null, "value")); 1432 } else { 1433 return null; 1434 } 1435 } catch (NullPointerException e) { 1436 throw new XmlPullParserException("Need value attribute in <" + tagName + ">"); 1437 } catch (NumberFormatException e) { 1438 throw new XmlPullParserException( 1439 "Not a number in value attribute in <" + tagName + ">"); 1440 } 1441 } 1442 beginDocument(XmlPullParser parser, String firstElementName)1443 public static final void beginDocument(XmlPullParser parser, String firstElementName) throws XmlPullParserException, IOException 1444 { 1445 int type; 1446 while ((type=parser.next()) != parser.START_TAG 1447 && type != parser.END_DOCUMENT) { 1448 ; 1449 } 1450 1451 if (type != parser.START_TAG) { 1452 throw new XmlPullParserException("No start tag found"); 1453 } 1454 1455 if (!parser.getName().equals(firstElementName)) { 1456 throw new XmlPullParserException("Unexpected start tag: found " + parser.getName() + 1457 ", expected " + firstElementName); 1458 } 1459 } 1460 nextElement(XmlPullParser parser)1461 public static final void nextElement(XmlPullParser parser) throws XmlPullParserException, IOException 1462 { 1463 int type; 1464 while ((type=parser.next()) != parser.START_TAG 1465 && type != parser.END_DOCUMENT) { 1466 ; 1467 } 1468 } 1469 nextElementWithin(XmlPullParser parser, int outerDepth)1470 public static boolean nextElementWithin(XmlPullParser parser, int outerDepth) 1471 throws IOException, XmlPullParserException { 1472 for (;;) { 1473 int type = parser.next(); 1474 if (type == XmlPullParser.END_DOCUMENT 1475 || (type == XmlPullParser.END_TAG && parser.getDepth() == outerDepth)) { 1476 return false; 1477 } 1478 if (type == XmlPullParser.START_TAG 1479 && parser.getDepth() == outerDepth + 1) { 1480 return true; 1481 } 1482 } 1483 } 1484 readIntAttribute(XmlPullParser in, String name, int defaultValue)1485 public static int readIntAttribute(XmlPullParser in, String name, int defaultValue) { 1486 final String value = in.getAttributeValue(null, name); 1487 try { 1488 return Integer.parseInt(value); 1489 } catch (NumberFormatException e) { 1490 return defaultValue; 1491 } 1492 } 1493 readIntAttribute(XmlPullParser in, String name)1494 public static int readIntAttribute(XmlPullParser in, String name) throws IOException { 1495 final String value = in.getAttributeValue(null, name); 1496 try { 1497 return Integer.parseInt(value); 1498 } catch (NumberFormatException e) { 1499 throw new ProtocolException("problem parsing " + name + "=" + value + " as int"); 1500 } 1501 } 1502 writeIntAttribute(XmlSerializer out, String name, int value)1503 public static void writeIntAttribute(XmlSerializer out, String name, int value) 1504 throws IOException { 1505 out.attribute(null, name, Integer.toString(value)); 1506 } 1507 readLongAttribute(XmlPullParser in, String name, long defaultValue)1508 public static long readLongAttribute(XmlPullParser in, String name, long defaultValue) { 1509 final String value = in.getAttributeValue(null, name); 1510 try { 1511 return Long.parseLong(value); 1512 } catch (NumberFormatException e) { 1513 return defaultValue; 1514 } 1515 } 1516 readLongAttribute(XmlPullParser in, String name)1517 public static long readLongAttribute(XmlPullParser in, String name) throws IOException { 1518 final String value = in.getAttributeValue(null, name); 1519 try { 1520 return Long.parseLong(value); 1521 } catch (NumberFormatException e) { 1522 throw new ProtocolException("problem parsing " + name + "=" + value + " as long"); 1523 } 1524 } 1525 writeLongAttribute(XmlSerializer out, String name, long value)1526 public static void writeLongAttribute(XmlSerializer out, String name, long value) 1527 throws IOException { 1528 out.attribute(null, name, Long.toString(value)); 1529 } 1530 readFloatAttribute(XmlPullParser in, String name)1531 public static float readFloatAttribute(XmlPullParser in, String name) throws IOException { 1532 final String value = in.getAttributeValue(null, name); 1533 try { 1534 return Float.parseFloat(value); 1535 } catch (NumberFormatException e) { 1536 throw new ProtocolException("problem parsing " + name + "=" + value + " as long"); 1537 } 1538 } 1539 writeFloatAttribute(XmlSerializer out, String name, float value)1540 public static void writeFloatAttribute(XmlSerializer out, String name, float value) 1541 throws IOException { 1542 out.attribute(null, name, Float.toString(value)); 1543 } 1544 readBooleanAttribute(XmlPullParser in, String name)1545 public static boolean readBooleanAttribute(XmlPullParser in, String name) { 1546 final String value = in.getAttributeValue(null, name); 1547 return Boolean.parseBoolean(value); 1548 } 1549 readBooleanAttribute(XmlPullParser in, String name, boolean defaultValue)1550 public static boolean readBooleanAttribute(XmlPullParser in, String name, 1551 boolean defaultValue) { 1552 final String value = in.getAttributeValue(null, name); 1553 if (value == null) { 1554 return defaultValue; 1555 } else { 1556 return Boolean.parseBoolean(value); 1557 } 1558 } 1559 writeBooleanAttribute(XmlSerializer out, String name, boolean value)1560 public static void writeBooleanAttribute(XmlSerializer out, String name, boolean value) 1561 throws IOException { 1562 out.attribute(null, name, Boolean.toString(value)); 1563 } 1564 readUriAttribute(XmlPullParser in, String name)1565 public static Uri readUriAttribute(XmlPullParser in, String name) { 1566 final String value = in.getAttributeValue(null, name); 1567 return (value != null) ? Uri.parse(value) : null; 1568 } 1569 writeUriAttribute(XmlSerializer out, String name, Uri value)1570 public static void writeUriAttribute(XmlSerializer out, String name, Uri value) 1571 throws IOException { 1572 if (value != null) { 1573 out.attribute(null, name, value.toString()); 1574 } 1575 } 1576 readStringAttribute(XmlPullParser in, String name)1577 public static String readStringAttribute(XmlPullParser in, String name) { 1578 return in.getAttributeValue(null, name); 1579 } 1580 writeStringAttribute(XmlSerializer out, String name, String value)1581 public static void writeStringAttribute(XmlSerializer out, String name, String value) 1582 throws IOException { 1583 if (value != null) { 1584 out.attribute(null, name, value); 1585 } 1586 } 1587 readByteArrayAttribute(XmlPullParser in, String name)1588 public static byte[] readByteArrayAttribute(XmlPullParser in, String name) { 1589 final String value = in.getAttributeValue(null, name); 1590 if (value != null) { 1591 return Base64.decode(value, Base64.DEFAULT); 1592 } else { 1593 return null; 1594 } 1595 } 1596 writeByteArrayAttribute(XmlSerializer out, String name, byte[] value)1597 public static void writeByteArrayAttribute(XmlSerializer out, String name, byte[] value) 1598 throws IOException { 1599 if (value != null) { 1600 out.attribute(null, name, Base64.encodeToString(value, Base64.DEFAULT)); 1601 } 1602 } 1603 readBitmapAttribute(XmlPullParser in, String name)1604 public static Bitmap readBitmapAttribute(XmlPullParser in, String name) { 1605 final byte[] value = readByteArrayAttribute(in, name); 1606 if (value != null) { 1607 return BitmapFactory.decodeByteArray(value, 0, value.length); 1608 } else { 1609 return null; 1610 } 1611 } 1612 1613 @Deprecated writeBitmapAttribute(XmlSerializer out, String name, Bitmap value)1614 public static void writeBitmapAttribute(XmlSerializer out, String name, Bitmap value) 1615 throws IOException { 1616 if (value != null) { 1617 final ByteArrayOutputStream os = new ByteArrayOutputStream(); 1618 value.compress(CompressFormat.PNG, 90, os); 1619 writeByteArrayAttribute(out, name, os.toByteArray()); 1620 } 1621 } 1622 1623 /** @hide */ 1624 public interface WriteMapCallback { 1625 /** 1626 * Called from writeMapXml when an Object type is not recognized. The implementer 1627 * must write out the entire element including start and end tags. 1628 * 1629 * @param v The object to be written out 1630 * @param name The mapping key for v. Must be written into the "name" attribute of the 1631 * start tag. 1632 * @param out The XML output stream. 1633 * @throws XmlPullParserException on unrecognized Object type. 1634 * @throws IOException on XmlSerializer serialization errors. 1635 * @hide 1636 */ writeUnknownObject(Object v, String name, XmlSerializer out)1637 public void writeUnknownObject(Object v, String name, XmlSerializer out) 1638 throws XmlPullParserException, IOException; 1639 } 1640 1641 /** @hide */ 1642 public interface ReadMapCallback { 1643 /** 1644 * Called from readThisMapXml when a START_TAG is not recognized. The input stream 1645 * is positioned within the start tag so that attributes can be read using in.getAttribute. 1646 * 1647 * @param in the XML input stream 1648 * @param tag the START_TAG that was not recognized. 1649 * @return the Object parsed from the stream which will be put into the map. 1650 * @throws XmlPullParserException if the START_TAG is not recognized. 1651 * @throws IOException on XmlPullParser serialization errors. 1652 * @hide 1653 */ readThisUnknownObjectXml(XmlPullParser in, String tag)1654 public Object readThisUnknownObjectXml(XmlPullParser in, String tag) 1655 throws XmlPullParserException, IOException; 1656 } 1657 } 1658