001package ezvcard;
002
003import java.io.IOException;
004import java.io.OutputStream;
005import java.io.Writer;
006import java.nio.file.Path;
007import java.time.Instant;
008import java.time.LocalDate;
009import java.time.temporal.Temporal;
010import java.util.AbstractList;
011import java.util.ArrayList;
012import java.util.Arrays;
013import java.util.Collection;
014import java.util.Collections;
015import java.util.HashSet;
016import java.util.Iterator;
017import java.util.List;
018import java.util.Map;
019import java.util.Set;
020
021import javax.xml.transform.TransformerException;
022
023import ezvcard.io.html.HCardPage;
024import ezvcard.io.json.JCardWriter;
025import ezvcard.io.text.VCardWriter;
026import ezvcard.io.xml.XCardWriter;
027import ezvcard.parameter.EmailType;
028import ezvcard.parameter.TelephoneType;
029import ezvcard.parameter.VCardParameters;
030import ezvcard.property.Address;
031import ezvcard.property.Agent;
032import ezvcard.property.Anniversary;
033import ezvcard.property.Birthday;
034import ezvcard.property.Birthplace;
035import ezvcard.property.CalendarRequestUri;
036import ezvcard.property.CalendarUri;
037import ezvcard.property.Categories;
038import ezvcard.property.Classification;
039import ezvcard.property.ClientPidMap;
040import ezvcard.property.Deathdate;
041import ezvcard.property.Deathplace;
042import ezvcard.property.Email;
043import ezvcard.property.Expertise;
044import ezvcard.property.FormattedName;
045import ezvcard.property.FreeBusyUrl;
046import ezvcard.property.Gender;
047import ezvcard.property.Geo;
048import ezvcard.property.HasAltId;
049import ezvcard.property.Hobby;
050import ezvcard.property.Impp;
051import ezvcard.property.Interest;
052import ezvcard.property.Key;
053import ezvcard.property.Kind;
054import ezvcard.property.Label;
055import ezvcard.property.Language;
056import ezvcard.property.Logo;
057import ezvcard.property.Mailer;
058import ezvcard.property.Member;
059import ezvcard.property.Nickname;
060import ezvcard.property.Note;
061import ezvcard.property.OrgDirectory;
062import ezvcard.property.Organization;
063import ezvcard.property.Photo;
064import ezvcard.property.ProductId;
065import ezvcard.property.Profile;
066import ezvcard.property.RawProperty;
067import ezvcard.property.Related;
068import ezvcard.property.Revision;
069import ezvcard.property.Role;
070import ezvcard.property.SortString;
071import ezvcard.property.Sound;
072import ezvcard.property.Source;
073import ezvcard.property.SourceDisplayText;
074import ezvcard.property.StructuredName;
075import ezvcard.property.Telephone;
076import ezvcard.property.Timezone;
077import ezvcard.property.Title;
078import ezvcard.property.Uid;
079import ezvcard.property.Url;
080import ezvcard.property.VCardProperty;
081import ezvcard.property.Xml;
082import ezvcard.util.ListMultimap;
083import ezvcard.util.StringUtils;
084
085/*
086 Copyright (c) 2012-2023, Michael Angstadt
087 All rights reserved.
088
089 Redistribution and use in source and binary forms, with or without
090 modification, are permitted provided that the following conditions are met: 
091
092 1. Redistributions of source code must retain the above copyright notice, this
093 list of conditions and the following disclaimer. 
094 2. Redistributions in binary form must reproduce the above copyright notice,
095 this list of conditions and the following disclaimer in the documentation
096 and/or other materials provided with the distribution. 
097
098 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
099 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
100 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
101 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
102 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
103 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
104 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
105 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
106 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
107 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
108
109 The views and conclusions contained in the software and documentation are those
110 of the authors and should not be interpreted as representing official policies, 
111 either expressed or implied, of the FreeBSD Project.
112 */
113
114/**
115 * Represents a vCard.
116 * @author Michael Angstadt
117 */
118public class VCard implements Iterable<VCardProperty> {
119        private VCardVersion version;
120        private final ListMultimap<Class<? extends VCardProperty>, VCardProperty> properties = new ListMultimap<>();
121
122        /**
123         * Creates a new vCard set to version 3.0.
124         */
125        public VCard() {
126                this(VCardVersion.V3_0);
127        }
128
129        /**
130         * Creates a new vCard.
131         * @param version the version to assign to the vCard
132         */
133        public VCard(VCardVersion version) {
134                this.version = version;
135        }
136
137        /**
138         * Creates a deep copy of the given vCard.
139         * @param original the vCard to copy
140         */
141        public VCard(VCard original) {
142                version = original.version;
143                for (VCardProperty property : original.getProperties()) {
144                        addProperty(property.copy());
145                }
146        }
147
148        /**
149         * <p>
150         * Marshals this vCard to its text representation.
151         * </p>
152         * <p>
153         * The vCard will be marshalled to whatever vCard version is assigned to
154         * this object (see {@link #setVersion(VCardVersion)}). If no version is
155         * set, then it will be marshalled to 3.0.
156         * </p>
157         * <p>
158         * Use the {@link VCardWriter} class for more control over the marshalling
159         * process and to write multiple vCards to the same stream.
160         * </p>
161         * @return the vCard string
162         * @see VCardWriter
163         * @see <a href="http://www.imc.org/pdi/vcard-21.rtf">vCard 2.1</a>
164         * @see <a href="http://tools.ietf.org/html/rfc2426">RFC 2426 (3.0)</a>
165         * @see <a href="http://tools.ietf.org/html/rfc6350">RFC 6350 (4.0)</a>
166         */
167        public String write() {
168                return Ezvcard.write(this).go();
169        }
170
171        /**
172         * <p>
173         * Marshals this vCard to its text representation.
174         * </p>
175         * <p>
176         * The vCard will be marshalled to whatever vCard version is assigned to
177         * this object (see {@link #setVersion(VCardVersion)}). If no version is
178         * set, then it will be marshalled to 3.0.
179         * </p>
180         * <p>
181         * Use the {@link VCardWriter} class for more control over the marshalling
182         * process and to write multiple vCards to the same stream.
183         * </p>
184         * @param file the file to write the vCard to
185         * @throws IOException if there's a problem writing to the file
186         * @see VCardWriter
187         * @see <a href="http://www.imc.org/pdi/vcard-21.rtf">vCard 2.1</a>
188         * @see <a href="http://tools.ietf.org/html/rfc2426">RFC 2426 (3.0)</a>
189         * @see <a href="http://tools.ietf.org/html/rfc6350">RFC 6350 (4.0)</a>
190         */
191        public void write(Path file) throws IOException {
192                Ezvcard.write(this).go(file);
193        }
194
195        /**
196         * <p>
197         * Marshals this vCard to its text representation.
198         * </p>
199         * <p>
200         * The vCard will be marshalled to whatever vCard version is assigned to
201         * this object (see {@link #setVersion(VCardVersion)}). If no version is
202         * set, then it will be marshalled to 3.0.
203         * </p>
204         * <p>
205         * Use the {@link VCardWriter} class for more control over the marshalling
206         * process and to write multiple vCards to the same stream.
207         * </p>
208         * @param out the output stream to write the vCard to
209         * @see VCardWriter
210         * @throws IOException if there's a problem writing to the output stream
211         * @see <a href="http://www.imc.org/pdi/vcard-21.rtf">vCard 2.1</a>
212         * @see <a href="http://tools.ietf.org/html/rfc2426">RFC 2426 (3.0)</a>
213         * @see <a href="http://tools.ietf.org/html/rfc6350">RFC 6350 (4.0)</a>
214         */
215        public void write(OutputStream out) throws IOException {
216                Ezvcard.write(this).go(out);
217        }
218
219        /**
220         * <p>
221         * Marshals this vCard to its text representation.
222         * </p>
223         * <p>
224         * The vCard will be marshalled to whatever vCard version is assigned to
225         * this object (see {@link #setVersion(VCardVersion)}). If no version is
226         * set, then it will be marshalled to 3.0.
227         * </p>
228         * <p>
229         * Use the {@link VCardWriter} class for more control over the marshalling
230         * process and to write multiple vCards to the same stream.
231         * </p>
232         * @param writer the writer to write the vCard to
233         * @throws IOException if there's a problem writing to the writer
234         * @see VCardWriter
235         * @see <a href="http://www.imc.org/pdi/vcard-21.rtf">vCard 2.1</a>
236         * @see <a href="http://tools.ietf.org/html/rfc2426">RFC 2426 (3.0)</a>
237         * @see <a href="http://tools.ietf.org/html/rfc6350">RFC 6350 (4.0)</a>
238         */
239        public void write(Writer writer) throws IOException {
240                Ezvcard.write(this).go(writer);
241        }
242
243        /**
244         * <p>
245         * Marshals this vCard to its XML representation (xCard).
246         * </p>
247         * <p>
248         * Use the {@link XCardWriter} class for more control over the marshalling
249         * process and to write multiple vCards to the same stream.
250         * </p>
251         * @return the vCard XML document
252         * @see XCardWriter
253         * @see <a href="http://tools.ietf.org/html/rfc6351">RFC 6351</a>
254         */
255        public String writeXml() {
256                return Ezvcard.writeXml(this).indent(2).go();
257        }
258
259        /**
260         * <p>
261         * Marshals this vCard to its XML representation (xCard).
262         * </p>
263         * <p>
264         * Use the {@link XCardWriter} class for more control over the marshalling
265         * process and to write multiple vCards to the same stream.
266         * </p>
267         * @param file the file to write to
268         * @throws IOException if there's a problem writing to the file
269         * @throws TransformerException if there's a problem writing the vCard
270         * @see XCardWriter
271         * @see <a href="http://tools.ietf.org/html/rfc6351">RFC 6351</a>
272         */
273        public void writeXml(Path file) throws IOException, TransformerException {
274                Ezvcard.writeXml(this).indent(2).go(file);
275        }
276
277        /**
278         * <p>
279         * Marshals this vCard to its XML representation (xCard).
280         * </p>
281         * <p>
282         * Use the {@link XCardWriter} class for more control over the marshalling
283         * process and to write multiple vCards to the same stream.
284         * </p>
285         * @param out the output stream to write the vCard to
286         * @throws TransformerException if there's a problem writing to the output
287         * stream
288         * @see XCardWriter
289         * @see <a href="http://tools.ietf.org/html/rfc6351">RFC 6351</a>
290         */
291        public void writeXml(OutputStream out) throws TransformerException {
292                Ezvcard.writeXml(this).indent(2).go(out);
293        }
294
295        /**
296         * <p>
297         * Marshals this vCard to its XML representation (xCard).
298         * </p>
299         * <p>
300         * Use the {@link XCardWriter} class for more control over the marshalling
301         * process and to write multiple vCards to the same stream.
302         * </p>
303         * @param writer the writer to write the vCard to
304         * @throws TransformerException if there's a problem writing to the writer
305         * @see XCardWriter
306         * @see <a href="http://tools.ietf.org/html/rfc6351">RFC 6351</a>
307         */
308        public void writeXml(Writer writer) throws TransformerException {
309                Ezvcard.writeXml(this).indent(2).go(writer);
310        }
311
312        /**
313         * <p>
314         * Marshals this vCard to a basic HTML page (hCard).
315         * </p>
316         * <p>
317         * Use the {@link HCardPage} class for more control over the marshalling
318         * process and to write multiple vCards to the same stream.
319         * </p>
320         * @return the HTML page
321         * @see HCardPage
322         * @see <a href="http://microformats.org/wiki/hcard">hCard 1.0</a>
323         */
324        public String writeHtml() {
325                return Ezvcard.writeHtml(this).go();
326        }
327
328        /**
329         * <p>
330         * Marshals this vCard to a basic HTML page (hCard).
331         * </p>
332         * <p>
333         * Use the {@link HCardPage} class for more control over the marshalling
334         * process and to write multiple vCards to the same stream.
335         * </p>
336         * @param file the file to write to
337         * @throws IOException if there's a problem writing to the file
338         * @see HCardPage
339         * @see <a href="http://microformats.org/wiki/hcard">hCard 1.0</a>
340         */
341        public void writeHtml(Path file) throws IOException {
342                Ezvcard.writeHtml(this).go(file);
343        }
344
345        /**
346         * <p>
347         * Marshals this vCard to a basic HTML page (hCard).
348         * </p>
349         * <p>
350         * Use the {@link HCardPage} class for more control over the marshalling
351         * process and to write multiple vCards to the same stream.
352         * </p>
353         * @param out the output stream to write to
354         * @throws IOException if there's a problem writing to the output stream
355         * @see HCardPage
356         * @see <a href="http://microformats.org/wiki/hcard">hCard 1.0</a>
357         */
358        public void writeHtml(OutputStream out) throws IOException {
359                Ezvcard.writeHtml(this).go(out);
360        }
361
362        /**
363         * <p>
364         * Marshals this vCard to a basic HTML page (hCard).
365         * </p>
366         * <p>
367         * Use the {@link HCardPage} class for more control over the marshalling
368         * process and to write multiple vCards to the same stream.
369         * </p>
370         * @param writer the writer to write to
371         * @throws IOException if there's a problem writing to the writer
372         * @see HCardPage
373         * @see <a href="http://microformats.org/wiki/hcard">hCard 1.0</a>
374         */
375        public void writeHtml(Writer writer) throws IOException {
376                Ezvcard.writeHtml(this).go(writer);
377        }
378
379        /**
380         * <p>
381         * Marshals this vCard to its JSON representation (jCard).
382         * </p>
383         * <p>
384         * Use the {@link JCardWriter} class for more control over the marshalling
385         * process and to write multiple vCards to the same stream.
386         * </p>
387         * @return the JSON string
388         * @see JCardWriter
389         * @see <a href="http://tools.ietf.org/html/rfc7095">RFC 7095</a>
390         */
391        public String writeJson() {
392                return Ezvcard.writeJson(this).go();
393        }
394
395        /**
396         * <p>
397         * Marshals this vCard to its JSON representation (jCard).
398         * </p>
399         * <p>
400         * Use the {@link JCardWriter} class for more control over the marshalling
401         * process and to write multiple vCards to the same stream.
402         * </p>
403         * @param file the file to write the vCard to
404         * @throws IOException if there's a problem writing to the file
405         * @see JCardWriter
406         * @see <a href="http://tools.ietf.org/html/rfc7095">RFC 7095</a>
407         */
408        public void writeJson(Path file) throws IOException {
409                Ezvcard.writeJson(this).go(file);
410        }
411
412        /**
413         * <p>
414         * Marshals this vCard to its JSON representation (jCard).
415         * </p>
416         * <p>
417         * Use the {@link JCardWriter} class for more control over the marshalling
418         * process and to write multiple vCards to the same stream.
419         * </p>
420         * @param out the output stream to write the vCard to
421         * @see JCardWriter
422         * @throws IOException if there's a problem writing to the output stream
423         * @see <a href="http://tools.ietf.org/html/rfc7095">RFC 7095</a>
424         */
425        public void writeJson(OutputStream out) throws IOException {
426                Ezvcard.writeJson(this).go(out);
427        }
428
429        /**
430         * <p>
431         * Marshals this vCard to its JSON representation (jCard).
432         * </p>
433         * <p>
434         * Use the {@link JCardWriter} class for more control over the marshalling
435         * process and to write multiple vCards to the same stream.
436         * </p>
437         * @param writer the writer to write the vCard to
438         * @throws IOException if there's a problem writing to the writer
439         * @see JCardWriter
440         * @see <a href="http://tools.ietf.org/html/rfc7095">RFC 7095</a>
441         */
442        public void writeJson(Writer writer) throws IOException {
443                Ezvcard.writeJson(this).go(writer);
444        }
445
446        /**
447         * Gets the version attached to this vCard.
448         * @return the vCard version
449         */
450        public VCardVersion getVersion() {
451                return version;
452        }
453
454        /**
455         * <p>
456         * Sets the version of this vCard.
457         * </p>
458         * <p>
459         * When marshalling a vCard with the {@link VCardWriter} class, use the
460         * {@link VCardWriter#setTargetVersion setTargetVersion} method to define
461         * what version the vCard should be marshalled as. {@link VCardWriter}
462         * <b>does not</b> look at the version that is set on the VCard object.
463         * </p>
464         * @param version the vCard version
465         */
466        public void setVersion(VCardVersion version) {
467                this.version = version;
468        }
469
470        /**
471         * <p>
472         * Gets the type of entity this vCard represents.
473         * </p>
474         * <p>
475         * <b>Property name:</b> {@code KIND}<br>
476         * <b>Supported versions:</b> {@code 4.0}
477         * </p>
478         * @return the kind property or null if not set
479         * @see <a href="http://tools.ietf.org/html/rfc6350#page-25">RFC 6350
480         * p.25</a>
481         */
482        public Kind getKind() {
483                return getProperty(Kind.class);
484        }
485
486        /**
487         * <p>
488         * Sets the type of entity this vCard represents.
489         * </p>
490         * <p>
491         * <b>Property name:</b> {@code KIND}<br>
492         * <b>Supported versions:</b> {@code 4.0}
493         * </p>
494         * @param kind the kind property or null to remove
495         * @see <a href="http://tools.ietf.org/html/rfc6350#page-25">RFC 6350
496         * p.25</a>
497         */
498        public void setKind(Kind kind) {
499                setProperty(Kind.class, kind);
500        }
501
502        /**
503         * <p>
504         * Gets the gender of the person.
505         * </p>
506         * <p>
507         * <b>Property name:</b> {@code GENDER}<br>
508         * <b>Supported versions:</b> {@code 4.0}
509         * </p>
510         * @return the gender property or null if not set
511         * @see <a href="http://tools.ietf.org/html/rfc6350#page-32">RFC 6350
512         * p.32</a>
513         */
514        public Gender getGender() {
515                return getProperty(Gender.class);
516        }
517
518        /**
519         * <p>
520         * Sets the gender of the person.
521         * </p>
522         * <p>
523         * <b>Property name:</b> {@code GENDER}<br>
524         * <b>Supported versions:</b> {@code 4.0}
525         * </p>
526         * @param gender the gender property or null to remove
527         * @see <a href="http://tools.ietf.org/html/rfc6350#page-32">RFC 6350
528         * p.32</a>
529         */
530        public void setGender(Gender gender) {
531                setProperty(Gender.class, gender);
532        }
533
534        /**
535         * <p>
536         * Gets the members of the group that this vCard represents.
537         * </p>
538         * <p>
539         * Note: If a vCard has any {@link Member} properties, then it must also
540         * have a {@link Kind} property whose value is set to "group".
541         * </p>
542         * <p>
543         * <b>Property name:</b> {@code MEMBER}<br>
544         * <b>Supported versions:</b> {@code 4.0}
545         * </p>
546         * @return the members properties (any changes made this list will affect
547         * the {@link VCard} object and vice versa)
548         * @see <a href="http://tools.ietf.org/html/rfc6350#page-41">RFC 6350
549         * p.41</a>
550         */
551        public List<Member> getMembers() {
552                return getProperties(Member.class);
553        }
554
555        /**
556         * <p>
557         * Adds a member to the group that this vCard represents.
558         * </p>
559         * <p>
560         * Note: If a vCard has any {@link Member} properties, then it must also
561         * have a {@link Kind} property whose value is set to "group".
562         * </p>
563         * <p>
564         * <b>Property name:</b> {@code MEMBER}<br>
565         * <b>Supported versions:</b> {@code 4.0}
566         * </p>
567         * @param member the member property to add
568         * @see <a href="http://tools.ietf.org/html/rfc6350#page-41">RFC 6350
569         * p.41</a>
570         */
571        public void addMember(Member member) {
572                addProperty(member);
573        }
574
575        /**
576         * <p>
577         * Adds a member to the group that this vCard represents.
578         * </p>
579         * <p>
580         * Note: If a vCard has any {@link Member} properties, then it must also
581         * have a {@link Kind} property whose value is set to "group".
582         * </p>
583         * <p>
584         * <b>Property name:</b> {@code MEMBER}<br>
585         * <b>Supported versions:</b> {@code 4.0}
586         * </p>
587         * @param altRepresentations the alternative representations of the same
588         * value. These properties contain the same information, but in different
589         * forms (such as different languages). See {@link VCardParameters#getAltId
590         * this description of the ALTID parameter} for more information. Note that
591         * this method automatically assigns an appropriate ALTID parameter to each
592         * property.
593         * @see <a href="http://tools.ietf.org/html/rfc6350#page-41">RFC 6350
594         * p.41</a>
595         */
596        public void addMemberAlt(Member... altRepresentations) {
597                addPropertyAlt(Member.class, altRepresentations);
598        }
599
600        /**
601         * <p>
602         * Gets the profile property. This property simply identifies the vCard as a
603         * vCard.
604         * </p>
605         * <p>
606         * <b>Property name:</b> {@code PROFILE}<br>
607         * <b>Supported versions:</b> {@code 3.0}
608         * </p>
609         * @return the profile property or null if not set
610         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
611         */
612        public Profile getProfile() {
613                return getProperty(Profile.class);
614        }
615
616        /**
617         * <p>
618         * Sets the profile property. This property simply identifies the vCard as a
619         * vCard.
620         * </p>
621         * <p>
622         * <b>Property name:</b> {@code PROFILE}<br>
623         * <b>Supported versions:</b> {@code 3.0}
624         * </p>
625         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
626         * @param profile the profile property or null to remove
627         */
628        public void setProfile(Profile profile) {
629                setProperty(Profile.class, profile);
630        }
631
632        /**
633         * <p>
634         * Gets the classification of the vCard, which describes the sensitivity of
635         * the information in the vCard.
636         * </p>
637         * <p>
638         * <b>Property name:</b> {@code CLASS}<br>
639         * <b>Supported versions:</b> {@code 3.0}
640         * </p>
641         * @return the classification property or null if not set
642         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
643         * p.26</a>
644         */
645        public Classification getClassification() {
646                return getProperty(Classification.class);
647        }
648
649        /**
650         * <p>
651         * Sets the classification of the vCard, which describes the sensitivity of
652         * the information in the vCard.
653         * </p>
654         * <p>
655         * <b>Property name:</b> {@code CLASS}<br>
656         * <b>Supported versions:</b> {@code 3.0}
657         * </p>
658         * @param classification the classification property or null to remove
659         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
660         * p.26</a>
661         */
662        public void setClassification(Classification classification) {
663                setProperty(Classification.class, classification);
664        }
665
666        /**
667         * <p>
668         * Sets the classification of the vCard, which describes the sensitivity of
669         * the information in the vCard.
670         * </p>
671         * <p>
672         * <b>Supported versions:</b> {@code 3.0}<br>
673         * <b>Property name:</b> {@code CLASS}
674         * </p>
675         * @param classification the classification (e.g. "PUBLIC", "PRIVATE",
676         * "CONFIDENTIAL") or null to remove
677         * @return the property object that was created
678         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
679         * p.26</a>
680         */
681        public Classification setClassification(String classification) {
682                Classification type = (classification == null) ? null : new Classification(classification);
683                setClassification(type);
684                return type;
685        }
686
687        /**
688         * <p>
689         * Gets the URIs that can be used to retrieve the most up-to-date version of
690         * the person's vCard.
691         * </p>
692         * <p>
693         * <b>Property name:</b> {@code SOURCE} <b>Supported versions:</b>
694         * {@code 3.0, 4.0}
695         * </p>
696         * @return the source properties (any changes made this list will affect the
697         * {@link VCard} object and vice versa)
698         * @see <a href="http://tools.ietf.org/html/rfc6350#page-24">RFC 6350
699         * p.24</a>
700         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
701         */
702        public List<Source> getSources() {
703                return getProperties(Source.class);
704        }
705
706        /**
707         * <p>
708         * Adds a URI that can be used to retrieve the most up-to-date version of
709         * the person's vCard.
710         * </p>
711         * <p>
712         * <b>Property name:</b> {@code SOURCE} <b>Supported versions:</b>
713         * {@code 3.0, 4.0}
714         * </p>
715         * @param source the source property
716         * @see <a href="http://tools.ietf.org/html/rfc6350#page-24">RFC 6350
717         * p.24</a>
718         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
719         */
720        public void addSource(Source source) {
721                addProperty(source);
722        }
723
724        /**
725         * <p>
726         * Adds a URI that can be used to retrieve the most up-to-date version of
727         * the person's vCard.
728         * </p>
729         * <p>
730         * <b>Property name:</b> {@code SOURCE}<br>
731         * <b>Supported versions:</b> {@code 3.0, 4.0}
732         * </p>
733         * @param source the source URI (e.g. "http://example.com/vcard.vcf")
734         * @return the property object that was created
735         * @see <a href="http://tools.ietf.org/html/rfc6350#page-24">RFC 6350
736         * p.24</a>
737         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
738         */
739        public Source addSource(String source) {
740                Source type = new Source(source);
741                addSource(type);
742                return type;
743        }
744
745        /**
746         * <p>
747         * Adds a URI that can be used to retrieve the most up-to-date version of
748         * the person's vCard.
749         * </p>
750         * <p>
751         * <b>Property name:</b> {@code SOURCE}<br>
752         * <b>Supported versions:</b> {@code 4.0*}<br>
753         * <i>* Only 4.0 supports alternative representations</i>
754         * </p>
755         * @param altRepresentations the alternative representations of the same
756         * value. These properties contain the same information, but in different
757         * forms (such as different languages). See {@link VCardParameters#getAltId
758         * this description of the ALTID parameter} for more information. Note that
759         * this method automatically assigns an appropriate ALTID parameter to each
760         * property.
761         * @see <a href="http://tools.ietf.org/html/rfc6350#page-24">RFC 6350
762         * p.24</a>
763         */
764        public void addSourceAlt(Source... altRepresentations) {
765                addPropertyAlt(Source.class, altRepresentations);
766        }
767
768        /**
769         * <p>
770         * Gets a textual representation of the {@link Source} property.
771         * </p>
772         * <p>
773         * <b>Property name:</b> {@code NAME}<br>
774         * <b>Supported versions:</b> {@code 3.0}
775         * </p>
776         * @return the property or null if not set
777         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
778         */
779        public SourceDisplayText getSourceDisplayText() {
780                return getProperty(SourceDisplayText.class);
781        }
782
783        /**
784         * <p>
785         * Sets a textual representation of the {@link Source} property.
786         * </p>
787         * <p>
788         * <b>Property name:</b> {@code NAME}<br>
789         * <b>Supported versions:</b> {@code 3.0}
790         * </p>
791         * @param sourceDisplayText the property null to remove
792         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
793         */
794        public void setSourceDisplayText(SourceDisplayText sourceDisplayText) {
795                setProperty(SourceDisplayText.class, sourceDisplayText);
796        }
797
798        /**
799         * <p>
800         * Sets a textual representation of the {@link Source} property.
801         * </p>
802         * <p>
803         * <b>Property name:</b> {@code NAME}<br>
804         * <b>Supported versions:</b> {@code 3.0}
805         * </p>
806         * @param sourceDisplayText a textual representation of the vCard source or
807         * null to remove
808         * @return the property object that was created
809         * @see <a href="http://tools.ietf.org/html/rfc2426#page-5">RFC 2426 p.5</a>
810         */
811        public SourceDisplayText setSourceDisplayText(String sourceDisplayText) {
812                SourceDisplayText type = (sourceDisplayText == null) ? null : new SourceDisplayText(sourceDisplayText);
813                setSourceDisplayText(type);
814                return type;
815        }
816
817        /**
818         * <p>
819         * Gets all instances of the {@link FormattedName} property.
820         * </p>
821         * <p>
822         * Version 4.0 vCards may have multiple instances if alternative
823         * representations are defined (see
824         * {@link #addFormattedNameAlt(FormattedName...) addFormattedNameAlt}) or if
825         * properties with different TYPE parameters are defined.
826         * </p>
827         * <p>
828         * <b>Property name:</b> {@code FN}<br>
829         * <b>Supported versions:</b> {@code 4.0*}<br>
830         * <i>* Only 4.0 supports multiple instances</i>
831         * </p>
832         * @return the formatted name properties (any changes made this list will
833         * affect the {@link VCard} object and vice versa)
834         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
835         * p.28</a>
836         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
837         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
838         */
839        public List<FormattedName> getFormattedNames() {
840                return getProperties(FormattedName.class);
841        }
842
843        /**
844         * <p>
845         * Gets the person's full name.
846         * </p>
847         * <p>
848         * <b>Property name:</b> {@code FN}<br>
849         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
850         * </p>
851         * @return the first formatted name property or null if not set
852         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
853         * p.28</a>
854         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
855         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
856         */
857        public FormattedName getFormattedName() {
858                return getProperty(FormattedName.class);
859        }
860
861        /**
862         * <p>
863         * Sets the person's full name.
864         * </p>
865         * <p>
866         * <b>Property name:</b> {@code FN}<br>
867         * <b>Supported versions:</b> {@code 4.0*}<br>
868         * <i>* Only 4.0 supports alternative representations</i>
869         * </p>
870         * @param altRepresentations the alternative representations of the same
871         * value. These properties contain the same information, but in different
872         * forms (such as different languages). See {@link VCardParameters#getAltId
873         * this description of the ALTID parameter} for more information. Note that
874         * this method automatically assigns an appropriate ALTID parameter to each
875         * property.
876         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
877         * p.28</a>
878         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
879         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
880         */
881        public void setFormattedNameAlt(FormattedName... altRepresentations) {
882                setPropertyAlt(FormattedName.class, altRepresentations);
883        }
884
885        /**
886         * <p>
887         * Adds a version of the person's full name.
888         * </p>
889         * <p>
890         * <b>Property name:</b> {@code FN}<br>
891         * <b>Supported versions:</b> {@code 4.0*}<br>
892         * <i>* Only 4.0 supports alternative representations</i>
893         * </p>
894         * @param altRepresentations the alternative representations of the same
895         * value. These properties contain the same information, but in different
896         * forms (such as different languages). See {@link VCardParameters#getAltId
897         * this description of the ALTID parameter} for more information. Note that
898         * this method automatically assigns an appropriate ALTID parameter to each
899         * property.
900         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
901         * p.28</a>
902         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
903         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
904         */
905        public void addFormattedNameAlt(FormattedName... altRepresentations) {
906                addPropertyAlt(FormattedName.class, altRepresentations);
907        }
908
909        /**
910         * <p>
911         * Sets the person's full name.
912         * </p>
913         * <p>
914         * <b>Property name:</b> {@code FN}<br>
915         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
916         * </p>
917         * @param formattedName the formatted name property or null to remove
918         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
919         * p.28</a>
920         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
921         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
922         */
923        public void setFormattedName(FormattedName formattedName) {
924                setProperty(FormattedName.class, formattedName);
925        }
926
927        /**
928         * <p>
929         * Adds a version of the person's full name.
930         * </p>
931         * <p>
932         * <b>Property name:</b> {@code FN}<br>
933         * <b>Supported versions:</b> {@code 4.0*}<br>
934         * <i>* Only 4.0 supports multiple instances</i>
935         * </p>
936         * @param formattedName the formatted name property to add
937         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
938         * p.28</a>
939         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
940         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
941         */
942        public void addFormattedName(FormattedName formattedName) {
943                addProperty(formattedName);
944        }
945
946        /**
947         * <p>
948         * Sets the person's full name.
949         * </p>
950         * <p>
951         * <b>Property name:</b> {@code FN}<br>
952         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
953         * </p>
954         * @param formattedName the formatted name (e.g. "John Doe") or null to
955         * remove
956         * @return the property object that was created
957         * @see <a href="http://tools.ietf.org/html/rfc6350#page-28">RFC 6350
958         * p.28</a>
959         * @see <a href="http://tools.ietf.org/html/rfc2426#page-8">RFC 2426 p.8</a>
960         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
961         */
962        public FormattedName setFormattedName(String formattedName) {
963                FormattedName type = (formattedName == null) ? null : new FormattedName(formattedName);
964                setFormattedName(type);
965                return type;
966        }
967
968        /**
969         * <p>
970         * Gets all structured name properties.
971         * </p>
972         * <p>
973         * Version 4.0 vCards may have multiple instances if alternative
974         * representations are defined (see
975         * {@link #setStructuredNameAlt(StructuredName...) setStructuredNameAlt}) or
976         * if properties with different TYPE parameters are defined.
977         * </p>
978         * <p>
979         * <b>Property name:</b> {@code N}<br>
980         * <b>Supported versions:</b> {@code 4.0*}<br>
981         * <i>* Only 4.0 supports alternative representations</i>
982         * </p>
983         * @return the structured name properties (any changes made this list will
984         * affect the {@link VCard} object and vice versa)
985         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
986         * p.29</a>
987         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
988         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
989         */
990        public List<StructuredName> getStructuredNames() {
991                return getProperties(StructuredName.class);
992        }
993
994        /**
995         * <p>
996         * Gets the individual components of the person's name.
997         * </p>
998         * <p>
999         * <b>Property name:</b> {@code N}<br>
1000         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1001         * </p>
1002         * @return the first structured name property or null if not set
1003         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1004         * p.29</a>
1005         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1006         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
1007         */
1008        public StructuredName getStructuredName() {
1009                return getProperty(StructuredName.class);
1010        }
1011
1012        /**
1013         * <p>
1014         * Sets the individual components of the person's name.
1015         * </p>
1016         * <p>
1017         * <b>Property name:</b> {@code N}<br>
1018         * <b>Supported versions:</b> {@code 4.0*}<br>
1019         * <i>* Only 4.0 supports alternative representations</i>
1020         * </p>
1021         * @param altRepresentations the alternative representations of the same
1022         * value. These properties contain the same information, but in different
1023         * forms (such as different languages). See {@link VCardParameters#getAltId
1024         * this description of the ALTID parameter} for more information. Note that
1025         * this method automatically assigns an appropriate ALTID parameter to each
1026         * property.
1027         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1028         * p.29</a>
1029         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1030         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.9</a>
1031         */
1032        public void setStructuredNameAlt(StructuredName... altRepresentations) {
1033                setPropertyAlt(StructuredName.class, altRepresentations);
1034        }
1035
1036        /**
1037         * Sets the individual components of the person's name.
1038         * <p>
1039         * <b>Property name:</b> {@code N}<br>
1040         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1041         * </p>
1042         * @param structuredName the structured name property or null to remove
1043         */
1044        public void setStructuredName(StructuredName structuredName) {
1045                setProperty(StructuredName.class, structuredName);
1046        }
1047
1048        /**
1049         * <p>
1050         * Gets all instances of the {@link Nickname} property.
1051         * </p>
1052         * <p>
1053         * Version 4.0 vCards may have multiple instances if alternative
1054         * representations are defined (see {@link #setNicknameAlt(Nickname...)
1055         * setNicknameAlt}) or if properties with different TYPE parameters are
1056         * defined.
1057         * </p>
1058         * <p>
1059         * <b>Property name:</b> {@code NICKNAME}<br>
1060         * <b>Supported versions:</b> {@code 3.0, 4.0}
1061         * </p>
1062         * @return the nickname properties (any changes made this list will affect
1063         * the {@link VCard} object and vice versa)
1064         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1065         * p.29</a>
1066         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1067         */
1068        public List<Nickname> getNicknames() {
1069                return getProperties(Nickname.class);
1070        }
1071
1072        /**
1073         * <p>
1074         * Gets the person's nicknames.
1075         * </p>
1076         * <p>
1077         * <b>Property name:</b> {@code NICKNAME}<br>
1078         * <b>Supported versions:</b> {@code 3.0, 4.0}
1079         * </p>
1080         * @return the nickname property (may contain multiple values) or null if
1081         * not set
1082         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1083         * p.29</a>
1084         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1085         */
1086        public Nickname getNickname() {
1087                return getProperty(Nickname.class);
1088        }
1089
1090        /**
1091         * <p>
1092         * Sets the person's nicknames.
1093         * </p>
1094         * <p>
1095         * <b>Property name:</b> {@code NICKNAME}<br>
1096         * <b>Supported versions:</b> {@code 4.0*}<br>
1097         * <i>* Only 4.0 supports alternative representations</i>
1098         * </p>
1099         * @param altRepresentations the alternative representations of the same
1100         * value. These properties contain the same information, but in different
1101         * forms (such as different languages). See {@link VCardParameters#getAltId
1102         * this description of the ALTID parameter} for more information. Note that
1103         * this method automatically assigns an appropriate ALTID parameter to each
1104         * property.
1105         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1106         * p.29</a>
1107         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1108         */
1109        public void setNicknameAlt(Nickname... altRepresentations) {
1110                setPropertyAlt(Nickname.class, altRepresentations);
1111        }
1112
1113        /**
1114         * <p>
1115         * Adds a collection of nicknames for the person.
1116         * </p>
1117         * <p>
1118         * <b>Property name:</b> {@code NICKNAME}<br>
1119         * <b>Supported versions:</b> {@code 4.0*}<br>
1120         * <i>* Only 4.0 supports alternative representations</i>
1121         * </p>
1122         * @param altRepresentations the alternative representations of the same
1123         * value. These properties contain the same information, but in different
1124         * forms (such as different languages). See {@link VCardParameters#getAltId
1125         * this description of the ALTID parameter} for more information. Note that
1126         * this method automatically assigns an appropriate ALTID parameter to each
1127         * property.
1128         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1129         * p.29</a>
1130         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1131         */
1132        public void addNicknameAlt(Nickname... altRepresentations) {
1133                addPropertyAlt(Nickname.class, altRepresentations);
1134        }
1135
1136        /**
1137         * <p>
1138         * Sets the person's nicknames.
1139         * </p>
1140         * <p>
1141         * <b>Property name:</b> {@code NICKNAME}<br>
1142         * <b>Supported versions:</b> {@code 3.0, 4.0}
1143         * </p>
1144         * @param nickname the nickname property (may contain multiple values) or
1145         * null to remove
1146         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1147         * p.29</a>
1148         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1149         */
1150        public void setNickname(Nickname nickname) {
1151                setProperty(Nickname.class, nickname);
1152        }
1153
1154        /**
1155         * <p>
1156         * Adds a set of nicknames for the person.
1157         * </p>
1158         * <p>
1159         * Note that only version 4.0 vCards support multiple instances of this
1160         * property.
1161         * </p>
1162         * <p>
1163         * <b>Property name:</b> {@code NICKNAME}<br>
1164         * <b>Supported versions:</b> {@code 4.0*}<br>
1165         * <i>* Only 4.0 supports multiple instances</i>
1166         * </p>
1167         * @param nickname the nickname property (may contain multiple values)
1168         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1169         * p.29</a>
1170         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1171         */
1172        public void addNickname(Nickname nickname) {
1173                addProperty(nickname);
1174        }
1175
1176        /**
1177         * <p>
1178         * Sets the person's nicknames.
1179         * </p>
1180         * <p>
1181         * <b>Property name:</b> {@code NICKNAME}<br>
1182         * <b>Supported versions:</b> {@code 3.0, 4.0}
1183         * </p>
1184         * @param nicknames the nicknames (e.g. "John", "Jon")
1185         * @return the property object that was created
1186         * @see <a href="http://tools.ietf.org/html/rfc6350#page-29">RFC 6350
1187         * p.29</a>
1188         * @see <a href="http://tools.ietf.org/html/rfc2426#page-9">RFC 2426 p.9</a>
1189         */
1190        public Nickname setNickname(String... nicknames) {
1191                Nickname property = null;
1192                if (nicknames != null && nicknames.length > 0 && nicknames[0] != null) {
1193                        property = new Nickname();
1194                        property.getValues().addAll(Arrays.asList(nicknames));
1195                }
1196                setNickname(property);
1197                return property;
1198        }
1199
1200        /**
1201         * <p>
1202         * Gets the string that should be used to sort the vCard. This typically set
1203         * to the person's family name (last name).
1204         * </p>
1205         * <p>
1206         * For 4.0 vCards, this information is stored in the
1207         * {@link StructuredName#getSortAs} and/or {@link Organization#getSortAs}
1208         * methods.
1209         * </p>
1210         * <p>
1211         * <b>Property name:</b> {@code SORT-STRING}<br>
1212         * <b>Supported versions:</b> {@code 3.0}
1213         * </p>
1214         * @return the sort string property or null if not set
1215         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
1216         * p.22</a>
1217         */
1218        public SortString getSortString() {
1219                return getProperty(SortString.class);
1220        }
1221
1222        /**
1223         * <p>
1224         * Sets the string that should be used to sort the vCard. This typically set
1225         * to the person's family name (last name).
1226         * </p>
1227         * <p>
1228         * For 4.0 vCards, this information is stored in the
1229         * {@link StructuredName#getSortAs} and/or {@link Organization#getSortAs}
1230         * methods.
1231         * </p>
1232         * <p>
1233         * <b>Property name:</b> {@code SORT-STRING}<br>
1234         * <b>Supported versions:</b> {@code 3.0}
1235         * </p>
1236         * @param sortString the sort string property or null to remove
1237         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
1238         * p.22</a>
1239         */
1240        public void setSortString(SortString sortString) {
1241                setProperty(SortString.class, sortString);
1242        }
1243
1244        /**
1245         * <p>
1246         * Sets the string that should be used to sort the vCard. This typically set
1247         * to the person's family name (last name).
1248         * </p>
1249         * <p>
1250         * For 4.0 vCards, this information is stored in the
1251         * {@link StructuredName#getSortAs} and/or {@link Organization#getSortAs}
1252         * methods.
1253         * </p>
1254         * <p>
1255         * <b>Property name:</b> {@code SORT-STRING}<br>
1256         * <b>Supported versions:</b> {@code 3.0}
1257         * </p>
1258         * @param sortString the sort string (e.g. "Armour" if the person's last
1259         * name is "d'Armour") or null to remove
1260         * @return the property object that was created
1261         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
1262         * p.22</a>
1263         */
1264        public SortString setSortString(String sortString) {
1265                SortString type = (sortString == null) ? null : new SortString(sortString);
1266                setSortString(type);
1267                return type;
1268        }
1269
1270        /**
1271         * <p>
1272         * Gets the titles associated with the person.
1273         * </p>
1274         * <p>
1275         * <b>Property name:</b> {@code TITLE}<br>
1276         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1277         * </p>
1278         * @return the title properties (any changes made this list will affect the
1279         * {@link VCard} object and vice versa)
1280         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1281         * p.39</a>
1282         * @see <a href="http://tools.ietf.org/html/rfc2426#page-17">RFC 2426
1283         * p.17</a>
1284         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1285         */
1286        public List<Title> getTitles() {
1287                return getProperties(Title.class);
1288        }
1289
1290        /**
1291         * <p>
1292         * Adds a title associated with the person.
1293         * </p>
1294         * <p>
1295         * <b>Property name:</b> {@code TITLE}<br>
1296         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1297         * </p>
1298         * @param title the title property to add
1299         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1300         * p.39</a>
1301         * @see <a href="http://tools.ietf.org/html/rfc2426#page-17">RFC 2426
1302         * p.17</a>
1303         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1304         */
1305        public void addTitle(Title title) {
1306                addProperty(title);
1307        }
1308
1309        /**
1310         * <p>
1311         * Adds a title associated with the person.
1312         * </p>
1313         * <p>
1314         * <b>Property name:</b> {@code TITLE}<br>
1315         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1316         * </p>
1317         * @param title the title to add (e.g. "V.P. Research and Development")
1318         * @return the property object that was created
1319         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1320         * p.39</a>
1321         * @see <a href="http://tools.ietf.org/html/rfc2426#page-17">RFC 2426
1322         * p.17</a>
1323         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1324         */
1325        public Title addTitle(String title) {
1326                Title type = new Title(title);
1327                addTitle(type);
1328                return type;
1329        }
1330
1331        /**
1332         * <p>
1333         * Adds a title associated with the person.
1334         * </p>
1335         * <p>
1336         * <b>Property name:</b> {@code TITLE}<br>
1337         * <b>Supported versions:</b> {@code 4.0*}<br>
1338         * <i>* Only 4.0 supports alternative representations</i>
1339         * </p>
1340         * @param altRepresentations the alternative representations of the same
1341         * value. These properties contain the same information, but in different
1342         * forms (such as different languages). See {@link VCardParameters#getAltId
1343         * this description of the ALTID parameter} for more information. Note that
1344         * this method automatically assigns an appropriate ALTID parameter to each
1345         * property.
1346         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1347         * p.39</a>
1348         * @see <a href="http://tools.ietf.org/html/rfc2426#page-17">RFC 2426
1349         * p.17</a>
1350         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1351         */
1352        public void addTitleAlt(Title... altRepresentations) {
1353                addPropertyAlt(Title.class, altRepresentations);
1354        }
1355
1356        /**
1357         * <p>
1358         * Gets the roles associated with the person.
1359         * </p>
1360         * <p>
1361         * <b>Property name:</b> {@code ROLE}<br>
1362         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1363         * </p>
1364         * @return the role properties (any changes made this list will affect the
1365         * {@link VCard} object and vice versa)
1366         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1367         * p.39</a>
1368         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1369         * p.18</a>
1370         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1371         */
1372        public List<Role> getRoles() {
1373                return getProperties(Role.class);
1374        }
1375
1376        /**
1377         * <p>
1378         * Adds a role associated with the person.
1379         * </p>
1380         * <p>
1381         * <b>Property name:</b> {@code ROLE}<br>
1382         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1383         * </p>
1384         * @param role the role property to add
1385         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1386         * p.39</a>
1387         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1388         * p.18</a>
1389         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1390         */
1391        public void addRole(Role role) {
1392                addProperty(role);
1393        }
1394
1395        /**
1396         * <p>
1397         * Adds a role associated with the person.
1398         * </p>
1399         * <p>
1400         * <b>Property name:</b> {@code ROLE}<br>
1401         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1402         * </p>
1403         * @param role the role to add (e.g. "Executive")
1404         * @return the property object that was created
1405         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1406         * p.39</a>
1407         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1408         * p.18</a>
1409         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1410         */
1411        public Role addRole(String role) {
1412                Role type = new Role(role);
1413                addRole(type);
1414                return type;
1415        }
1416
1417        /**
1418         * <p>
1419         * Adds a role associated with the person.
1420         * </p>
1421         * <p>
1422         * <b>Property name:</b> {@code ROLE}<br>
1423         * <b>Supported versions:</b> {@code 4.0*}<br>
1424         * <i>* Only 4.0 supports alternative representations</i>
1425         * </p>
1426         * @param altRepresentations the alternative representations of the same
1427         * value. These properties contain the same information, but in different
1428         * forms (such as different languages). See {@link VCardParameters#getAltId
1429         * this description of the ALTID parameter} for more information. Note that
1430         * this method automatically assigns an appropriate ALTID parameter to each
1431         * property.
1432         * @see <a href="http://tools.ietf.org/html/rfc6350#page-39">RFC 6350
1433         * p.39</a>
1434         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1435         * p.18</a>
1436         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1437         */
1438        public void addRoleAlt(Role... altRepresentations) {
1439                addPropertyAlt(Role.class, altRepresentations);
1440        }
1441
1442        /**
1443         * <p>
1444         * Gets the photos attached to the vCard, such as the person's portrait.
1445         * </p>
1446         * <p>
1447         * <b>Property name:</b> {@code PHOTO}<br>
1448         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1449         * </p>
1450         * @return the photo properties (any changes made this list will affect the
1451         * {@link VCard} object and vice versa)
1452         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1453         * p.30</a>
1454         * @see <a href="http://tools.ietf.org/html/rfc2426#page-10">RFC 2426
1455         * p.10</a>
1456         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.10</a>
1457         */
1458        public List<Photo> getPhotos() {
1459                return getProperties(Photo.class);
1460        }
1461
1462        /**
1463         * <p>
1464         * Adds a photo to the vCard, such as the person's portrait.
1465         * </p>
1466         * <p>
1467         * <b>Property name:</b> {@code PHOTO}<br>
1468         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1469         * </p>
1470         * @param photo the photo property to add
1471         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1472         * p.30</a>
1473         * @see <a href="http://tools.ietf.org/html/rfc2426#page-10">RFC 2426
1474         * p.10</a>
1475         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.10</a>
1476         */
1477        public void addPhoto(Photo photo) {
1478                addProperty(photo);
1479        }
1480
1481        /**
1482         * <p>
1483         * Adds a photo to the vCard, such as the person's portrait.
1484         * </p>
1485         * <p>
1486         * <b>Property name:</b> {@code PHOTO}<br>
1487         * <b>Supported versions:</b> {@code 4.0*}<br>
1488         * <i>* Only 4.0 supports alternative representations</i>
1489         * </p>
1490         * @param altRepresentations the alternative representations of the same
1491         * value. These properties contain the same information, but in different
1492         * forms (such as different languages). See {@link VCardParameters#getAltId
1493         * this description of the ALTID parameter} for more information. Note that
1494         * this method automatically assigns an appropriate ALTID parameter to each
1495         * property.
1496         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1497         * p.30</a>
1498         * @see <a href="http://tools.ietf.org/html/rfc2426#page-10">RFC 2426
1499         * p.10</a>
1500         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.10</a>
1501         */
1502        public void addPhotoAlt(Photo... altRepresentations) {
1503                addPropertyAlt(Photo.class, altRepresentations);
1504        }
1505
1506        /**
1507         * <p>
1508         * Gets the logos attached to the vCard, such a company logo.
1509         * </p>
1510         * <p>
1511         * <b>Property name:</b> {@code LOGO}<br>
1512         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1513         * </p>
1514         * @return the logo properties (any changes made this list will affect the
1515         * {@link VCard} object and vice versa)
1516         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
1517         * p.40</a>
1518         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1519         * p.18</a>
1520         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1521         */
1522        public List<Logo> getLogos() {
1523                return getProperties(Logo.class);
1524        }
1525
1526        /**
1527         * <p>
1528         * Adds a logo to the vCard, such as a company logo.
1529         * </p>
1530         * <p>
1531         * <b>Property name:</b> {@code LOGO}<br>
1532         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1533         * </p>
1534         * @param logo the logo property to add
1535         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
1536         * p.40</a>
1537         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1538         * p.18</a>
1539         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1540         */
1541        public void addLogo(Logo logo) {
1542                addProperty(logo);
1543        }
1544
1545        /**
1546         * <p>
1547         * Adds a logo to the vCard, such as a company logo.
1548         * </p>
1549         * <p>
1550         * <b>Property name:</b> {@code LOGO}<br>
1551         * <b>Supported versions:</b> {@code 4.0*}<br>
1552         * <i>* Only 4.0 supports alternative representations</i>
1553         * </p>
1554         * @param altRepresentations the alternative representations of the same
1555         * value. These properties contain the same information, but in different
1556         * forms (such as different languages). See {@link VCardParameters#getAltId
1557         * this description of the ALTID parameter} for more information. Note that
1558         * this method automatically assigns an appropriate ALTID parameter to each
1559         * property.
1560         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
1561         * p.40</a>
1562         * @see <a href="http://tools.ietf.org/html/rfc2426#page-18">RFC 2426
1563         * p.18</a>
1564         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.17</a>
1565         */
1566        public void addLogoAlt(Logo... altRepresentations) {
1567                addPropertyAlt(Logo.class, altRepresentations);
1568        }
1569
1570        /**
1571         * <p>
1572         * Gets the sounds attached to the vCard, such as a pronunciation of the
1573         * person's name.
1574         * </p>
1575         * <p>
1576         * <b>Property name:</b> {@code SOUND}<br>
1577         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1578         * </p>
1579         * @return the sound properties (any changes made this list will affect the
1580         * {@link VCard} object and vice versa)
1581         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
1582         * p.45</a>
1583         * @see <a href="http://tools.ietf.org/html/rfc2426#page-23">RFC 2426
1584         * p.23</a>
1585         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.20</a>
1586         */
1587        public List<Sound> getSounds() {
1588                return getProperties(Sound.class);
1589        }
1590
1591        /**
1592         * <p>
1593         * Adds a sound to the vCard, such as a pronunciation of the person's name.
1594         * </p>
1595         * <p>
1596         * <b>Property name:</b> {@code SOUND}<br>
1597         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1598         * </p>
1599         * @param sound the sound property to add
1600         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
1601         * p.45</a>
1602         * @see <a href="http://tools.ietf.org/html/rfc2426#page-23">RFC 2426
1603         * p.23</a>
1604         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.20</a>
1605         */
1606        public void addSound(Sound sound) {
1607                addProperty(sound);
1608        }
1609
1610        /**
1611         * <p>
1612         * Adds a sound to the vCard, such as a pronunciation of the person's name.
1613         * </p>
1614         * <p>
1615         * <b>Property name:</b> {@code SOUND}<br>
1616         * <b>Supported versions:</b> {@code 4.0*}<br>
1617         * <i>* Only 4.0 supports alternative representations</i>
1618         * </p>
1619         * @param altRepresentations the alternative representations of the same
1620         * value. These properties contain the same information, but in different
1621         * forms (such as different languages). See {@link VCardParameters#getAltId
1622         * this description of the ALTID parameter} for more information. Note that
1623         * this method automatically assigns an appropriate ALTID parameter to each
1624         * property.
1625         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
1626         * p.45</a>
1627         * @see <a href="http://tools.ietf.org/html/rfc2426#page-23">RFC 2426
1628         * p.23</a>
1629         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.20</a>
1630         */
1631        public void addSoundAlt(Sound... altRepresentations) {
1632                addPropertyAlt(Sound.class, altRepresentations);
1633        }
1634
1635        /**
1636         * <p>
1637         * Gets all {@link Birthplace} property instances.
1638         * </p>
1639         * <p>
1640         * There may be multiple instances if alternative representations are
1641         * defined (see {@link #setBirthplaceAlt(Birthplace...) setBirthplaceAlt}).
1642         * </p>
1643         * <p>
1644         * <b>Property name:</b> {@code BIRTHPLACE}<br>
1645         * <b>Supported versions:</b> {@code 4.0}
1646         * </p>
1647         * @return the birthplace properties (any changes made this list will affect
1648         * the {@link VCard} object and vice versa)
1649         * @see <a href="http://tools.ietf.org/html/rfc6474#page-2">RFC 6474 p.2</a>
1650         */
1651        public List<Birthplace> getBirthplaces() {
1652                return getProperties(Birthplace.class);
1653        }
1654
1655        /**
1656         * <p>
1657         * Gets the person's birthplace.
1658         * </p>
1659         * <p>
1660         * <b>Property name:</b> {@code BIRTHPLACE}<br>
1661         * <b>Supported versions:</b> {@code 4.0}
1662         * </p>
1663         * @return the first birthplace property or null if not set
1664         * @see <a href="http://tools.ietf.org/html/rfc6474#page-2">RFC 6474 p.2</a>
1665         */
1666        public Birthplace getBirthplace() {
1667                return getProperty(Birthplace.class);
1668        }
1669
1670        /**
1671         * <p>
1672         * Sets the person's birthplace.
1673         * </p>
1674         * <p>
1675         * <b>Property name:</b> {@code BIRTHPLACE}<br>
1676         * <b>Supported versions:</b> {@code 4.0}
1677         * </p>
1678         * @param altRepresentations the alternative representations of the same
1679         * value. These properties contain the same information, but in different
1680         * forms (such as different languages). See {@link VCardParameters#getAltId
1681         * this description of the ALTID parameter} for more information. Note that
1682         * this method automatically assigns an appropriate ALTID parameter to each
1683         * property.
1684         * @see <a href="http://tools.ietf.org/html/rfc6474#page-2">RFC 6474 p.2</a>
1685         */
1686        public void setBirthplaceAlt(Birthplace... altRepresentations) {
1687                setPropertyAlt(Birthplace.class, altRepresentations);
1688        }
1689
1690        /**
1691         * <p>
1692         * Sets the person's birthplace.
1693         * </p>
1694         * <p>
1695         * <b>Property name:</b> {@code BIRTHPLACE}<br>
1696         * <b>Supported versions:</b> {@code 4.0}
1697         * </p>
1698         * @param birthplace the birthplace property or null to remove
1699         * @see <a href="http://tools.ietf.org/html/rfc6474#page-2">RFC 6474 p.2</a>
1700         */
1701        public void setBirthplace(Birthplace birthplace) {
1702                setProperty(Birthplace.class, birthplace);
1703        }
1704
1705        /**
1706         * <p>
1707         * Gets all {@link Deathplace} property instances.
1708         * </p>
1709         * <p>
1710         * There may be multiple instances if alternative representations are
1711         * defined (see {@link #setDeathplaceAlt(Deathplace...) setDeathplaceAlt}).
1712         * </p>
1713         * <p>
1714         * <b>Property name:</b> {@code DEATHPLACE}<br>
1715         * <b>Supported versions:</b> {@code 4.0}
1716         * </p>
1717         * @return the deathplace properties (any changes made this list will affect
1718         * the {@link VCard} object and vice versa)
1719         * @see <a href="http://tools.ietf.org/html/rfc6474#page-3">RFC 6474 p.3</a>
1720         */
1721        public List<Deathplace> getDeathplaces() {
1722                return getProperties(Deathplace.class);
1723        }
1724
1725        /**
1726         * <p>
1727         * Gets the person's place of death.
1728         * </p>
1729         * <p>
1730         * <b>Property name:</b> {@code DEATHPLACE}<br>
1731         * <b>Supported versions:</b> {@code 4.0}
1732         * </p>
1733         * @return the first deathplace property or null if not set
1734         * @see <a href="http://tools.ietf.org/html/rfc6474#page-3">RFC 6474 p.3</a>
1735         */
1736        public Deathplace getDeathplace() {
1737                return getProperty(Deathplace.class);
1738        }
1739
1740        /**
1741         * <p>
1742         * Sets the person's place of death.
1743         * </p>
1744         * <p>
1745         * <b>Property name:</b> {@code DEATHPLACE}<br>
1746         * <b>Supported versions:</b> {@code 4.0}
1747         * </p>
1748         * @param altRepresentations the alternative representations of the same
1749         * value. These properties contain the same information, but in different
1750         * forms (such as different languages). See {@link VCardParameters#getAltId
1751         * this description of the ALTID parameter} for more information. Note that
1752         * this method automatically assigns an appropriate ALTID parameter to each
1753         * property.
1754         * @see <a href="http://tools.ietf.org/html/rfc6474#page-3">RFC 6474 p.3</a>
1755         */
1756        public void setDeathplaceAlt(Deathplace... altRepresentations) {
1757                setPropertyAlt(Deathplace.class, altRepresentations);
1758        }
1759
1760        /**
1761         * <p>
1762         * Sets the person's place of death.
1763         * </p>
1764         * <p>
1765         * <b>Property name:</b> {@code DEATHPLACE}<br>
1766         * <b>Supported versions:</b> {@code 4.0}
1767         * </p>
1768         * @param deathplace the deathplace property or null to remove
1769         * @see <a href="http://tools.ietf.org/html/rfc6474#page-3">RFC 6474 p.3</a>
1770         */
1771        public void setDeathplace(Deathplace deathplace) {
1772                setProperty(Deathplace.class, deathplace);
1773        }
1774
1775        /**
1776         * <p>
1777         * Gets all {@link Deathdate} property instances.
1778         * </p>
1779         * <p>
1780         * There may be multiple instances if alternative representations are
1781         * defined (see {@link #setDeathdateAlt(Deathdate...) setDeathdateAlt}).
1782         * </p>
1783         * <p>
1784         * <b>Property name:</b> {@code DEATHDATE}<br>
1785         * <b>Supported versions:</b> {@code 4.0}
1786         * </p>
1787         * @return the death date properties (any changes made this list will affect
1788         * the {@link VCard} object and vice versa)
1789         * @see <a href="http://tools.ietf.org/html/rfc6474#page-4">RFC 6474 p.4</a>
1790         */
1791        public List<Deathdate> getDeathdates() {
1792                return getProperties(Deathdate.class);
1793        }
1794
1795        /**
1796         * <p>
1797         * Gets the person's time of death.
1798         * </p>
1799         * <p>
1800         * <b>Property name:</b> {@code DEATHDATE}<br>
1801         * <b>Supported versions:</b> {@code 4.0}
1802         * </p>
1803         * @return the first death date property or null if not set
1804         * @see <a href="http://tools.ietf.org/html/rfc6474">RFC 6474</a>
1805         * @see <a href="http://tools.ietf.org/html/rfc6474#page-4">RFC 6474 p.4</a>
1806         */
1807        public Deathdate getDeathdate() {
1808                return getProperty(Deathdate.class);
1809        }
1810
1811        /**
1812         * <p>
1813         * Sets the person's time of death.
1814         * </p>
1815         * <p>
1816         * <b>Property name:</b> {@code DEATHDATE}<br>
1817         * <b>Supported versions:</b> {@code 4.0}
1818         * </p>
1819         * @param altRepresentations the alternative representations of the same
1820         * value. These properties contain the same information, but in different
1821         * forms (such as different languages). See {@link VCardParameters#getAltId
1822         * this description of the ALTID parameter} for more information. Note that
1823         * this method automatically assigns an appropriate ALTID parameter to each
1824         * property.
1825         * @see <a href="http://tools.ietf.org/html/rfc6474#page-4">RFC 6474 p.4</a>
1826         */
1827        public void setDeathdateAlt(Deathdate... altRepresentations) {
1828                setPropertyAlt(Deathdate.class, altRepresentations);
1829        }
1830
1831        /**
1832         * <p>
1833         * Sets the person's time of death.
1834         * </p>
1835         * <p>
1836         * <b>Property name:</b> {@code DEATHDATE}<br>
1837         * <b>Supported versions:</b> {@code 4.0}
1838         * </p>
1839         * @param date the death date or null to remove
1840         * @return the property object that was created
1841         * @see <a href="http://tools.ietf.org/html/rfc6474">RFC 6474</a>
1842         * @see <a href="http://tools.ietf.org/html/rfc6474#page-4">RFC 6474 p.4</a>
1843         */
1844        public Deathdate setDeathdate(LocalDate date) {
1845                Deathdate type = (date == null) ? null : new Deathdate(date);
1846                setDeathdate(type);
1847                return type;
1848        }
1849
1850        /**
1851         * <p>
1852         * Sets the person's time of death.
1853         * </p>
1854         * <p>
1855         * <b>Property name:</b> {@code DEATHDATE}<br>
1856         * <b>Supported versions:</b> {@code 4.0}
1857         * </p>
1858         * @param deathdate the death date property or null to remove
1859         * @see <a href="http://tools.ietf.org/html/rfc6474">RFC 6474</a>
1860         * @see <a href="http://tools.ietf.org/html/rfc6474#page-4">RFC 6474 p.4</a>
1861         */
1862        public void setDeathdate(Deathdate deathdate) {
1863                setProperty(Deathdate.class, deathdate);
1864        }
1865
1866        /**
1867         * <p>
1868         * Gets all {@link Birthday} property instances.
1869         * </p>
1870         * <p>
1871         * There may be multiple instances if alternative representations are
1872         * defined (see {@link #setBirthdayAlt(Birthday...) setBirthdayAlt}).
1873         * </p>
1874         * <p>
1875         * <b>Property name:</b> {@code BDAY}<br>
1876         * <b>Supported versions:</b> {@code 4.0*}<br>
1877         * <i>* Only 4.0 supports alternative representations</i>
1878         * </p>
1879         * @return the birthday properties (any changes made this list will affect
1880         * the {@link VCard} object and vice versa)
1881         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1882         * p.30</a>
1883         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
1884         * p.11</a>
1885         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
1886         */
1887        public List<Birthday> getBirthdays() {
1888                return getProperties(Birthday.class);
1889        }
1890
1891        /**
1892         * <p>
1893         * Gets the person's birthday.
1894         * </p>
1895         * <p>
1896         * <b>Property name:</b> {@code BDAY}<br>
1897         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1898         * </p>
1899         * @return the first birthday property or null if not set
1900         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1901         * p.30</a>
1902         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
1903         * p.11</a>
1904         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
1905         */
1906        public Birthday getBirthday() {
1907                return getProperty(Birthday.class);
1908        }
1909
1910        /**
1911         * <p>
1912         * Sets the person's birthday.
1913         * </p>
1914         * <p>
1915         * <b>Property name:</b> {@code BDAY}<br>
1916         * <b>Supported versions:</b> {@code 4.0*}<br>
1917         * <i>* Only 4.0 supports alternative representations</i>
1918         * </p>
1919         * @param altRepresentations the alternative representations of the same
1920         * value. These properties contain the same information, but in different
1921         * forms (such as different languages). See {@link VCardParameters#getAltId
1922         * this description of the ALTID parameter} for more information. Note that
1923         * this method automatically assigns an appropriate ALTID parameter to each
1924         * property.
1925         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1926         * p.30</a>
1927         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
1928         * p.11</a>
1929         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
1930         */
1931        public void setBirthdayAlt(Birthday... altRepresentations) {
1932                setPropertyAlt(Birthday.class, altRepresentations);
1933        }
1934
1935        /**
1936         * <p>
1937         * Sets the person's birthday.
1938         * </p>
1939         * <p>
1940         * <b>Property name:</b> {@code BDAY}<br>
1941         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1942         * </p>
1943         * @param date the birthday or null to remove
1944         * @return the property object that was created
1945         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1946         * p.30</a>
1947         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
1948         * p.11</a>
1949         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
1950         */
1951        public Birthday setBirthday(LocalDate date) {
1952                Birthday type = (date == null) ? null : new Birthday(date);
1953                setBirthday(type);
1954                return type;
1955        }
1956
1957        /**
1958         * <p>
1959         * Sets the person's birthday.
1960         * </p>
1961         * <p>
1962         * <b>Property name:</b> {@code BDAY}<br>
1963         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
1964         * </p>
1965         * @param birthday the birthday or null to remove
1966         * @see <a href="http://tools.ietf.org/html/rfc6350#page-30">RFC 6350
1967         * p.30</a>
1968         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
1969         * p.11</a>
1970         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
1971         */
1972        public void setBirthday(Birthday birthday) {
1973                setProperty(Birthday.class, birthday);
1974        }
1975
1976        /**
1977         * <p>
1978         * Gets all {@link Anniversary} property instances.
1979         * </p>
1980         * <p>
1981         * There may be multiple instances if alternative representations are
1982         * defined (see {@link #setAnniversaryAlt(Anniversary...) setAnniversaryAlt}
1983         * ).
1984         * </p>
1985         * <p>
1986         * <b>Property name:</b> {@code ANNIVERSARY}<br>
1987         * <b>Supported versions:</b> {@code 4.0}
1988         * </p>
1989         * @return the anniversary properties (any changes made this list will
1990         * affect the {@link VCard} object and vice versa)
1991         * @see <a href="http://tools.ietf.org/html/rfc6350#page-31">RFC 6350
1992         * p.31</a>
1993         */
1994        public List<Anniversary> getAnniversaries() {
1995                return getProperties(Anniversary.class);
1996        }
1997
1998        /**
1999         * <p>
2000         * Gets the person's anniversary.
2001         * </p>
2002         * <p>
2003         * <b>Property name:</b> {@code ANNIVERSARY}<br>
2004         * <b>Supported versions:</b> {@code 4.0}
2005         * </p>
2006         * @return the first anniversary property or null if not set
2007         * @see <a href="http://tools.ietf.org/html/rfc6350#page-31">RFC 6350
2008         * p.31</a>
2009         */
2010        public Anniversary getAnniversary() {
2011                return getProperty(Anniversary.class);
2012        }
2013
2014        /**
2015         * <p>
2016         * Sets the person's anniversary.
2017         * </p>
2018         * <p>
2019         * <b>Property name:</b> {@code ANNIVERSARY}<br>
2020         * <b>Supported versions:</b> {@code 4.0}
2021         * </p>
2022         * @param altRepresentations the alternative representations of the same
2023         * value. These properties contain the same information, but in different
2024         * forms (such as different languages). See {@link VCardParameters#getAltId
2025         * this description of the ALTID parameter} for more information. Note that
2026         * this method automatically assigns an appropriate ALTID parameter to each
2027         * property.
2028         * @see <a href="http://tools.ietf.org/html/rfc6350#page-31">RFC 6350
2029         * p.31</a>
2030         */
2031        public void setAnniversaryAlt(Anniversary... altRepresentations) {
2032                setPropertyAlt(Anniversary.class, altRepresentations);
2033        }
2034
2035        /**
2036         * <p>
2037         * Sets the person's anniversary.
2038         * </p>
2039         * <p>
2040         * <b>Property name:</b> {@code ANNIVERSARY}<br>
2041         * <b>Supported versions:</b> {@code 4.0}
2042         * </p>
2043         * @param date the date of the anniversary or null to remove
2044         * @return the property object that was created
2045         * @see <a href="http://tools.ietf.org/html/rfc6350#page-31">RFC 6350
2046         * p.31</a>
2047         */
2048        public Anniversary setAnniversary(LocalDate date) {
2049                Anniversary type = (date == null) ? null : new Anniversary(date);
2050                setAnniversary(type);
2051                return type;
2052        }
2053
2054        /**
2055         * <p>
2056         * Sets the person's anniversary.
2057         * </p>
2058         * <p>
2059         * <b>Property name:</b> {@code ANNIVERSARY}<br>
2060         * <b>Supported versions:</b> {@code 4.0}
2061         * </p>
2062         * @param anniversary the anniversary property or null to remove
2063         * @see <a href="http://tools.ietf.org/html/rfc6350#page-31">RFC 6350
2064         * p.31</a>
2065         */
2066        public void setAnniversary(Anniversary anniversary) {
2067                setProperty(Anniversary.class, anniversary);
2068        }
2069
2070        /**
2071         * Gets the time that the vCard was last modified.
2072         * <p>
2073         * <b>Property name:</b> {@code REV}<br>
2074         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2075         * </p>
2076         * @return the revision property or null if not set
2077         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
2078         * p.45</a>
2079         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
2080         * p.22</a>
2081         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2082         */
2083        public Revision getRevision() {
2084                return getProperty(Revision.class);
2085        }
2086
2087        /**
2088         * <p>
2089         * Sets the time that the vCard was last modified.
2090         * </p>
2091         * <p>
2092         * <b>Property name:</b> {@code REV}<br>
2093         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2094         * </p>
2095         * @param revision the revision property or null to remove
2096         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
2097         * p.45</a>
2098         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
2099         * p.22</a>
2100         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2101         */
2102        public void setRevision(Revision revision) {
2103                setProperty(Revision.class, revision);
2104        }
2105
2106        /**
2107         * <p>
2108         * Sets the time that the vCard was last modified.
2109         * </p>
2110         * <p>
2111         * <b>Property name:</b> {@code REV}<br>
2112         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2113         * </p>
2114         * @param rev the last modified time ({@link Instant} recommended) or null
2115         * to remove
2116         * @return the property object that was created
2117         * @see <a href="http://tools.ietf.org/html/rfc6350#page-45">RFC 6350
2118         * p.45</a>
2119         * @see <a href="http://tools.ietf.org/html/rfc2426#page-22">RFC 2426
2120         * p.22</a>
2121         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2122         */
2123        public Revision setRevision(Temporal rev) {
2124                Revision type = (rev == null) ? null : new Revision(rev);
2125                setRevision(type);
2126                return type;
2127        }
2128
2129        /**
2130         * <p>
2131         * Gets the product ID, which identifies the software that created the
2132         * vCard.
2133         * </p>
2134         * <p>
2135         * <b>Property name:</b> {@code PRODID}<br>
2136         * <b>Supported versions:</b> {@code 3.0, 4.0}
2137         * </p>
2138         * @return the product ID property or null if not set
2139         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
2140         * p.44</a>
2141         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
2142         * p.21</a>
2143         */
2144        public ProductId getProductId() {
2145                return getProperty(ProductId.class);
2146        }
2147
2148        /**
2149         * <p>
2150         * Sets the product ID, which identifies the software that created the
2151         * vCard.
2152         * </p>
2153         * <p>
2154         * <b>Property name:</b> {@code PRODID}<br>
2155         * <b>Supported versions:</b> {@code 3.0, 4.0}
2156         * </p>
2157         * @param productId the product ID property or null to remove
2158         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
2159         * p.44</a>
2160         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
2161         * p.21</a>
2162         */
2163        public void setProductId(ProductId productId) {
2164                setProperty(ProductId.class, productId);
2165        }
2166
2167        /**
2168         * <p>
2169         * Sets the product ID, which identifies the software that created the
2170         * vCard.
2171         * </p>
2172         * <p>
2173         * <b>Property name:</b> {@code PRODID}<br>
2174         * <b>Supported versions:</b> {@code 3.0, 4.0}
2175         * </p>
2176         * @param productId the product ID (e.g. "ez-vcard 1.0") or null to remove
2177         * @return the property object that was created
2178         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
2179         * p.44</a>
2180         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
2181         * p.21</a>
2182         */
2183        public ProductId setProductId(String productId) {
2184                ProductId type = (productId == null) ? null : new ProductId(productId);
2185                setProductId(type);
2186                return type;
2187        }
2188
2189        /**
2190         * <p>
2191         * Gets the mailing addresses.
2192         * </p>
2193         * <p>
2194         * <b>Property name:</b> {@code ADR}<br>
2195         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2196         * </p>
2197         * @return the mailing address properties (any changes made this list will
2198         * affect the {@link VCard} object and vice versa)
2199         * @see <a href="http://tools.ietf.org/html/rfc6350#page-32">RFC 6350
2200         * p.32</a>
2201         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
2202         * p.11</a>
2203         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
2204         */
2205        public List<Address> getAddresses() {
2206                return getProperties(Address.class);
2207        }
2208
2209        /**
2210         * <p>
2211         * Adds a mailing address.
2212         * </p>
2213         * <p>
2214         * <b>Property name:</b> {@code ADR}<br>
2215         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2216         * </p>
2217         * @param address the mailing address property to add
2218         * @see <a href="http://tools.ietf.org/html/rfc6350#page-32">RFC 6350
2219         * p.32</a>
2220         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
2221         * p.11</a>
2222         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
2223         */
2224        public void addAddress(Address address) {
2225                addProperty(address);
2226        }
2227
2228        /**
2229         * <p>
2230         * Adds a mailing address.
2231         * </p>
2232         * <p>
2233         * <b>Property name:</b> {@code ADR}<br>
2234         * <b>Supported versions:</b> {@code 4.0*}<br>
2235         * <i>* Only 4.0 supports alternative representations</i>
2236         * </p>
2237         * @param altRepresentations the alternative representations of the same
2238         * value. These properties contain the same information, but in different
2239         * forms (such as different languages). See {@link VCardParameters#getAltId
2240         * this description of the ALTID parameter} for more information. Note that
2241         * this method automatically assigns an appropriate ALTID parameter to each
2242         * property.
2243         * @see <a href="http://tools.ietf.org/html/rfc6350#page-32">RFC 6350
2244         * p.32</a>
2245         * @see <a href="http://tools.ietf.org/html/rfc2426#page-11">RFC 2426
2246         * p.11</a>
2247         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.11</a>
2248         */
2249        public void addAddressAlt(Address... altRepresentations) {
2250                addPropertyAlt(Address.class, altRepresentations);
2251        }
2252
2253        /**
2254         * <p>
2255         * Gets all mailing labels that could not be assigned to an {@link Address}
2256         * property. Use {@link Address#getLabel} to get a label that has been
2257         * assigned to an address.
2258         * </p>
2259         * <p>
2260         * <b>Property name:</b> {@code LABEL}<br>
2261         * <b>Supported versions:</b> {@code 2.1, 3.0}
2262         * </p>
2263         * @return the orphaned label properties (any changes made this list will
2264         * affect the {@link VCard} object and vice versa)
2265         * @see <a href="http://tools.ietf.org/html/rfc2426#page-13">RFC 2426
2266         * p.13</a>
2267         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.12</a>
2268         */
2269        public List<Label> getOrphanedLabels() {
2270                return getProperties(Label.class);
2271        }
2272
2273        /**
2274         * <p>
2275         * Adds a mailing label which is not associated with an {@link Address}
2276         * property.
2277         * </p>
2278         * <p>
2279         * Use of this method is strongly discouraged. To add a mailing label to an
2280         * address, use the {@link Address#setLabel} method.
2281         * </p>
2282         * <p>
2283         * <b>Property name:</b> {@code LABEL}<br>
2284         * <b>Supported versions:</b> {@code 2.1, 3.0}
2285         * </p>
2286         * @param label the orphaned label property to add
2287         * @see <a href="http://tools.ietf.org/html/rfc2426#page-13">RFC 2426
2288         * p.13</a>
2289         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.12</a>
2290         */
2291        public void addOrphanedLabel(Label label) {
2292                addProperty(label);
2293        }
2294
2295        /**
2296         * <p>
2297         * Gets the email addresses.
2298         * </p>
2299         * <p>
2300         * <b>Property name:</b> {@code EMAIL}<br>
2301         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2302         * </p>
2303         * @return the email address properties (any changes made this list will
2304         * affect the {@link VCard} object and vice versa)
2305         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
2306         * p.36</a>
2307         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2308         * p.15</a>
2309         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2310         */
2311        public List<Email> getEmails() {
2312                return getProperties(Email.class);
2313        }
2314
2315        /**
2316         * <p>
2317         * Adds an email address.
2318         * </p>
2319         * <p>
2320         * <b>Property name:</b> {@code EMAIL}<br>
2321         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2322         * </p>
2323         * @param email the email address property to add
2324         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
2325         * p.36</a>
2326         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2327         * p.15</a>
2328         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2329         */
2330        public void addEmail(Email email) {
2331                addProperty(email);
2332        }
2333
2334        /**
2335         * <p>
2336         * Adds an email address.
2337         * </p>
2338         * <p>
2339         * <b>Property name:</b> {@code EMAIL}<br>
2340         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2341         * </p>
2342         * @param email the email address to add (e.g. "johndoe@aol.com")
2343         * @param types the type(s) to assign to the email
2344         * @return the property object that was created
2345         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
2346         * p.36</a>
2347         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2348         * p.15</a>
2349         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2350         */
2351        public Email addEmail(String email, EmailType... types) {
2352                Email property = new Email(email);
2353                property.getTypes().addAll(Arrays.asList(types));
2354                addEmail(property);
2355                return property;
2356        }
2357
2358        /**
2359         * <p>
2360         * Adds an email address.
2361         * </p>
2362         * <p>
2363         * <b>Property name:</b> {@code EMAIL}<br>
2364         * <b>Supported versions:</b> {@code 4.0*}<br>
2365         * <i>* Only 4.0 supports alternative representations</i>
2366         * </p>
2367         * @param altRepresentations the alternative representations of the same
2368         * value. These properties contain the same information, but in different
2369         * forms (such as different languages). See {@link VCardParameters#getAltId
2370         * this description of the ALTID parameter} for more information. Note that
2371         * this method automatically assigns an appropriate ALTID parameter to each
2372         * property.
2373         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
2374         * p.36</a>
2375         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2376         * p.15</a>
2377         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2378         */
2379        public void addEmailAlt(Email... altRepresentations) {
2380                addPropertyAlt(Email.class, altRepresentations);
2381        }
2382
2383        /**
2384         * <p>
2385         * Gets the telephone numbers.
2386         * </p>
2387         * <p>
2388         * <b>Property name:</b> {@code TEL}<br>
2389         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2390         * </p>
2391         * @return the telephone number properties (any changes made this list will
2392         * affect the {@link VCard} object and vice versa)
2393         * @see <a href="http://tools.ietf.org/html/rfc6350#page-34">RFC 6350
2394         * p.34</a>
2395         * @see <a href="http://tools.ietf.org/html/rfc2426#page-14">RFC 2426
2396         * p.14</a>
2397         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.13</a>
2398         */
2399        public List<Telephone> getTelephoneNumbers() {
2400                return getProperties(Telephone.class);
2401        }
2402
2403        /**
2404         * <p>
2405         * Adds a telephone number.
2406         * </p>
2407         * <p>
2408         * <b>Property name:</b> {@code TEL}<br>
2409         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2410         * </p>
2411         * @param telephoneNumber the telephone number property to add
2412         * @see <a href="http://tools.ietf.org/html/rfc6350#page-34">RFC 6350
2413         * p.34</a>
2414         * @see <a href="http://tools.ietf.org/html/rfc2426#page-14">RFC 2426
2415         * p.14</a>
2416         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.13</a>
2417         */
2418        public void addTelephoneNumber(Telephone telephoneNumber) {
2419                addProperty(telephoneNumber);
2420        }
2421
2422        /**
2423         * <p>
2424         * Adds a telephone number.
2425         * </p>
2426         * <p>
2427         * <b>Property name:</b> {@code TEL}<br>
2428         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2429         * </p>
2430         * @param telephoneNumber the telephone number to add (e.g. "+1
2431         * 555-555-5555")
2432         * @param types the type(s) to assign to the telephone number (e.g. "cell",
2433         * "work", etc)
2434         * @return the property object that was created
2435         * @see <a href="http://tools.ietf.org/html/rfc6350#page-34">RFC 6350
2436         * p.34</a>
2437         * @see <a href="http://tools.ietf.org/html/rfc2426#page-14">RFC 2426
2438         * p.14</a>
2439         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.13</a>
2440         */
2441        public Telephone addTelephoneNumber(String telephoneNumber, TelephoneType... types) {
2442                Telephone property = new Telephone(telephoneNumber);
2443                property.getTypes().addAll(Arrays.asList(types));
2444                addTelephoneNumber(property);
2445                return property;
2446        }
2447
2448        /**
2449         * <p>
2450         * Adds a telephone number.
2451         * </p>
2452         * <p>
2453         * <b>Property name:</b> {@code TEL}<br>
2454         * <b>Supported versions:</b> {@code 4.0*}<br>
2455         * <i>* Only 4.0 supports alternative representations</i>
2456         * </p>
2457         * @param altRepresentations the alternative representations of the same
2458         * value. These properties contain the same information, but in different
2459         * forms (such as different languages). See {@link VCardParameters#getAltId
2460         * this description of the ALTID parameter} for more information. Note that
2461         * this method automatically assigns an appropriate ALTID parameter to each
2462         * property.
2463         * @see <a href="http://tools.ietf.org/html/rfc6350#page-34">RFC 6350
2464         * p.34</a>
2465         * @see <a href="http://tools.ietf.org/html/rfc2426#page-14">RFC 2426
2466         * p.14</a>
2467         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.13</a>
2468         */
2469        public void addTelephoneNumberAlt(Telephone... altRepresentations) {
2470                addPropertyAlt(Telephone.class, altRepresentations);
2471        }
2472
2473        /**
2474         * <p>
2475         * Gets the email client that the person uses.
2476         * </p>
2477         * <p>
2478         * <b>Property name:</b> {@code MAILER}<br>
2479         * <b>Supported versions:</b> {@code 2.1, 3.0}
2480         * </p>
2481         * @return the mailer property or null if not set
2482         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2483         * p.15</a>
2484         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2485         */
2486        public Mailer getMailer() {
2487                return getProperty(Mailer.class);
2488        }
2489
2490        /**
2491         * <p>
2492         * Sets the email client that the person uses.
2493         * </p>
2494         * <p>
2495         * <b>Property name:</b> {@code MAILER}<br>
2496         * <b>Supported versions:</b> {@code 2.1, 3.0}
2497         * </p>
2498         * @param mailer the mailer property or null to remove
2499         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2500         * p.15</a>
2501         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2502         */
2503        public void setMailer(Mailer mailer) {
2504                setProperty(Mailer.class, mailer);
2505        }
2506
2507        /**
2508         * <p>
2509         * Sets the email client that the person uses.
2510         * </p>
2511         * <p>
2512         * <b>Property name:</b> {@code MAILER}<br>
2513         * <b>Supported versions:</b> {@code 2.1, 3.0}
2514         * </p>
2515         * @param mailer the email client (e.g. "Thunderbird") or null to remove
2516         * @return the property object that was created
2517         * @see <a href="http://tools.ietf.org/html/rfc2426#page-15">RFC 2426
2518         * p.15</a>
2519         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.15</a>
2520         */
2521        public Mailer setMailer(String mailer) {
2522                Mailer type = (mailer == null) ? null : new Mailer(mailer);
2523                setMailer(type);
2524                return type;
2525        }
2526
2527        /**
2528         * <p>
2529         * Gets the URLs. URLs can point to websites such as a personal homepage or
2530         * business website.
2531         * </p>
2532         * <p>
2533         * <b>Property name:</b> {@code URL}<br>
2534         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2535         * </p>
2536         * @return the URL properties (any changes made this list will affect the
2537         * {@link VCard} object and vice versa)
2538         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
2539         * p.47</a>
2540         * @see <a href="http://tools.ietf.org/html/rfc2426#page-25">RFC 2426
2541         * p.25</a>
2542         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
2543         */
2544        public List<Url> getUrls() {
2545                return getProperties(Url.class);
2546        }
2547
2548        /**
2549         * <p>
2550         * Adds a URL. URLs can point to websites such as a personal homepage or
2551         * business website.
2552         * </p>
2553         * <p>
2554         * <b>Property name:</b> {@code URL}<br>
2555         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2556         * </p>
2557         * @param url the URL property to add
2558         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
2559         * p.47</a>
2560         * @see <a href="http://tools.ietf.org/html/rfc2426#page-25">RFC 2426
2561         * p.25</a>
2562         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
2563         */
2564        public void addUrl(Url url) {
2565                addProperty(url);
2566        }
2567
2568        /**
2569         * <p>
2570         * Adds a URL. URLs can point to websites such as a personal homepage or
2571         * business website.
2572         * </p>
2573         * <p>
2574         * <b>Property name:</b> {@code URL}<br>
2575         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2576         * </p>
2577         * @param url the URL to add (e.g. "http://example.com")
2578         * @return the property object that was created
2579         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
2580         * p.47</a>
2581         * @see <a href="http://tools.ietf.org/html/rfc2426#page-25">RFC 2426
2582         * p.25</a>
2583         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
2584         */
2585        public Url addUrl(String url) {
2586                Url type = new Url(url);
2587                addUrl(type);
2588                return type;
2589        }
2590
2591        /**
2592         * <p>
2593         * Adds a URL. URLs can point to websites such as a personal homepage or
2594         * business website.
2595         * </p>
2596         * <p>
2597         * <b>Property name:</b> {@code URL}<br>
2598         * <b>Supported versions:</b> {@code 4.0*}<br>
2599         * <i>* Only 4.0 supports alternative representations</i>
2600         * </p>
2601         * @param altRepresentations the alternative representations of the same
2602         * value. These properties contain the same information, but in different
2603         * forms (such as different languages). See {@link VCardParameters#getAltId
2604         * this description of the ALTID parameter} for more information. Note that
2605         * this method automatically assigns an appropriate ALTID parameter to each
2606         * property.
2607         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
2608         * p.47</a>
2609         * @see <a href="http://tools.ietf.org/html/rfc2426#page-25">RFC 2426
2610         * p.25</a>
2611         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
2612         */
2613        public void addUrlAlt(Url... altRepresentations) {
2614                addPropertyAlt(Url.class, altRepresentations);
2615        }
2616
2617        /**
2618         * <p>
2619         * Gets all instances of the {@link Timezone} property.
2620         * </p>
2621         * <p>
2622         * Version 4.0 vCards may have multiple instances if alternative
2623         * representations are defined (see {@link #setTimezoneAlt(Timezone...)
2624         * setTimezoneAlt}) or if properties with different TYPE parameters are
2625         * defined.
2626         * </p>
2627         * <p>
2628         * <b>Property name:</b> {@code TZ}<br>
2629         * <b>Supported versions:</b> {@code 4.0*}<br>
2630         * <i>* Only 4.0 supports multiple instances</i>
2631         * </p>
2632         * @return the timezone properties (any changes made this list will affect
2633         * the {@link VCard} object and vice versa)
2634         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2635         * p.22</a>
2636         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2637         * p.16</a>
2638         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2639         */
2640        public List<Timezone> getTimezones() {
2641                return getProperties(Timezone.class);
2642        }
2643
2644        /**
2645         * <p>
2646         * Gets the timezone the person lives/works in.
2647         * </p>
2648         * <p>
2649         * <b>Property name:</b> {@code TZ}<br>
2650         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2651         * </p>
2652         * @return the first timezone property or null if not set
2653         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2654         * p.22</a>
2655         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2656         * p.16</a>
2657         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2658         */
2659        public Timezone getTimezone() {
2660                return getProperty(Timezone.class);
2661        }
2662
2663        /**
2664         * <p>
2665         * Sets the timezone the person lives/works in.
2666         * </p>
2667         * <p>
2668         * <b>Property name:</b> {@code TZ}<br>
2669         * <b>Supported versions:</b> {@code 4.0*}<br>
2670         * <i>* Only 4.0 supports alternative representations</i>
2671         * </p>
2672         * @param altRepresentations the alternative representations of the same
2673         * value. These properties contain the same information, but in different
2674         * forms (such as different languages). See {@link VCardParameters#getAltId
2675         * this description of the ALTID parameter} for more information. Note that
2676         * this method automatically assigns an appropriate ALTID parameter to each
2677         * property.
2678         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2679         * p.22</a>
2680         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2681         * p.16</a>
2682         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2683         */
2684        public void setTimezoneAlt(Timezone... altRepresentations) {
2685                setPropertyAlt(Timezone.class, altRepresentations);
2686        }
2687
2688        /**
2689         * <p>
2690         * Adds a timezone the person lives/works in.
2691         * </p>
2692         * <p>
2693         * <b>Property name:</b> {@code TZ}<br>
2694         * <b>Supported versions:</b> {@code 4.0*}<br>
2695         * <i>* Only 4.0 supports alternative representations</i>
2696         * </p>
2697         * @param altRepresentations the alternative representations of the same
2698         * value. These properties contain the same information, but in different
2699         * forms (such as different languages). See {@link VCardParameters#getAltId
2700         * this description of the ALTID parameter} for more information. Note that
2701         * this method automatically assigns an appropriate ALTID parameter to each
2702         * property.
2703         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2704         * p.22</a>
2705         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2706         * p.16</a>
2707         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2708         */
2709        public void addTimezoneAlt(Timezone... altRepresentations) {
2710                addPropertyAlt(Timezone.class, altRepresentations);
2711        }
2712
2713        /**
2714         * <p>
2715         * Sets the timezone the person lives/works in.
2716         * </p>
2717         * <p>
2718         * <b>Property name:</b> {@code TZ}<br>
2719         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2720         * </p>
2721         * @param timezone the timezone property or null to remove
2722         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2723         * p.22</a>
2724         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2725         * p.16</a>
2726         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2727         */
2728        public void setTimezone(Timezone timezone) {
2729                setProperty(Timezone.class, timezone);
2730        }
2731
2732        /**
2733         * <p>
2734         * Adds a timezone the person lives/works in.
2735         * </p>
2736         * <p>
2737         * <b>Property name:</b> {@code TZ}<br>
2738         * <b>Supported versions:</b> {@code 4.0*}<br>
2739         * <i>* Only 4.0 supports multiple instances</i>
2740         * </p>
2741         * @param timezone the timezone property to add
2742         * @see <a href="http://tools.ietf.org/html/rfc6350#page-22">RFC 6350
2743         * p.22</a>
2744         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2745         * p.16</a>
2746         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2747         */
2748        public void addTimezone(Timezone timezone) {
2749                addProperty(timezone);
2750        }
2751
2752        /**
2753         * <p>
2754         * Gets all instances of the {@link Geo} property.
2755         * </p>
2756         * <p>
2757         * Version 4.0 vCards may have multiple instances if alternative
2758         * representations are defined (see {@link #setGeoAlt(Geo...) setGeoAlt}) or
2759         * if properties with different TYPE parameters are defined.
2760         * </p>
2761         * <p>
2762         * <b>Property name:</b> {@code GEO}<br>
2763         * <b>Supported versions:</b> {@code 4.0*}<br>
2764         * <i>* Only 4.0 supports multiple instances</i>
2765         * </p>
2766         * @return the geo properties (any changes made this list will affect the
2767         * {@link VCard} object and vice versa)
2768         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2769         * p.38</a>
2770         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2771         * p.16</a>
2772         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2773         */
2774        public List<Geo> getGeos() {
2775                return getProperties(Geo.class);
2776        }
2777
2778        /**
2779         * <p>
2780         * Gets the geographical position of where the person lives/works.
2781         * </p>
2782         * <p>
2783         * <b>Property name:</b> {@code GEO}<br>
2784         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2785         * </p>
2786         * @return the first geo property or null if not set
2787         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2788         * p.38</a>
2789         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2790         * p.16</a>
2791         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2792         */
2793        public Geo getGeo() {
2794                return getProperty(Geo.class);
2795        }
2796
2797        /**
2798         * <p>
2799         * Sets the geographical position of where the person lives/works.
2800         * </p>
2801         * <p>
2802         * <b>Property name:</b> {@code GEO}<br>
2803         * <b>Supported versions:</b> {@code 4.0*}<br>
2804         * <i>* Only 4.0 supports alternative representations</i>
2805         * </p>
2806         * @param altRepresentations the alternative representations of the same
2807         * value. These properties contain the same information, but in different
2808         * forms (such as different languages). See {@link VCardParameters#getAltId
2809         * this description of the ALTID parameter} for more information. Note that
2810         * this method automatically assigns an appropriate ALTID parameter to each
2811         * property.
2812         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2813         * p.38</a>
2814         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2815         * p.16</a>
2816         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2817         */
2818        public void setGeoAlt(Geo... altRepresentations) {
2819                setPropertyAlt(Geo.class, altRepresentations);
2820        }
2821
2822        /**
2823         * <p>
2824         * Adds a geographical position of where the person lives/works.
2825         * </p>
2826         * <p>
2827         * <b>Property name:</b> {@code GEO}<br>
2828         * <b>Supported versions:</b> {@code 4.0*}<br>
2829         * <i>* Only 4.0 supports alternative representations</i>
2830         * </p>
2831         * @param altRepresentations the alternative representations of the same
2832         * value. These properties contain the same information, but in different
2833         * forms (such as different languages). See {@link VCardParameters#getAltId
2834         * this description of the ALTID parameter} for more information. Note that
2835         * this method automatically assigns an appropriate ALTID parameter to each
2836         * property.
2837         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2838         * p.38</a>
2839         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2840         * p.16</a>
2841         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2842         */
2843        public void addGeoAlt(Geo... altRepresentations) {
2844                addPropertyAlt(Geo.class, altRepresentations);
2845        }
2846
2847        /**
2848         * <p>
2849         * Sets the geographical position of where the person lives/works.
2850         * </p>
2851         * <p>
2852         * <b>Property name:</b> {@code GEO}<br>
2853         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2854         * </p>
2855         * @param geo the geo property or null to remove
2856         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2857         * p.38</a>
2858         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2859         * p.16</a>
2860         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2861         */
2862        public void setGeo(Geo geo) {
2863                setProperty(Geo.class, geo);
2864        }
2865
2866        /**
2867         * <p>
2868         * Adds a geographical position of where the person lives/works. Note that
2869         * only version 4.0 vCards support multiple instances of this property.
2870         * </p>
2871         * <p>
2872         * <b>Property name:</b> {@code GEO}<br>
2873         * <b>Supported versions:</b> {@code 4.0*}<br>
2874         * <i>* Only 4.0 supports multiple instances</i>
2875         * </p>
2876         * @param geo the geo property to add
2877         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2878         * p.38</a>
2879         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2880         * p.16</a>
2881         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2882         */
2883        public void addGeo(Geo geo) {
2884                addProperty(geo);
2885        }
2886
2887        /**
2888         * <p>
2889         * Sets the geographical position of where the person lives/works.
2890         * </p>
2891         * <p>
2892         * <b>Property name:</b> {@code GEO}<br>
2893         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2894         * </p>
2895         * @param latitude the latitude
2896         * @param longitude the longitude
2897         * @return the property object that was created
2898         * @see <a href="http://tools.ietf.org/html/rfc6350#page-38">RFC 6350
2899         * p.38</a>
2900         * @see <a href="http://tools.ietf.org/html/rfc2426#page-16">RFC 2426
2901         * p.16</a>
2902         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.16</a>
2903         */
2904        public Geo setGeo(double latitude, double longitude) {
2905                Geo type = new Geo(latitude, longitude);
2906                setGeo(type);
2907                return type;
2908        }
2909
2910        /**
2911         * <p>
2912         * Gets all instances of the {@link Organization} property.
2913         * </p>
2914         * <p>
2915         * Version 4.0 vCards may have multiple instances if alternative
2916         * representations are defined (see
2917         * {@link #setOrganizationAlt(Organization...) setOrganizationAlt}) or if
2918         * properties with different TYPE parameters are defined.
2919         * </p>
2920         * <p>
2921         * <b>Property name:</b> {@code ORG}<br>
2922         * <b>Supported versions:</b> {@code 4.0*}<br>
2923         * <i>* Only 4.0 supports multiple instances</i>
2924         * </p>
2925         * @return the organization properties (any changes made this list will
2926         * affect the {@link VCard} object and vice versa)
2927         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
2928         * p.40</a>
2929         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
2930         * p.20</a>
2931         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2932         */
2933        public List<Organization> getOrganizations() {
2934                return getProperties(Organization.class);
2935        }
2936
2937        /**
2938         * <p>
2939         * Gets the hierarchy of department(s) to which the person belongs.
2940         * </p>
2941         * <p>
2942         * <b>Property name:</b> {@code ORG}<br>
2943         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
2944         * </p>
2945         * @return the first organization property or null if not set
2946         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
2947         * p.40</a>
2948         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
2949         * p.20</a>
2950         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2951         */
2952        public Organization getOrganization() {
2953                return getProperty(Organization.class);
2954        }
2955
2956        /**
2957         * <p>
2958         * Sets the hierarchy of department(s) to which the person belongs.
2959         * </p>
2960         * <p>
2961         * <b>Property name:</b> {@code ORG}<br>
2962         * <b>Supported versions:</b> {@code 4.0*}<br>
2963         * <i>* Only 4.0 supports alternative representations</i>
2964         * </p>
2965         * @param altRepresentations the alternative representations of the same
2966         * value. These properties contain the same information, but in different
2967         * forms (such as different languages). See {@link VCardParameters#getAltId
2968         * this description of the ALTID parameter} for more information. Note that
2969         * this method automatically assigns an appropriate ALTID parameter to each
2970         * property.
2971         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
2972         * p.40</a>
2973         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
2974         * p.20</a>
2975         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
2976         */
2977        public void setOrganizationAlt(Organization... altRepresentations) {
2978                setPropertyAlt(Organization.class, altRepresentations);
2979        }
2980
2981        /**
2982         * <p>
2983         * Adds a hierarchy of department(s) to which the person belongs.
2984         * </p>
2985         * <p>
2986         * <b>Property name:</b> {@code ORG}<br>
2987         * <b>Supported versions:</b> {@code 4.0*}<br>
2988         * <i>* Only 4.0 supports alternative representations</i>
2989         * </p>
2990         * @param altRepresentations the alternative representations of the same
2991         * value. These properties contain the same information, but in different
2992         * forms (such as different languages). See {@link VCardParameters#getAltId
2993         * this description of the ALTID parameter} for more information. Note that
2994         * this method automatically assigns an appropriate ALTID parameter to each
2995         * property.
2996         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
2997         * p.40</a>
2998         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
2999         * p.20</a>
3000         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3001         */
3002        public void addOrganizationAlt(Organization... altRepresentations) {
3003                addPropertyAlt(Organization.class, altRepresentations);
3004        }
3005
3006        /**
3007         * <p>
3008         * Sets the hierarchy of departments to which the person belongs.
3009         * </p>
3010         * <p>
3011         * <b>Property name:</b> {@code ORG}<br>
3012         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3013         * </p>
3014         * @param organization the organization property or null to remove
3015         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
3016         * p.40</a>
3017         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3018         * p.20</a>
3019         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3020         */
3021        public void setOrganization(Organization organization) {
3022                setProperty(Organization.class, organization);
3023        }
3024
3025        /**
3026         * <p>
3027         * Adds a hierarchy of departments to which the person belongs. Note that
3028         * only version 4.0 vCards support multiple instances of this property.
3029         * </p>
3030         * <p>
3031         * <b>Property name:</b> {@code ORG}<br>
3032         * <b>Supported versions:</b> {@code 4.0*}<br>
3033         * <i>* Only 4.0 supports multiple instances</i>
3034         * </p>
3035         * @param organization the organization property to add
3036         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
3037         * p.40</a>
3038         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3039         * p.20</a>
3040         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3041         */
3042        public void addOrganization(Organization organization) {
3043                addProperty(organization);
3044        }
3045
3046        /**
3047         * <p>
3048         * Sets the hierarchy of departments to which the person belongs.
3049         * </p>
3050         * <p>
3051         * <b>Property name:</b> {@code ORG}<br>
3052         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3053         * </p>
3054         * @param departments the ordered list of department(s), starting with the
3055         * broadest and ending with the most specific (e.g. "Google", "Gmail Team",
3056         * "Spam Detection Squad") or an empty arguments list to remove
3057         * @return the property object that was created
3058         * @see <a href="http://tools.ietf.org/html/rfc6350#page-40">RFC 6350
3059         * p.40</a>
3060         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3061         * p.20</a>
3062         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3063         */
3064        public Organization setOrganization(String... departments) {
3065                Organization type = null;
3066                if (departments.length > 0) {
3067                        type = new Organization();
3068                        type.getValues().addAll(Arrays.asList(departments));
3069                }
3070                setOrganization(type);
3071                return type;
3072        }
3073
3074        /**
3075         * <p>
3076         * Gets all instances of the {@link Categories} property.
3077         * </p>
3078         * <p>
3079         * Version 4.0 vCards may have multiple instances if alternative
3080         * representations are defined (see {@link #setCategoriesAlt(Categories...)
3081         * setCategoriesAlt}) or if properties with different TYPE parameters are
3082         * defined.
3083         * </p>
3084         * <p>
3085         * <b>Property name:</b> {@code CATEGORIES}<br>
3086         * <b>Supported versions:</b> {@code 4.0*}<br>
3087         * <i>* Only 4.0 supports multiple instances</i>
3088         * </p>
3089         * @return the categories properties (any changes made this list will affect
3090         * the {@link VCard} object and vice versa)
3091         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3092         * p.43</a>
3093         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3094         * p.20</a>
3095         */
3096        public List<Categories> getCategoriesList() {
3097                return getProperties(Categories.class);
3098        }
3099
3100        /**
3101         * <p>
3102         * Gets the list of "keywords" or "tags" that can be used to describe the
3103         * person.
3104         * </p>
3105         * <p>
3106         * <b>Property name:</b> {@code CATEGORIES}<br>
3107         * <b>Supported versions:</b> {@code 3.0, 4.0}
3108         * </p>
3109         * @return the first categories property (can contain multiple values) or
3110         * null if not set
3111         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3112         * p.43</a>
3113         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3114         * p.20</a>
3115         */
3116        public Categories getCategories() {
3117                return getProperty(Categories.class);
3118        }
3119
3120        /**
3121         * <p>
3122         * Sets the list of "keywords" or "tags" that can be used to describe the
3123         * person.
3124         * </p>
3125         * <p>
3126         * <b>Property name:</b> {@code CATEGORIES}<br>
3127         * <b>Supported versions:</b> {@code 4.0*}<br>
3128         * <i>* Only 4.0 supports alternative representations</i>
3129         * </p>
3130         * @param altRepresentations the alternative representations of the same
3131         * value. These properties contain the same information, but in different
3132         * forms (such as different languages). See {@link VCardParameters#getAltId
3133         * this description of the ALTID parameter} for more information. Note that
3134         * this method automatically assigns an appropriate ALTID parameter to each
3135         * property.
3136         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3137         * p.43</a>
3138         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3139         * p.20</a>
3140         */
3141        public void setCategoriesAlt(Categories... altRepresentations) {
3142                setPropertyAlt(Categories.class, altRepresentations);
3143        }
3144
3145        /**
3146         * <p>
3147         * Adds a list of "keywords" or "tags" that can be used to describe the
3148         * person.
3149         * </p>
3150         * <p>
3151         * <b>Property name:</b> {@code CATEGORIES}<br>
3152         * <b>Supported versions:</b> {@code 4.0*}<br>
3153         * <i>* Only 4.0 supports alternative representations</i>
3154         * </p>
3155         * @param altRepresentations the alternative representations of the same
3156         * value. These properties contain the same information, but in different
3157         * forms (such as different languages). See {@link VCardParameters#getAltId
3158         * this description of the ALTID parameter} for more information. Note that
3159         * this method automatically assigns an appropriate ALTID parameter to each
3160         * property.
3161         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3162         * p.43</a>
3163         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3164         * p.20</a>
3165         */
3166        public void addCategoriesAlt(Categories... altRepresentations) {
3167                addPropertyAlt(Categories.class, altRepresentations);
3168        }
3169
3170        /**
3171         * <p>
3172         * Sets the list of "keywords" or "tags" that can be used to describe the
3173         * person.
3174         * </p>
3175         * <p>
3176         * <b>Property name:</b> {@code CATEGORIES}<br>
3177         * <b>Supported versions:</b> {@code 3.0, 4.0}
3178         * </p>
3179         * @param categories the categories property (can contain multiple values)
3180         * or null to remove
3181         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3182         * p.43</a>
3183         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3184         * p.20</a>
3185         */
3186        public void setCategories(Categories categories) {
3187                setProperty(Categories.class, categories);
3188        }
3189
3190        /**
3191         * <p>
3192         * Adds a list of "keywords" or "tags" that can be used to describe the
3193         * person. Note that only version 4.0 vCards support multiple instances of
3194         * this property.
3195         * </p>
3196         * <p>
3197         * <b>Property name:</b> {@code CATEGORIES}<br>
3198         * <b>Supported versions:</b> {@code 4.0*}<br>
3199         * <i>* Only 4.0 supports multiple instances</i>
3200         * </p>
3201         * @param categories the categories property to add (can contain multiple
3202         * values)
3203         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3204         * p.43</a>
3205         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3206         * p.20</a>
3207         */
3208        public void addCategories(Categories categories) {
3209                addProperty(categories);
3210        }
3211
3212        /**
3213         * <p>
3214         * Sets the list of "keywords" or "tags" that can be used to describe the
3215         * person.
3216         * </p>
3217         * <p>
3218         * <b>Property name:</b> {@code CATEGORIES}<br>
3219         * <b>Supported versions:</b> {@code 3.0, 4.0}
3220         * </p>
3221         * @param categories the categories (e.g. "swimmer", "biker", "knitter") or
3222         * an empty arguments list to remove
3223         * @return the property object that was created
3224         * @see <a href="http://tools.ietf.org/html/rfc6350#page-43">RFC 6350
3225         * p.43</a>
3226         * @see <a href="http://tools.ietf.org/html/rfc2426#page-20">RFC 2426
3227         * p.20</a>
3228         */
3229        public Categories setCategories(String... categories) {
3230                Categories type = null;
3231                if (categories.length > 0) {
3232                        type = new Categories();
3233                        type.getValues().addAll(Arrays.asList(categories));
3234                }
3235                setCategories(type);
3236                return type;
3237        }
3238
3239        /**
3240         * <p>
3241         * Gets information about the person's agent.
3242         * </p>
3243         * <p>
3244         * <b>Property name:</b> {@code AGENT}<br>
3245         * <b>Supported versions:</b> {@code 2.1, 3.0}
3246         * </p>
3247         * @return the agent property or null if not set
3248         * @see <a href="http://tools.ietf.org/html/rfc2426#page-19">RFC 2426
3249         * p.19</a>
3250         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.18</a>
3251         */
3252        public Agent getAgent() {
3253                return getProperty(Agent.class);
3254        }
3255
3256        /**
3257         * <p>
3258         * Sets information about the person's agent.
3259         * </p>
3260         * <p>
3261         * <b>Property name:</b> {@code AGENT}<br>
3262         * <b>Supported versions:</b> {@code 2.1, 3.0}
3263         * </p>
3264         * @param agent the agent property or null to remove
3265         * @see <a href="http://tools.ietf.org/html/rfc2426#page-19">RFC 2426
3266         * p.19</a>
3267         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.18</a>
3268         */
3269        public void setAgent(Agent agent) {
3270                setProperty(Agent.class, agent);
3271        }
3272
3273        /**
3274         * <p>
3275         * Gets the notes. Notes contain free-form, miscellaneous text.
3276         * </p>
3277         * <p>
3278         * <b>Property name:</b> {@code NOTE}<br>
3279         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3280         * </p>
3281         * @return the note properties (any changes made this list will affect the
3282         * {@link VCard} object and vice versa)
3283         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
3284         * p.44</a>
3285         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
3286         * p.21</a>
3287         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3288         */
3289        public List<Note> getNotes() {
3290                return getProperties(Note.class);
3291        }
3292
3293        /**
3294         * <p>
3295         * Adds a note. Notes contain free-form, miscellaneous text.
3296         * </p>
3297         * <p>
3298         * <b>Property name:</b> {@code NOTE}<br>
3299         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3300         * </p>
3301         * @param note the note property to add
3302         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
3303         * p.44</a>
3304         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
3305         * p.21</a>
3306         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3307         */
3308        public void addNote(Note note) {
3309                addProperty(note);
3310        }
3311
3312        /**
3313         * <p>
3314         * Adds a note. Notes contain free-form, miscellaneous text.
3315         * </p>
3316         * <p>
3317         * <b>Property name:</b> {@code NOTE}<br>
3318         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3319         * </p>
3320         * @param note the note to add
3321         * @return the property object that was created
3322         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
3323         * p.44</a>
3324         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
3325         * p.21</a>
3326         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3327         */
3328        public Note addNote(String note) {
3329                Note type = new Note(note);
3330                addNote(type);
3331                return type;
3332        }
3333
3334        /**
3335         * <p>
3336         * Adds a note. Notes contain free-form, miscellaneous text.
3337         * </p>
3338         * <p>
3339         * <b>Property name:</b> {@code NOTE}<br>
3340         * <b>Supported versions:</b> {@code 4.0*}<br>
3341         * <i>* Only 4.0 supports alternative representations</i>
3342         * </p>
3343         * @param altRepresentations the alternative representations of the same
3344         * value. These properties contain the same information, but in different
3345         * forms (such as different languages). See {@link VCardParameters#getAltId
3346         * this description of the ALTID parameter} for more information. Note that
3347         * this method automatically assigns an appropriate ALTID parameter to each
3348         * property.
3349         * @see <a href="http://tools.ietf.org/html/rfc6350#page-44">RFC 6350
3350         * p.44</a>
3351         * @see <a href="http://tools.ietf.org/html/rfc2426#page-21">RFC 2426
3352         * p.21</a>
3353         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.19</a>
3354         */
3355        public void addNoteAlt(Note... altRepresentations) {
3356                addPropertyAlt(Note.class, altRepresentations);
3357        }
3358
3359        /**
3360         * <p>
3361         * Gets the unique identifier of the vCard.
3362         * </p>
3363         * <p>
3364         * <b>Property name:</b> {@code UID}<br>
3365         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3366         * </p>
3367         * @return the unique identifier property or null if not set
3368         * @see <a href="http://tools.ietf.org/html/rfc6350#page-46">RFC 6350
3369         * p.46</a>
3370         * @see <a href="http://tools.ietf.org/html/rfc2426#page-24">RFC 2426
3371         * p.24</a>
3372         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
3373         */
3374        public Uid getUid() {
3375                return getProperty(Uid.class);
3376        }
3377
3378        /**
3379         * <p>
3380         * Sets the unique identifier of the vCard.
3381         * </p>
3382         * <p>
3383         * <b>Property name:</b> {@code UID}<br>
3384         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3385         * </p>
3386         * @param uid the unique identifier property or null to remove
3387         * @see <a href="http://tools.ietf.org/html/rfc6350#page-46">RFC 6350
3388         * p.46</a>
3389         * @see <a href="http://tools.ietf.org/html/rfc2426#page-24">RFC 2426
3390         * p.24</a>
3391         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.21</a>
3392         */
3393        public void setUid(Uid uid) {
3394                setProperty(Uid.class, uid);
3395        }
3396
3397        /**
3398         * <p>
3399         * Gets the public encryption keys.
3400         * </p>
3401         * <p>
3402         * <b>Property name:</b> {@code KEY}<br>
3403         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3404         * </p>
3405         * @return the key properties (any changes made this list will affect the
3406         * {@link VCard} object and vice versa)
3407         * @see <a href="http://tools.ietf.org/html/rfc6350#page-48">RFC 6350
3408         * p.48</a>
3409         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
3410         * p.26</a>
3411         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.22</a>
3412         */
3413        public List<Key> getKeys() {
3414                return getProperties(Key.class);
3415        }
3416
3417        /**
3418         * <p>
3419         * Adds a public encryption key.
3420         * </p>
3421         * <p>
3422         * <b>Property name:</b> {@code KEY}<br>
3423         * <b>Supported versions:</b> {@code 2.1, 3.0, 4.0}
3424         * </p>
3425         * @param key the key property to add
3426         * @see <a href="http://tools.ietf.org/html/rfc6350#page-48">RFC 6350
3427         * p.48</a>
3428         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
3429         * p.26</a>
3430         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.22</a>
3431         */
3432        public void addKey(Key key) {
3433                addProperty(key);
3434        }
3435
3436        /**
3437         * <p>
3438         * Adds a public encryption key.
3439         * </p>
3440         * <p>
3441         * <b>Property name:</b> {@code KEY}<br>
3442         * <b>Supported versions:</b> {@code 4.0*}<br>
3443         * <i>* Only 4.0 supports alternative representations</i>
3444         * </p>
3445         * @param altRepresentations the alternative representations of the same
3446         * value. These properties contain the same information, but in different
3447         * forms (such as different languages). See {@link VCardParameters#getAltId
3448         * this description of the ALTID parameter} for more information. Note that
3449         * this method automatically assigns an appropriate ALTID parameter to each
3450         * property.
3451         * @see <a href="http://tools.ietf.org/html/rfc6350#page-48">RFC 6350
3452         * p.48</a>
3453         * @see <a href="http://tools.ietf.org/html/rfc2426#page-26">RFC 2426
3454         * p.26</a>
3455         * @see <a href="http://www.imc.org/pdi/vcard-21.doc">vCard 2.1 p.22</a>
3456         */
3457        public void addKeyAlt(Key... altRepresentations) {
3458                addPropertyAlt(Key.class, altRepresentations);
3459        }
3460
3461        /**
3462         * <p>
3463         * Gets the instant messaging handles.
3464         * </p>
3465         * <p>
3466         * <b>Property name:</b> {@code IMPP}<br>
3467         * <b>Supported versions:</b> {@code 3.0, 4.0}
3468         * </p>
3469         * @return the IMPP properties (any changes made this list will affect the
3470         * {@link VCard} object and vice versa)
3471         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
3472         * p.36</a>
3473         * @see <a href="http://tools.ietf.org/html/rfc4770">RFC 4770</a>
3474         */
3475        public List<Impp> getImpps() {
3476                return getProperties(Impp.class);
3477        }
3478
3479        /**
3480         * <p>
3481         * Adds an instant messaging handle.
3482         * </p>
3483         * <p>
3484         * <b>Property name:</b> {@code IMPP}<br>
3485         * <b>Supported versions:</b> {@code 3.0, 4.0}
3486         * </p>
3487         * @param impp the IMPP property to add
3488         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
3489         * p.36</a>
3490         * @see <a href="http://tools.ietf.org/html/rfc4770">RFC 4770</a>
3491         */
3492        public void addImpp(Impp impp) {
3493                addProperty(impp);
3494        }
3495
3496        /**
3497         * <p>
3498         * Adds an instant messaging handle.
3499         * </p>
3500         * <p>
3501         * <b>Property name:</b> {@code IMPP}<br>
3502         * <b>Supported versions:</b> {@code 4.0*}<br>
3503         * <i>* Only 4.0 supports alternative representations</i>
3504         * </p>
3505         * @param altRepresentations the alternative representations of the same
3506         * value. These properties contain the same information, but in different
3507         * forms (such as different languages). See {@link VCardParameters#getAltId
3508         * this description of the ALTID parameter} for more information. Note that
3509         * this method automatically assigns an appropriate ALTID parameter to each
3510         * property.
3511         * @see <a href="http://tools.ietf.org/html/rfc6350#page-36">RFC 6350
3512         * p.36</a>
3513         * @see <a href="http://tools.ietf.org/html/rfc4770">RFC 4770</a>
3514         */
3515        public void addImppAlt(Impp... altRepresentations) {
3516                addPropertyAlt(Impp.class, altRepresentations);
3517        }
3518
3519        /**
3520         * <p>
3521         * Gets a list of people that the person is related to.
3522         * </p>
3523         * <p>
3524         * <b>Property name:</b> {@code RELATED}<br>
3525         * <b>Supported versions:</b> {@code 4.0}
3526         * </p>
3527         * @return the relation properties (any changes made this list will affect
3528         * the {@link VCard} object and vice versa)
3529         * @see <a href="http://tools.ietf.org/html/rfc6350#page-42">RFC 6350
3530         * p.42</a>
3531         */
3532        public List<Related> getRelations() {
3533                return getProperties(Related.class);
3534        }
3535
3536        /**
3537         * <p>
3538         * Adds someone that the person is related to.
3539         * </p>
3540         * <p>
3541         * <b>Property name:</b> {@code RELATED}<br>
3542         * <b>Supported versions:</b> {@code 4.0}
3543         * </p>
3544         * @param related the relation property to add
3545         * @see <a href="http://tools.ietf.org/html/rfc6350#page-42">RFC 6350
3546         * p.42</a>
3547         */
3548        public void addRelated(Related related) {
3549                addProperty(related);
3550        }
3551
3552        /**
3553         * <p>
3554         * Adds someone that the person is related to.
3555         * </p>
3556         * <p>
3557         * <b>Property name:</b> {@code RELATED}<br>
3558         * <b>Supported versions:</b> {@code 4.0}
3559         * </p>
3560         * @param altRepresentations the alternative representations of the same
3561         * value. These properties contain the same information, but in different
3562         * forms (such as different languages). See {@link VCardParameters#getAltId
3563         * this description of the ALTID parameter} for more information. Note that
3564         * this method automatically assigns an appropriate ALTID parameter to each
3565         * property.
3566         * @see <a href="http://tools.ietf.org/html/rfc6350#page-42">RFC 6350
3567         * p.42</a>
3568         */
3569        public void addRelatedAlt(Related... altRepresentations) {
3570                addPropertyAlt(Related.class, altRepresentations);
3571        }
3572
3573        /**
3574         * <p>
3575         * Gets the languages that the person speaks.
3576         * </p>
3577         * <p>
3578         * <b>Property name:</b> {@code LANG}<br>
3579         * <b>Supported versions:</b> {@code 4.0}
3580         * </p>
3581         * @return the language properties (any changes made this list will affect
3582         * the {@link VCard} object and vice versa)
3583         * @see <a href="http://tools.ietf.org/html/rfc6350#page-37">RFC 6350
3584         * p.37</a>
3585         */
3586        public List<Language> getLanguages() {
3587                return getProperties(Language.class);
3588        }
3589
3590        /**
3591         * <p>
3592         * Adds a language that the person speaks.
3593         * </p>
3594         * <p>
3595         * <b>Property name:</b> {@code LANG}<br>
3596         * <b>Supported versions:</b> {@code 4.0}
3597         * </p>
3598         * @param language the language property to add
3599         * @see <a href="http://tools.ietf.org/html/rfc6350#page-37">RFC 6350
3600         * p.37</a>
3601         */
3602        public void addLanguage(Language language) {
3603                addProperty(language);
3604        }
3605
3606        /**
3607         * <p>
3608         * Adds a language that the person speaks.
3609         * </p>
3610         * <p>
3611         * <b>Property name:</b> {@code LANG}<br>
3612         * <b>Supported versions:</b> {@code 4.0}
3613         * </p>
3614         * @param language the language to add (e.g. "en-us")
3615         * @return the property object that was created
3616         * @see <a href="http://tools.ietf.org/html/rfc6350#page-37">RFC 6350
3617         * p.37</a>
3618         */
3619        public Language addLanguage(String language) {
3620                Language type = new Language(language);
3621                addLanguage(type);
3622                return type;
3623        }
3624
3625        /**
3626         * <p>
3627         * Adds a language that the person speaks.
3628         * </p>
3629         * <p>
3630         * <b>Property name:</b> {@code LANG}<br>
3631         * <b>Supported versions:</b> {@code 4.0}
3632         * @param altRepresentations the alternative representations of the same
3633         * value. These properties contain the same information, but in different
3634         * forms (such as different languages). See {@link VCardParameters#getAltId
3635         * this description of the ALTID parameter} for more information. Note that
3636         * this method automatically assigns an appropriate ALTID parameter to each
3637         * property.
3638         * @see <a href="http://tools.ietf.org/html/rfc6350#page-37">RFC 6350
3639         * p.37</a>
3640         */
3641        public void addLanguageAlt(Language... altRepresentations) {
3642                addPropertyAlt(Language.class, altRepresentations);
3643        }
3644
3645        /**
3646         * <p>
3647         * Gets the URIs that can be used to schedule a meeting with the person on
3648         * his or her calendar.
3649         * </p>
3650         * <p>
3651         * <b>Property name:</b> {@code CALADRURI}<br>
3652         * <b>Supported versions:</b> {@code 4.0}
3653         * </p>
3654         * @return the calendar request URI properties (any changes made this list
3655         * will affect the {@link VCard} object and vice versa)
3656         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3657         * p.50</a>
3658         */
3659        public List<CalendarRequestUri> getCalendarRequestUris() {
3660                return getProperties(CalendarRequestUri.class);
3661        }
3662
3663        /**
3664         * <p>
3665         * Adds a URI that can be used to schedule a meeting with the person on his
3666         * or her calendar.
3667         * </p>
3668         * <p>
3669         * <b>Property name:</b> {@code CALADRURI}<br>
3670         * <b>Supported versions:</b> {@code 4.0}
3671         * </p>
3672         * @param calendarRequestUri the calendar request URI property to add
3673         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3674         * p.50</a>
3675         */
3676        public void addCalendarRequestUri(CalendarRequestUri calendarRequestUri) {
3677                addProperty(calendarRequestUri);
3678        }
3679
3680        /**
3681         * <p>
3682         * Adds a URI that can be used to schedule a meeting with the person on his
3683         * or her calendar.
3684         * </p>
3685         * <p>
3686         * <b>Property name:</b> {@code CALADRURI}<br>
3687         * <b>Supported versions:</b> {@code 4.0}
3688         * </p>
3689         * @param altRepresentations the alternative representations of the same
3690         * value. These properties contain the same information, but in different
3691         * forms (such as different languages). See {@link VCardParameters#getAltId
3692         * this description of the ALTID parameter} for more information. Note that
3693         * this method automatically assigns an appropriate ALTID parameter to each
3694         * property.
3695         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3696         * p.50</a>
3697         */
3698        public void addCalendarRequestUriAlt(CalendarRequestUri... altRepresentations) {
3699                addPropertyAlt(CalendarRequestUri.class, altRepresentations);
3700        }
3701
3702        /**
3703         * <p>
3704         * Gets the URIs that point to the person's calendar.
3705         * </p>
3706         * <p>
3707         * <b>Property name:</b> {@code CALURI}<br>
3708         * <b>Supported versions:</b> {@code 4.0}
3709         * </p>
3710         * @return the calendar URI properties (any changes made this list will
3711         * affect the {@link VCard} object and vice versa)
3712         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3713         * p.50</a>
3714         */
3715        public List<CalendarUri> getCalendarUris() {
3716                return getProperties(CalendarUri.class);
3717        }
3718
3719        /**
3720         * <p>
3721         * Adds a URI that points to the person's calendar.
3722         * </p>
3723         * <p>
3724         * <b>Property name:</b> {@code CALURI}<br>
3725         * <b>Supported versions:</b> {@code 4.0}
3726         * </p>
3727         * @param calendarUri the calendar URI property to add
3728         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3729         * p.50</a>
3730         */
3731        public void addCalendarUri(CalendarUri calendarUri) {
3732                addProperty(calendarUri);
3733        }
3734
3735        /**
3736         * <p>
3737         * Adds a URI that points to the person's calendar.
3738         * </p>
3739         * <p>
3740         * <b>Property name:</b> {@code CALURI}<br>
3741         * <b>Supported versions:</b> {@code 4.0}
3742         * </p>
3743         * @param altRepresentations the alternative representations of the same
3744         * value. These properties contain the same information, but in different
3745         * forms (such as different languages). See {@link VCardParameters#getAltId
3746         * this description of the ALTID parameter} for more information. Note that
3747         * this method automatically assigns an appropriate ALTID parameter to each
3748         * property.
3749         * @see <a href="http://tools.ietf.org/html/rfc6350#page-50">RFC 6350
3750         * p.50</a>
3751         */
3752        public void addCalendarUriAlt(CalendarUri... altRepresentations) {
3753                addPropertyAlt(CalendarUri.class, altRepresentations);
3754        }
3755
3756        /**
3757         * <p>
3758         * Gets the URLs that can be used to determine when the person is free or
3759         * busy.
3760         * </p>
3761         * <p>
3762         * <b>Property name:</b> {@code FBURL}<br>
3763         * <b>Supported versions:</b> {@code 4.0}
3764         * </p>
3765         * @return the free-busy URL properties (any changes made this list will
3766         * affect the {@link VCard} object and vice versa)
3767         * @see <a href="http://tools.ietf.org/html/rfc6350#page-49">RFC 6350
3768         * p.49</a>
3769         */
3770        public List<FreeBusyUrl> getFbUrls() {
3771                return getProperties(FreeBusyUrl.class);
3772        }
3773
3774        /**
3775         * <p>
3776         * Adds a URL that can be used to determine when the person is free or busy.
3777         * </p>
3778         * <p>
3779         * <b>Property name:</b> {@code FBURL}<br>
3780         * <b>Supported versions:</b> {@code 4.0}
3781         * </p>
3782         * @param fbUrl the free-busy URL property to add
3783         * @see <a href="http://tools.ietf.org/html/rfc6350#page-49">RFC 6350
3784         * p.49</a>
3785         */
3786        public void addFbUrl(FreeBusyUrl fbUrl) {
3787                addProperty(fbUrl);
3788        }
3789
3790        /**
3791         * <p>
3792         * Adds a URL that can be used to determine when the person is free or busy.
3793         * </p>
3794         * <p>
3795         * <b>Property name:</b> {@code FBURL}<br>
3796         * <b>Supported versions:</b> {@code 4.0}
3797         * </p>
3798         * @param altRepresentations the alternative representations of the same
3799         * value. These properties contain the same information, but in different
3800         * forms (such as different languages). See {@link VCardParameters#getAltId
3801         * this description of the ALTID parameter} for more information. Note that
3802         * this method automatically assigns an appropriate ALTID parameter to each
3803         * property.
3804         * @see <a href="http://tools.ietf.org/html/rfc6350#page-49">RFC 6350
3805         * p.49</a>
3806         */
3807        public void addFbUrlAlt(FreeBusyUrl... altRepresentations) {
3808                addPropertyAlt(FreeBusyUrl.class, altRepresentations);
3809        }
3810
3811        /**
3812         * <p>
3813         * Gets the properties that are used to assign globally-unique identifiers
3814         * to individual property instances. They are used for merging together
3815         * different versions of the same vCard.
3816         * </p>
3817         * <p>
3818         * <b>Property name:</b> {@code CLIENTPIDMAP}<br>
3819         * <b>Supported versions:</b> {@code 4.0}
3820         * </p>
3821         * @return the client PID map properties (any changes made this list will
3822         * affect the {@link VCard} object and vice versa)
3823         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
3824         * p.47</a>
3825         */
3826        public List<ClientPidMap> getClientPidMaps() {
3827                return getProperties(ClientPidMap.class);
3828        }
3829
3830        /**
3831         * <p>
3832         * Adds a property that is used to assign a globally-unique identifier to an
3833         * individual property instance. They are used for merging together
3834         * different versions of the same vCard.
3835         * </p>
3836         * <p>
3837         * <b>Property name:</b> {@code CLIENTPIDMAP}<br>
3838         * <b>Supported versions:</b> {@code 4.0}
3839         * </p>
3840         * @param clientPidMap the client PID map property to add
3841         * @see <a href="http://tools.ietf.org/html/rfc6350#page-47">RFC 6350
3842         * p.47</a>
3843         */
3844        public void addClientPidMap(ClientPidMap clientPidMap) {
3845                addProperty(clientPidMap);
3846        }
3847
3848        /**
3849         * <p>
3850         * Gets any XML data that is attached to the vCard.
3851         * </p>
3852         * <p>
3853         * These properties may be present if the vCard was encoded in XML ("xCard"
3854         * format) and the XML document contained non-standard elements. In this
3855         * case, the properties would contain all of the non-standard XML elements.
3856         * </p>
3857         * <p>
3858         * <b>Property name:</b> {@code XML}<br>
3859         * <b>Supported versions:</b> {@code 4.0}
3860         * </p>
3861         * @return the XML properties (any changes made this list will affect the
3862         * {@link VCard} object and vice versa)
3863         * @see <a href="http://tools.ietf.org/html/rfc6350#page-27">RFC 6350
3864         * p.27</a>
3865         */
3866        public List<Xml> getXmls() {
3867                return getProperties(Xml.class);
3868        }
3869
3870        /**
3871         * <p>
3872         * Adds XML data to the vCard.
3873         * </p>
3874         * <p>
3875         * These properties may be present if the vCard was encoded in XML ("xCard"
3876         * format) and the XML document contained non-standard elements. In this
3877         * case, the properties would contain all of the non-standard XML elements.
3878         * </p>
3879         * <p>
3880         * <b>Property name:</b> {@code XML}<br>
3881         * <b>Supported versions:</b> {@code 4.0}
3882         * </p>
3883         * @param xml the XML property to add
3884         * @see <a href="http://tools.ietf.org/html/rfc6350#page-27">RFC 6350
3885         * p.27</a>
3886         */
3887        public void addXml(Xml xml) {
3888                addProperty(xml);
3889        }
3890
3891        /**
3892         * <p>
3893         * Adds XML data to the vCard.
3894         * </p>
3895         * <p>
3896         * These properties may be present if the vCard was encoded in XML ("xCard"
3897         * format) and the XML document contained non-standard elements. In this
3898         * case, the properties would contain all of the non-standard XML elements.
3899         * </p>
3900         * <p>
3901         * <b>Property name:</b> {@code XML}<br>
3902         * <b>Supported versions:</b> {@code 4.0}
3903         * </p>
3904         * @param altRepresentations the alternative representations of the same
3905         * value. These properties contain the same information, but in different
3906         * forms (such as different languages). See {@link VCardParameters#getAltId
3907         * this description of the ALTID parameter} for more information. Note that
3908         * this method automatically assigns an appropriate ALTID parameter to each
3909         * property.
3910         * @see <a href="http://tools.ietf.org/html/rfc6350#page-27">RFC 6350
3911         * p.27</a>
3912         */
3913        public void addXmlAlt(Xml... altRepresentations) {
3914                addPropertyAlt(Xml.class, altRepresentations);
3915        }
3916
3917        /**
3918         * <p>
3919         * Gets the professional subject areas that the person is knowledgeable in.
3920         * </p>
3921         * <p>
3922         * <b>Property name:</b> {@code EXPERTISE}<br>
3923         * <b>Supported versions:</b> {@code 4.0}
3924         * </p>
3925         * @return the expertise properties (any changes made this list will affect
3926         * the {@link VCard} object and vice versa)
3927         * @see <a href="http://tools.ietf.org/html/rfc6715#page-3">RFC 6715 p.3</a>
3928         */
3929        public List<Expertise> getExpertise() {
3930                return getProperties(Expertise.class);
3931        }
3932
3933        /**
3934         * <p>
3935         * Adds a professional subject area that the person is knowledgeable in.
3936         * </p>
3937         * <p>
3938         * <b>Property name:</b> {@code EXPERTISE}<br>
3939         * <b>Supported versions:</b> {@code 4.0}
3940         * </p>
3941         * @param expertise the expertise property to add
3942         * @see <a href="http://tools.ietf.org/html/rfc6715#page-3">RFC 6715 p.3</a>
3943         */
3944        public void addExpertise(Expertise expertise) {
3945                addProperty(expertise);
3946        }
3947
3948        /**
3949         * <p>
3950         * Adds a professional subject area that the person is knowledgeable in.
3951         * </p>
3952         * <p>
3953         * <b>Property name:</b> {@code EXPERTISE}<br>
3954         * <b>Supported versions:</b> {@code 4.0}
3955         * </p>
3956         * @param expertise the professional subject area to add (e.g.
3957         * "programming")
3958         * @return the property object that was created
3959         * @see <a href="http://tools.ietf.org/html/rfc6715#page-3">RFC 6715 p.3</a>
3960         */
3961        public Expertise addExpertise(String expertise) {
3962                Expertise type = new Expertise(expertise);
3963                addExpertise(type);
3964                return type;
3965        }
3966
3967        /**
3968         * <p>
3969         * Adds a professional subject area that the person is knowledgeable in.
3970         * </p>
3971         * <p>
3972         * <b>Property name:</b> {@code EXPERTISE}<br>
3973         * <b>Supported versions:</b> {@code 4.0}
3974         * </p>
3975         * @param altRepresentations the alternative representations of the same
3976         * value. These properties contain the same information, but in different
3977         * forms (such as different languages). See {@link VCardParameters#getAltId
3978         * this description of the ALTID parameter} for more information. Note that
3979         * this method automatically assigns an appropriate ALTID parameter to each
3980         * property.
3981         * @see <a href="http://tools.ietf.org/html/rfc6715#page-3">RFC 6715 p.3</a>
3982         */
3983        public void addExpertiseAlt(Expertise... altRepresentations) {
3984                addPropertyAlt(Expertise.class, altRepresentations);
3985        }
3986
3987        /**
3988         * <p>
3989         * Gets the hobbies that the person actively engages in.
3990         * </p>
3991         * <p>
3992         * <b>Property name:</b> {@code HOBBY}<br>
3993         * <b>Supported versions:</b> {@code 4.0}
3994         * </p>
3995         * @return the hobby properties (any changes made this list will affect the
3996         * {@link VCard} object and vice versa)
3997         * @see <a href="http://tools.ietf.org/html/rfc6715#page-4">RFC 6715 p.4</a>
3998         */
3999        public List<Hobby> getHobbies() {
4000                return getProperties(Hobby.class);
4001        }
4002
4003        /**
4004         * <p>
4005         * Adds a hobby that the person actively engages in.
4006         * </p>
4007         * <p>
4008         * <b>Property name:</b> {@code HOBBY}<br>
4009         * <b>Supported versions:</b> {@code 4.0}
4010         * </p>
4011         * @param hobby the hobby property to add
4012         * @see <a href="http://tools.ietf.org/html/rfc6715#page-4">RFC 6715 p.4</a>
4013         */
4014        public void addHobby(Hobby hobby) {
4015                addProperty(hobby);
4016        }
4017
4018        /**
4019         * <p>
4020         * Adds a hobby that the person actively engages in.
4021         * </p>
4022         * <p>
4023         * <b>Property name:</b> {@code HOBBY}<br>
4024         * <b>Supported versions:</b> {@code 4.0}
4025         * </p>
4026         * @param hobby the hobby to add (e.g. "photography")
4027         * @return the property object that was created
4028         * @see <a href="http://tools.ietf.org/html/rfc6715#page-4">RFC 6715 p.4</a>
4029         */
4030        public Hobby addHobby(String hobby) {
4031                Hobby type = new Hobby(hobby);
4032                addHobby(type);
4033                return type;
4034        }
4035
4036        /**
4037         * <p>
4038         * Adds a hobby that the person actively engages in.
4039         * </p>
4040         * <p>
4041         * <b>Property name:</b> {@code HOBBY}<br>
4042         * <b>Supported versions:</b> {@code 4.0}
4043         * </p>
4044         * @param altRepresentations the alternative representations of the same
4045         * value. These properties contain the same information, but in different
4046         * forms (such as different languages). See {@link VCardParameters#getAltId
4047         * this description of the ALTID parameter} for more information. Note that
4048         * this method automatically assigns an appropriate ALTID parameter to each
4049         * property.
4050         * @see <a href="http://tools.ietf.org/html/rfc6715#page-4">RFC 6715 p.4</a>
4051         */
4052        public void addHobbyAlt(Hobby... altRepresentations) {
4053                addPropertyAlt(Hobby.class, altRepresentations);
4054        }
4055
4056        /**
4057         * <p>
4058         * Gets the person's interests.
4059         * </p>
4060         * <p>
4061         * <b>Property name:</b> {@code INTEREST}<br>
4062         * <b>Supported versions:</b> {@code 4.0}
4063         * </p>
4064         * @return the interest properties (any changes made this list will affect
4065         * the {@link VCard} object and vice versa)
4066         * @see <a href="http://tools.ietf.org/html/rfc6715#page-5">RFC 6715 p.5</a>
4067         */
4068        public List<Interest> getInterests() {
4069                return getProperties(Interest.class);
4070        }
4071
4072        /**
4073         * <p>
4074         * Adds an interest.
4075         * </p>
4076         * <p>
4077         * <b>Property name:</b> {@code INTEREST}<br>
4078         * <b>Supported versions:</b> {@code 4.0}
4079         * </p>
4080         * @param interest the interest property to add
4081         * @see <a href="http://tools.ietf.org/html/rfc6715#page-5">RFC 6715 p.5</a>
4082         */
4083        public void addInterest(Interest interest) {
4084                addProperty(interest);
4085        }
4086
4087        /**
4088         * <p>
4089         * Adds an interest.
4090         * </p>
4091         * <p>
4092         * <b>Property name:</b> {@code INTEREST}<br>
4093         * <b>Supported versions:</b> {@code 4.0}
4094         * </p>
4095         * @param interest the interest to add (e.g. "football")
4096         * @return the property object that was created
4097         * @see <a href="http://tools.ietf.org/html/rfc6715#page-5">RFC 6715 p.5</a>
4098         */
4099        public Interest addInterest(String interest) {
4100                Interest type = new Interest(interest);
4101                addInterest(type);
4102                return type;
4103        }
4104
4105        /**
4106         * <p>
4107         * Adds an interest.
4108         * </p>
4109         * <p>
4110         * <b>Property name:</b> {@code INTEREST}<br>
4111         * <b>Supported versions:</b> {@code 4.0}
4112         * </p>
4113         * @param altRepresentations the alternative representations of the same
4114         * value. These properties contain the same information, but in different
4115         * forms (such as different languages). See {@link VCardParameters#getAltId
4116         * this description of the ALTID parameter} for more information. Note that
4117         * this method automatically assigns an appropriate ALTID parameter to each
4118         * property.
4119         * @see <a href="http://tools.ietf.org/html/rfc6715#page-5">RFC 6715 p.5</a>
4120         */
4121        public void addInterestAlt(Interest... altRepresentations) {
4122                addPropertyAlt(Interest.class, altRepresentations);
4123        }
4124
4125        /**
4126         * <p>
4127         * Gets the organization directories.
4128         * </p>
4129         * <p>
4130         * <b>Property name:</b> {@code ORG-DIRECTORY}<br>
4131         * <b>Supported versions:</b> {@code 4.0}
4132         * </p>
4133         * @return the organization directory properties (any changes made this list
4134         * will affect the {@link VCard} object and vice versa)
4135         * @see <a href="http://tools.ietf.org/html/rfc6715#page-6">RFC 6715 p.6</a>
4136         */
4137        public List<OrgDirectory> getOrgDirectories() {
4138                return getProperties(OrgDirectory.class);
4139        }
4140
4141        /**
4142         * <p>
4143         * Adds an organization directory.
4144         * </p>
4145         * <p>
4146         * <b>Property name:</b> {@code ORG-DIRECTORY}<br>
4147         * <b>Supported versions:</b> {@code 4.0}
4148         * </p>
4149         * @param orgDirectory the organization directory property to add
4150         * @see <a href="http://tools.ietf.org/html/rfc6715#page-6">RFC 6715 p.6</a>
4151         */
4152        public void addOrgDirectory(OrgDirectory orgDirectory) {
4153                addProperty(orgDirectory);
4154        }
4155
4156        /**
4157         * <p>
4158         * Adds an organization directory.
4159         * </p>
4160         * <p>
4161         * <b>Property name:</b> {@code ORG-DIRECTORY}<br>
4162         * <b>Supported versions:</b> {@code 4.0}
4163         * </p>
4164         * @param orgDirectory the organization directory to add (e.g.
4165         * "http://company.com/staff")
4166         * @return the property object that was created
4167         * @see <a href="http://tools.ietf.org/html/rfc6715#page-6">RFC 6715 p.6</a>
4168         */
4169        public OrgDirectory addOrgDirectory(String orgDirectory) {
4170                OrgDirectory type = new OrgDirectory(orgDirectory);
4171                addOrgDirectory(type);
4172                return type;
4173        }
4174
4175        /**
4176         * <p>
4177         * Adds an organization directory.
4178         * </p>
4179         * <p>
4180         * <b>Property name:</b> {@code ORG-DIRECTORY}<br>
4181         * <b>Supported versions:</b> {@code 4.0}
4182         * </p>
4183         * @param altRepresentations the alternative representations of the same
4184         * value. These properties contain the same information, but in different
4185         * forms (such as different languages). See {@link VCardParameters#getAltId
4186         * this description of the ALTID parameter} for more information. Note that
4187         * this method automatically assigns an appropriate ALTID parameter to each
4188         * property.
4189         * @see <a href="http://tools.ietf.org/html/rfc6715#page-6">RFC 6715 p.6</a>
4190         */
4191        public void addOrgDirectoryAlt(OrgDirectory... altRepresentations) {
4192                addPropertyAlt(OrgDirectory.class, altRepresentations);
4193        }
4194
4195        /**
4196         * Iterates through each of the vCard's properties in no particular order.
4197         * Does not include the "BEGIN", "END", or "VERSION" properties.
4198         * @return the iterator
4199         */
4200        public Iterator<VCardProperty> iterator() {
4201                return properties.values().iterator();
4202        }
4203
4204        /**
4205         * Gets the first property of a given class.
4206         * @param clazz the property class
4207         * @param <T> the property class
4208         * @return the property or null if not found
4209         */
4210        public <T extends VCardProperty> T getProperty(Class<T> clazz) {
4211                return clazz.cast(properties.first(clazz));
4212        }
4213
4214        /**
4215         * Gets all properties of a given class.
4216         * @param clazz the property class
4217         * @param <T> the property class
4218         * @return the properties (any changes made this list will affect the
4219         * {@link VCard} object and vice versa)
4220         */
4221        public <T extends VCardProperty> List<T> getProperties(Class<T> clazz) {
4222                return new VCardPropertyList<>(clazz);
4223        }
4224
4225        /**
4226         * Gets all properties of a given class, grouping the alternative
4227         * representations of each property together (see:
4228         * {@link VCardParameters#getAltId description of ALTID})
4229         * @param clazz the property class
4230         * @param <T> the property class
4231         * @return the properties (this list is immutable)
4232         */
4233        public <T extends VCardProperty & HasAltId> List<List<T>> getPropertiesAlt(Class<T> clazz) {
4234                List<T> propertiesWithoutAltIds = new ArrayList<>();
4235                ListMultimap<String, T> propertiesWithAltIds = new ListMultimap<>();
4236                for (T property : getProperties(clazz)) {
4237                        String altId = property.getAltId();
4238                        if (altId == null) {
4239                                propertiesWithoutAltIds.add(property);
4240                        } else {
4241                                propertiesWithAltIds.put(altId, property);
4242                        }
4243                }
4244
4245                int size = propertiesWithoutAltIds.size() + propertiesWithAltIds.size();
4246                List<List<T>> listToReturn = new ArrayList<>(size);
4247                for (Map.Entry<String, List<T>> entry : propertiesWithAltIds) {
4248                        listToReturn.add(Collections.unmodifiableList(entry.getValue()));
4249                }
4250
4251                //put properties without ALTIDs at the end
4252                for (T property : propertiesWithoutAltIds) {
4253                        List<T> list = new ArrayList<>(1);
4254                        list.add(property);
4255                        listToReturn.add(Collections.unmodifiableList(list));
4256                }
4257
4258                return Collections.unmodifiableList(listToReturn);
4259        }
4260
4261        /**
4262         * Gets all the properties in this vCard.
4263         * @return the properties (this list is immutable)
4264         */
4265        public Collection<VCardProperty> getProperties() {
4266                return properties.values();
4267        }
4268
4269        /**
4270         * Adds a property.
4271         * @param property the property to add
4272         */
4273        public void addProperty(VCardProperty property) {
4274                properties.put(property.getClass(), property);
4275        }
4276
4277        /**
4278         * Replaces all existing properties of the given property instance's class
4279         * with the given property instance.
4280         * @param property the property
4281         * @return the properties that were replaced (this list is immutable)
4282         */
4283        public List<VCardProperty> setProperty(VCardProperty property) {
4284                return properties.replace(property.getClass(), property);
4285        }
4286
4287        /**
4288         * Replaces all existing properties of the given class with a single
4289         * property instance. If the property instance is null, then all instances
4290         * of that property will be removed.
4291         * @param clazz the property class (e.g. "Note.class")
4292         * @param property the property or null to remove
4293         * @param <T> the property class
4294         * @return the properties that were replaced (this list is immutable)
4295         */
4296        public <T extends VCardProperty> List<T> setProperty(Class<T> clazz, T property) {
4297                List<VCardProperty> replaced = properties.replace(clazz, property);
4298                return castList(replaced, clazz);
4299        }
4300
4301        /**
4302         * Removes a property instance from the vCard.
4303         * @param property the property to remove
4304         * @return true if it was removed, false if it wasn't found
4305         */
4306        public boolean removeProperty(VCardProperty property) {
4307                return properties.remove(property.getClass(), property);
4308        }
4309
4310        /**
4311         * Removes all properties of a given class.
4312         * @param clazz the class of the properties to remove (e.g. "Note.class")
4313         * @param <T> the property class
4314         * @return the properties that were removed (this list is immutable)
4315         */
4316        public <T extends VCardProperty> List<T> removeProperties(Class<T> clazz) {
4317                List<VCardProperty> removed = properties.removeAll(clazz);
4318                return castList(removed, clazz);
4319        }
4320
4321        /**
4322         * Gets the first extended property with a given name.
4323         * @param name the property name (e.g. "X-ALT-DESC")
4324         * @return the property or null if none were found
4325         */
4326        public RawProperty getExtendedProperty(String name) {
4327                for (RawProperty raw : getExtendedProperties()) {
4328                        if (raw.getPropertyName().equalsIgnoreCase(name)) {
4329                                return raw;
4330                        }
4331                }
4332                return null;
4333        }
4334
4335        /**
4336         * Gets all extended properties with a given name.
4337         * @param name the property name (e.g. "X-ALT-DESC")
4338         * @return the properties (this list is immutable)
4339         */
4340        public List<RawProperty> getExtendedProperties(String name) {
4341                List<RawProperty> properties = new ArrayList<>();
4342
4343                for (RawProperty raw : getExtendedProperties()) {
4344                        if (raw.getPropertyName().equalsIgnoreCase(name)) {
4345                                properties.add(raw);
4346                        }
4347                }
4348
4349                return Collections.unmodifiableList(properties);
4350        }
4351
4352        /**
4353         * Gets all extended properties.
4354         * @return the properties (any changes made this list will affect the
4355         * {@link VCard} object and vice versa)
4356         */
4357        public List<RawProperty> getExtendedProperties() {
4358                return getProperties(RawProperty.class);
4359        }
4360
4361        /**
4362         * Adds an extended property.
4363         * @param name the property name (e.g. "X-ALT-DESC")
4364         * @param value the property value
4365         * @return the property object that was created
4366         */
4367        public RawProperty addExtendedProperty(String name, String value) {
4368                RawProperty raw = new RawProperty(name, value);
4369                addProperty(raw);
4370                return raw;
4371        }
4372
4373        /**
4374         * Adds an extended property.
4375         * @param name the property name (e.g. "X-ALT-DESC")
4376         * @param value the property value
4377         * @param dataType the property value's data type
4378         * @return the property object that was created
4379         */
4380        public RawProperty addExtendedProperty(String name, String value, VCardDataType dataType) {
4381                RawProperty raw = new RawProperty(name, value, dataType);
4382                addProperty(raw);
4383                return raw;
4384        }
4385
4386        /**
4387         * Replaces all existing extended properties with the given name with a
4388         * single property instance.
4389         * @param name the property name (e.g. "X-ALT-DESC")
4390         * @param value the property value
4391         * @return the property object that was created
4392         */
4393        public RawProperty setExtendedProperty(String name, String value) {
4394                removeExtendedProperty(name);
4395                return addExtendedProperty(name, value);
4396        }
4397
4398        /**
4399         * Replaces all existing extended properties with the given name with a
4400         * single property instance.
4401         * @param name the property name (e.g. "X-ALT-DESC")
4402         * @param value the property value
4403         * @param dataType the property value's data type
4404         * @return the property object that was created
4405         */
4406        public RawProperty setExtendedProperty(String name, String value, VCardDataType dataType) {
4407                removeExtendedProperty(name);
4408                return addExtendedProperty(name, value, dataType);
4409        }
4410
4411        /**
4412         * Removes all extended properties that have the given name.
4413         * @param name the component name (e.g. "X-ALT-DESC")
4414         * @return the properties that were removed (this list is immutable)
4415         */
4416        public List<RawProperty> removeExtendedProperty(String name) {
4417                List<RawProperty> all = getExtendedProperties();
4418                List<RawProperty> toRemove = new ArrayList<>();
4419                for (RawProperty property : all) {
4420                        if (property.getPropertyName().equalsIgnoreCase(name)) {
4421                                toRemove.add(property);
4422                        }
4423                }
4424
4425                all.removeAll(toRemove);
4426                return Collections.unmodifiableList(toRemove);
4427        }
4428
4429        /**
4430         * Adds a property in the form of a collection of alternative
4431         * representations. This method will generate a unique ALTID parameter value
4432         * and assign it to each of the property instances (see:
4433         * {@link VCardParameters#getAltId description of ALTID}).
4434         * @param propertyClass the property class
4435         * @param altRepresentations the alternative representations of the property
4436         * to add
4437         * @param <T> the property class
4438         */
4439        public <T extends VCardProperty & HasAltId> void addPropertyAlt(Class<T> propertyClass, T... altRepresentations) {
4440                addPropertyAlt(propertyClass, Arrays.asList(altRepresentations));
4441        }
4442
4443        /**
4444         * Adds a property in the form of a collection of alternative
4445         * representations. This method will generate a unique ALTID parameter value
4446         * and assign it to each of the property instances (see:
4447         * {@link VCardParameters#getAltId description of ALTID}).
4448         * @param propertyClass the property class
4449         * @param altRepresentations the alternative representations of the property
4450         * to add
4451         * @param <T> the property class
4452         */
4453        public <T extends VCardProperty & HasAltId> void addPropertyAlt(Class<T> propertyClass, Collection<T> altRepresentations) {
4454                String altId = generateAltId(getProperties(propertyClass));
4455                for (T property : altRepresentations) {
4456                        property.setAltId(altId);
4457                        addProperty(property);
4458                }
4459        }
4460
4461        /**
4462         * Sets a property in the form of a collection of alternative
4463         * representations. This method will generate a unique ALTID parameter value
4464         * and assign it to each of the property instances (see:
4465         * {@link VCardParameters#getAltId description of ALTID}).
4466         * @param propertyClass the property class
4467         * @param altRepresentations the alternative representations of the property
4468         * to add
4469         * @param <T> the property class
4470         * @return the properties that were replaced (this list is immutable)
4471         */
4472        public <T extends VCardProperty & HasAltId> List<T> setPropertyAlt(Class<T> propertyClass, T... altRepresentations) {
4473                return setPropertyAlt(propertyClass, Arrays.asList(altRepresentations));
4474        }
4475
4476        /**
4477         * Sets a property in the form of a collection of alternative
4478         * representations. This method will generate a unique ALTID parameter value
4479         * and assign it to each of the property instances (see:
4480         * {@link VCardParameters#getAltId description of ALTID}).
4481         * @param propertyClass the property class
4482         * @param altRepresentations the alternative representations of the property
4483         * to add
4484         * @param <T> the property class
4485         * @return the properties that were replaced (this list is immutable)
4486         */
4487        public <T extends VCardProperty & HasAltId> List<T> setPropertyAlt(Class<T> propertyClass, Collection<T> altRepresentations) {
4488                List<T> removed = removeProperties(propertyClass);
4489                addPropertyAlt(propertyClass, altRepresentations);
4490                return removed;
4491        }
4492
4493        /**
4494         * Casts all objects in the given list to the given class, adding the casted
4495         * objects to a new list.
4496         * @param list the list to cast
4497         * @param castTo the class to cast to
4498         * @param <T> the class to cast to
4499         * @return the new list (this list is immutable)
4500         */
4501        private static <T> List<T> castList(List<?> list, Class<T> castTo) {
4502                List<T> casted = new ArrayList<>(list.size());
4503                for (Object object : list) {
4504                        casted.add(castTo.cast(object));
4505                }
4506                return Collections.unmodifiableList(casted);
4507        }
4508
4509        /**
4510         * Checks this vCard for data consistency problems or deviations from the
4511         * spec. These problems will not prevent the vCard from being written to a
4512         * data stream, but may prevent it from being parsed correctly by the
4513         * consuming application. These problems can largely be avoided by reading
4514         * the Javadocs of the property classes, or by being familiar with the vCard
4515         * standard.
4516         * @param version the version to check the vCard against (use
4517         * {@link VCardVersion#V4_0} for xCard and jCard)
4518         * @return the validation warnings
4519         */
4520        public ValidationWarnings validate(VCardVersion version) {
4521                ValidationWarnings warnings = new ValidationWarnings();
4522
4523                //validate overall vCard object
4524                if (getStructuredName() == null && (version == VCardVersion.V2_1 || version == VCardVersion.V3_0)) {
4525                        warnings.add(null, new ValidationWarning(0));
4526                }
4527                if (getFormattedName() == null && (version == VCardVersion.V3_0 || version == VCardVersion.V4_0)) {
4528                        warnings.add(null, new ValidationWarning(1));
4529                }
4530
4531                //validate properties
4532                for (VCardProperty property : this) {
4533                        List<ValidationWarning> propWarnings = property.validate(version, this);
4534                        if (!propWarnings.isEmpty()) {
4535                                warnings.add(property, propWarnings);
4536                        }
4537                }
4538
4539                return warnings;
4540        }
4541
4542        @Override
4543        public String toString() {
4544                StringBuilder sb = new StringBuilder();
4545                sb.append("version=").append(version);
4546                for (VCardProperty property : properties.values()) {
4547                        sb.append(StringUtils.NEWLINE).append(property);
4548                }
4549                return sb.toString();
4550        }
4551
4552        @Override
4553        public int hashCode() {
4554                final int prime = 31;
4555                int result = 1;
4556
4557                result = prime * result + ((version == null) ? 0 : version.hashCode());
4558
4559                int propertiesHash = 1;
4560                for (VCardProperty property : properties.values()) {
4561                        propertiesHash += property.hashCode();
4562                }
4563                result = prime * result + propertiesHash;
4564
4565                return result;
4566        }
4567
4568        @Override
4569        public boolean equals(Object obj) {
4570                if (this == obj) return true;
4571                if (obj == null) return false;
4572                if (getClass() != obj.getClass()) return false;
4573                VCard other = (VCard) obj;
4574                if (version != other.version) return false;
4575                if (properties.size() != other.properties.size()) return false;
4576
4577                for (Map.Entry<Class<? extends VCardProperty>, List<VCardProperty>> entry : properties) {
4578                        Class<? extends VCardProperty> key = entry.getKey();
4579                        List<VCardProperty> value = entry.getValue();
4580                        List<VCardProperty> otherValue = other.properties.get(key);
4581
4582                        if (value.size() != otherValue.size()) {
4583                                return false;
4584                        }
4585
4586                        List<VCardProperty> otherValueCopy = new ArrayList<>(otherValue);
4587                        for (VCardProperty property : value) {
4588                                if (!otherValueCopy.remove(property)) {
4589                                        return false;
4590                                }
4591                        }
4592                }
4593
4594                return true;
4595        }
4596
4597        /**
4598         * Generates a unique ALTID parameter value.
4599         * @param properties the collection of properties under which the ALTID must
4600         * be unique
4601         * @param <T> the property class
4602         * @return a unique ALTID
4603         */
4604        static <T extends HasAltId> String generateAltId(Collection<T> properties) {
4605                Set<String> altIds = new HashSet<>();
4606                for (T property : properties) {
4607                        String altId = property.getAltId();
4608                        if (altId != null) {
4609                                altIds.add(altId);
4610                        }
4611                }
4612
4613                int altId = 1;
4614                while (altIds.contains(Integer.toString(altId))) {
4615                        altId++;
4616                }
4617                return Integer.toString(altId);
4618        }
4619
4620        /**
4621         * <p>
4622         * A list that automatically casts {@link VCardProperty} instances stored in
4623         * this {@link VCard} to a given property class.
4624         * </p>
4625         * <p>
4626         * This list is backed by the {@link VCard} object. Any changes made to the
4627         * list will affect the {@link VCard} object and vice versa.
4628         * </p>
4629         * @param <T> the property class
4630         */
4631        private class VCardPropertyList<T extends VCardProperty> extends AbstractList<T> {
4632                protected final Class<T> propertyClass;
4633                protected final List<VCardProperty> properties;
4634
4635                /**
4636                 * @param propertyClass the property class
4637                 */
4638                public VCardPropertyList(Class<T> propertyClass) {
4639                        this.propertyClass = propertyClass;
4640                        properties = VCard.this.properties.get(propertyClass);
4641                }
4642
4643                @Override
4644                public void add(int index, T value) {
4645                        properties.add(index, value);
4646                }
4647
4648                @Override
4649                public T remove(int index) {
4650                        VCardProperty removed = properties.remove(index);
4651                        return cast(removed);
4652                }
4653
4654                @Override
4655                public T get(int index) {
4656                        VCardProperty property = properties.get(index);
4657                        return cast(property);
4658                }
4659
4660                @Override
4661                public T set(int index, T value) {
4662                        VCardProperty replaced = properties.set(index, value);
4663                        return cast(replaced);
4664                }
4665
4666                @Override
4667                public int size() {
4668                        return properties.size();
4669                }
4670
4671                private T cast(VCardProperty value) {
4672                        return propertyClass.cast(value);
4673                }
4674        }
4675}