-
Notifications
You must be signed in to change notification settings - Fork 12
/
Copy pathoverview-summary.html
684 lines (589 loc) · 30.5 KB
/
overview-summary.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<!-- NewPage -->
<html lang="en">
<head>
<!-- Generated by javadoc (1.8.0_45) on Fri Feb 05 16:09:17 GMT 2016 -->
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Overview (Media Authoring with Java API)</title>
<meta name="date" content="2016-02-05">
<link rel="stylesheet" type="text/css" href="stylesheet.css" title="Style">
<script type="text/javascript" src="script.js"></script>
</head>
<body>
<script type="text/javascript"><!--
try {
if (location.href.indexOf('is-external=true') == -1) {
parent.document.title="Overview (Media Authoring with Java API)";
}
}
catch(err) {
}
//-->
</script>
<noscript>
<div>JavaScript is disabled on your browser.</div>
</noscript>
<!-- ========= START OF TOP NAVBAR ======= -->
<div class="topNav"><a name="navbar.top">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.top" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.top.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li class="navBarCell1Rev">Overview</li>
<li>Package</li>
<li>Class</li>
<li><a href="overview-tree.html">Tree</a></li>
<li><a href="deprecated-list.html">Deprecated</a></li>
<li><a href="index-files/index-1.html">Index</a></li>
</ul>
<div class="aboutLanguage">Media Authoring with Java API (MAJ)</div>
</div>
<div class="subNav">
<ul class="navList">
<li>Prev</li>
<li>Next</li>
</ul>
<ul class="navList">
<li><a href="index.html?overview-summary.html" target="_top">Frames</a></li>
<li><a href="overview-summary.html" target="_top">No Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_top">
<li><a href="allclasses-noframe.html">All Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_top");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<a name="skip.navbar.top">
<!-- -->
</a></div>
<!-- ========= END OF TOP NAVBAR ========= -->
<div class="header">
<h1 class="title">MAJ API Overview</h1>
</div>
<div class="header">
<div class="subTitle">
<div class="block">This documentation describes the <em>Media Authoring with Java API</em>
(MAJ API), some generic <em>media industry</em> and an implementation of the classes of the Advanced Authoring Format
specification in Java.</div>
</div>
<p>See: <a href="#overview.description">Description</a></p>
</div>
<div class="contentContainer">
<table class="overviewSummary" border="0" cellpadding="3" cellspacing="0" summary="Packages table, listing packages, and an explanation">
<caption><span>Packages</span><span class="tabEnd"> </span></caption>
<tr>
<th class="colFirst" scope="col">Package</th>
<th class="colLast" scope="col">Description</th>
</tr>
<tbody>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/constant/package-summary.html">tv.amwa.maj.constant</a></td>
<td class="colLast">
<div class="block">Defines constant values used throughout the MAJ API and defined by external specifications.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/enumeration/package-summary.html">tv.amwa.maj.enumeration</a></td>
<td class="colLast">
<div class="block">Defines <a href="http://docs.oracle.com/javase/8/docs/api/java/lang/Enum.html?is-external=true" title="class or interface in java.lang">Java enumerations</a> representing the enumerations specified in the AAF object
specification and other enumerations used across the MAJ API.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/example/package-summary.html">tv.amwa.maj.example</a></td>
<td class="colLast">
<div class="block">Example code demonstrating the use of the MAJ API.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/exception/package-summary.html">tv.amwa.maj.exception</a></td>
<td class="colLast">
<div class="block">Specific exceptions thrown due to exceptional behaviour during the execution of method calls
from the MAJ API.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/avid/package-summary.html">tv.amwa.maj.extensions.avid</a></td>
<td class="colLast"> </td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/avid/impl/package-summary.html">tv.amwa.maj.extensions.avid.impl</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/example/package-summary.html">tv.amwa.maj.extensions.example</a></td>
<td class="colLast">
<div class="block">Example code demonstrating an extension built with the
<a href="tv/amwa/maj/util/AutoGeneration.html" title="class in tv.amwa.maj.util">auto generator</a>.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/example/impl/package-summary.html">tv.amwa.maj.extensions.example.impl</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/quantel/package-summary.html">tv.amwa.maj.extensions.quantel</a></td>
<td class="colLast"> </td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/quantel/impl/package-summary.html">tv.amwa.maj.extensions.quantel.impl</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/st436/package-summary.html">tv.amwa.maj.extensions.st436</a></td>
<td class="colLast"> </td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/extensions/st436/impl/package-summary.html">tv.amwa.maj.extensions.st436.impl</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/industry/package-summary.html">tv.amwa.maj.industry</a></td>
<td class="colLast">
<div class="block">Industry for manufacturing, storing and making instances of classes and meta-classes,
referenced by names and registered identifiers.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/integer/package-summary.html">tv.amwa.maj.integer</a></td>
<td class="colLast">
<div class="block">Provides annotations to label that a value of a Java primitive type in the current
context should be interpreted as a particular AAF integer data type.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/io/aaf/package-summary.html">tv.amwa.maj.io.aaf</a></td>
<td class="colLast"> </td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/io/file/package-summary.html">tv.amwa.maj.io.file</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/io/mxf/package-summary.html">tv.amwa.maj.io.mxf</a></td>
<td class="colLast">
<div class="block">Support for the serialization of AAF data to and from KLV format files and streams according
to the SMPTE MXF standards.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/io/mxf/impl/package-summary.html">tv.amwa.maj.io.mxf.impl</a></td>
<td class="colLast"> </td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/io/xml/package-summary.html">tv.amwa.maj.io.xml</a></td>
<td class="colLast">
<div class="block">Support for the input and output of <a href="tv/amwa/maj/industry/MetadataObject.html" title="interface in tv.amwa.maj.industry">metadata objects</a> as XML fragments and
documents.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/meta/package-summary.html">tv.amwa.maj.meta</a></td>
<td class="colLast">
<div class="block">Specifications of all the meta-classes of AAF that provides meta-information about classes, properties
and data types.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/meta/impl/package-summary.html">tv.amwa.maj.meta.impl</a></td>
<td class="colLast">
<div class="block">A meta engine providing loosely-coupled class, property and type management services.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/misctype/package-summary.html">tv.amwa.maj.misctype</a></td>
<td class="colLast">
<div class="block">Provides annotations that describe the mapping of miscellaneous
AAF data types to Java data types.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/model/package-summary.html">tv.amwa.maj.model</a></td>
<td class="colLast">
<div class="block">Specifications of all the interchangeable classes of AAF as Java interfaces.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/model/impl/package-summary.html">tv.amwa.maj.model.impl</a></td>
<td class="colLast">
<div class="block">Implementation of the AAF interchange object classes.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/record/package-summary.html">tv.amwa.maj.record</a></td>
<td class="colLast">
<div class="block">Specifications of representations of structured values,
such as those of the <a href="tv/amwa/maj/meta/TypeDefinitionRecord.html" title="interface in tv.amwa.maj.meta">AAF record data types</a>.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/record/impl/package-summary.html">tv.amwa.maj.record.impl</a></td>
<td class="colLast">
<div class="block">Implementations of structured values that can be embedded as properties of
entity beans.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/union/package-summary.html">tv.amwa.maj.union</a></td>
<td class="colLast">
<div class="block">Provides interfaces to a union type representing values which may contain one of many different sub-types.</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="tv/amwa/maj/union/impl/package-summary.html">tv.amwa.maj.union.impl</a></td>
<td class="colLast">
<div class="block">Implementations of classes used to package up collections of values as an argument to
a method of the MAJ API.</div>
</td>
</tr>
<tr class="altColor">
<td class="colFirst"><a href="tv/amwa/maj/util/package-summary.html">tv.amwa.maj.util</a></td>
<td class="colLast">
<div class="block">Static utility methods and generators used internally by the MAJ API that may also be useful to
applications using the API.</div>
</td>
</tr>
</tbody>
</table>
</div>
<div class="contentContainer"><a name="overview.description">
<!-- -->
</a>
<div class="block"><p>This documentation describes the <em>Media Authoring with Java API</em>
(MAJ API), some generic <em>media industry</em> and an implementation of the classes of the Advanced Authoring Format
specification in Java. The media industry is a general purpose library code for making and manipulating structures
defined according to <a href="http://www.smpte-ra.org">SMPTE registers</a>. The AAF classes are implemented
as plain old Java objects (POJOs) and that can be mapped to EJB3-style persistent entities.</p>
<p>This API provides the basis for applications that capture. edit, manage and distribute media
according to professional standards. The API provides support for AAF, MXF and Reg-XML file formats.
It provides extensions mechanism to allow implementors to extend the core classes to meet new
standards or represent private data. This API is being developed as a project of the
<a href="http://www.amwa.tv">Advanced Media Workflow Association</a> and is licensed
under the Apache 2.0 License. Note, however, that support for manipulating essence
with MAJ is currently very limited.</p>
<p>This is a developer's release 1.1.4, a number chosen to indicate the level of object model
support similar to the <a href="http://sourceforge.net/projects/aaf/">AAF SDK reference implementation</a>.
The documentation of all the packages is rich and complete, so worthwhile exploring for a technical person. In
particular, <a href="tv/amwa/maj/industry/MediaEngine.html" title="class in tv.amwa.maj.industry">media engine</a>,
<a href="tv/amwa/maj/industry/Forge.html" title="class in tv.amwa.maj.industry">forge</a>, and <a href="tv/amwa/maj/industry/Warehouse.html" title="class in tv.amwa.maj.industry">warehouse</a>
are at the heart of the API's capabilities, so it is a good place to start exploring.</p>
<p>This page provides some getting started topics:</p>
<ul>
<li><a href="#scratch">Writing code from scratch</a>;</li>
<li><a href="#aaf-klc">Reading and writing MXF files (AAF-KLV)</a>;</li>
<li><a href="#aaf-ss">Reading and writing AAF files (AAF-SS)</a>;</li>
<li><a href="#aaf-xml">Reading and writing Reg-XML files (AAF-XML)</a>;</li>
<li><a href="#extensions">Working with extensions, including auto-generating your own extensions</a>;</li>
<li><a href="#advanced">Advanced features of the API, including database persistence</a>;</li>
<li><a href="#resources">Resources to help you</a>.</li>
</ul>
<h2 id="scratch">Writing code from scratch</h2>
<p>An application can be written using the AAF data model from scratch without the need to read
or write files. One difference between MAJ and the AAF SDK is that you can write code that uses
classes of the AAF model without the need to contain them within a virtual file at runtime. For more
details, see the documentation of the <a href="tv/amwa/maj/industry/package-summary.html">industry
package</a>.</p>
<p>The starting point is to initialize the local Java virtual machine so that it supports
processing the AAF data model with <a href="tv/amwa/maj/industry/MediaEngine.html#initializeAAF--"><code>MediaEngine.initializeAAF()</code></a>.
You can then start creating objects of the AAF data model, including
<a href="tv/amwa/maj/model/Package.html" title="interface in tv.amwa.maj.model">packages</a>, <a href="tv/amwa/maj/model/Track.html" title="interface in tv.amwa.maj.model">tracks</a>,
<a href="tv/amwa/maj/model/Sequence.html" title="interface in tv.amwa.maj.model">sequences</a> and <a href="tv/amwa/maj/model/SourceClip.html" title="interface in tv.amwa.maj.model">source clips</a>,
using the <em>make...</em> methods of the @linkplain tv.amwa.maj.industry.Forge forge}, for example
<a href="tv/amwa/maj/industry/Forge.html#make-java.lang.Class-java.lang.Object...-"><code>make(Class, Object...)</code></a>.</p>
<p>Every class in MAJ provides a registered XML representation as its <code>toString()</code>
output, which in turn is created by
<a href="tv/amwa/maj/industry/MediaEngine.html#toString-tv.amwa.maj.industry.MetadataObject-"><code>MediaEngine.toString(MetadataObject)</code></a>.
This make debugging fairly easy as you can query a value in the debugger and see a human-readable XML format.</p>
<p>To help you get started, here is a <a href="tv/amwa/maj/example/AMWADemoClass.html" title="class in tv.amwa.maj.example">code example</a>:</p>
<pre>
package tv.amwa.maj.example;
import tv.amwa.maj.industry.Forge;
import tv.amwa.maj.industry.MediaEngine;
import tv.amwa.maj.model.*;
public class AMWADemoClass
implements tv.amwa.maj.constant.CommonConstants {
public static void main(String[] args) throws Exception {
MediaEngine.initializeAAF(); // Required to initialize AAF specified classes
MaterialPackage amwaPackage = Forge.makeByName(
AAF_XML_NAMESPACE, "MaterialPackage",
"PackageID", Forge.randomUMID(), // Randomly generated
"Name", "AMWADemoPackage",
"PackageLastModified", Forge.now(),
"CreationTime", Forge.now());
Sequence amwaVideoSequence = Forge.makeByName(
AAF_XML_NAMESPACE, "Sequence",
"ComponentDataDefinition", "Picture");
amwaVideoSequence.appendComponentObject(
Forge.make(
SourceClip.class,
"ComponentDataDefinition", "Picture",
"ComponentLength", 60l,
"SourcePackageID", "urn:smpte:umid:060c2b34.02051101.01001000.13000000.11ee08d4.040311d4.8e3d0090.27dfca7c",
"SourceTrackID", 1,
"StartPosition", 10l));
TimelineTrack amwaVideoTrack = Forge.make(
TimelineTrack.class,
"TrackID", 1,
"TrackSegment", amwaVideoSequence,
"EditRate", "25/1",
"Origin", 0l);
amwaVideoTrack.setTrackName("AMWA VIDEO TRACK");
amwaPackage.appendPackageTrack(amwaVideoTrack);
amwaPackage.appendPackageUserComment("company", "portability 4 media");
System.out.println(amwaPackage.toString());
}
}
</pre>
<p>For a more complex example, see the source for the <a href="tv/amwa/maj/example/CompositionExample.html" title="class in tv.amwa.maj.example">composition
example</a> that is part of the AMWA training course.</p>
<h2 id="aaf-klv">MXF files - AAF-KLV</h2>
<p>MXF files, also known as AAF-KLV files, consist of sequence of partitions. Partitions contain
a partition header and may contain metadata, index tables and/or essence data. Support for reading
and writing MXF files is provided in package
<code><a href="tv/amwa/maj/io/mxf/package-summary.html">tv.amwa.maj.io.mxf</a></code>.</p>
<h3>Reading MXF partitions</h3>
<p>MXF files contain one or more partitions. The first step in reading an MXF file is to build an
in memory cache of the structure of those partitions. To do this:</p>
<pre>
import tv.amwa.maj.industry.MediaEngine;
import tv.amwa.maj.io.mxf.MXFFactory;
import tv.amwa.maj.io.mxf.MXFFile;
...
MXFFile mxfFile = MXFFactory.readPartitions("filename.mxf");
</pre>
<p>All MXF files contain a header partition. Most also contain a footer partition. To access these:</p>
<pre>
import tv.amwa.maj.io.mxf.HeaderPartition;
import tv.amwa.maj.io.mxf.FooterPartition;
...
HeaderPartition header = mxfFile.getHeaderPartition();
FooterPartition footer = mxfFile.getFooterPartition();
</pre>
<h3>Reading header metadata</h3>
<p>Partitions can contain header metadata and this is split into a primer pack and a preface.
The metadata can be read into memory from file using the readHeaderMetadata() method.</p>
<p>If a footer partition is present in an MXF file and it contains header metadata, this version
is often the most trusted source for metadata about the file as it was written once the rest of the
file is complete. If the footer partition is not present or does not contain header metadata, read
the header partition's header metadata.</p>
<pre>
import tv.amwa.maj.model.Preface;
import tv.amwa.maj.io.mxf.HeaderMetadata;
...
HeaderMetadata headerMD = null;
if ((footer != null) && (footer.hasHeaderMetadata())
headerMD = footer.readHeaderMetadata();
else
headerMD = header.readHeaderMetadata();
Preface preface = headerMD.getPreface();
</pre>
<p>Methods from the preface interface can be used to interrogate what is in the MXF file, or you
can call <code>toString()</code> on the preface to get an XML representation.</p>
<h3>Writing header metadata</h3>
<p>This code is still in development, but it will take the form of an application altering an
existing preface, setting it to replace that within existing header metadata and calling a write method.
Well structured MXF should have padding at the end of the existing metadata, allowing the existing
metadata to be overwritten and extended. Writing will fail if insufficient padding space is available.</p>
<h3>Reading the index table</h3>
<p>An index table maps edit unit indexes to stream offsets in essence containers. This enables the data
representing a specific frame of video or audio sample to be located in the file, for example to generate
a still frame or carry out a partial restore. Any <em>long GOP</em> structure used to store the essence can also be
interrogated to work out a safe point to break a file, e.g. don't forget the previous I-frame!</p>
<p>Any partition may have an index table. To read the index table and find the stream offset to the 10th
frame 2nd element, measured in bytes from the beginning of its essence container, use ...</p>
<pre>
import tv.amwa.maj.io.mxf.IndexTable;
...
IndexTable index = footer.readIndexTable();
long tenthFrameOffset = index.streamOffset(10, 2);
</pre>
<p>Note that in interleaved streams, the element number determines whether it is an edit unit worth of
video, audio or data track being referred to. You need to know your stream layout to insert the correct
element number.</p>
<h2 id="aaf-ss">AAF files - AAF-SS</h2>
<p>AAF files, also known as AAF-SS or AAF structured storage files, store AAF structured data in a Microsoft
structured storage container. To read and write these files, MAJ uses the
<a href="http://poi.apache.org/download.html#POI-3.7">Apache POI library version 3.7</a>.</p>
<p>Support for reading
and writing AAF files is provided in package
<code><a href="tv/amwa/maj/io/aaf/package-summary.html">tv.amwa.maj.io.aaf</a></code>. MAJ provides a
helper class <a href="tv/amwa/maj/io/aaf/AAFFactory.html" title="class in tv.amwa.maj.io.aaf"><code>AAFFactory</code></a> as a starting point for reading and writing
AAF files.</p>
<h3>Reading a preface from an AAF file</h3>
<p>To read a preface from an AAF file, such as those generated by Avid, use the
<a href="tv/amwa/maj/io/aaf/AAFFactory.html" title="class in tv.amwa.maj.io.aaf"><code>AAFFactory#readPreface(java.lang.String) readPreface()</code></a> method
of the <a href="tv/amwa/maj/io/aaf/AAFFactory.html" title="class in tv.amwa.maj.io.aaf"><code>AAFFactory</code></a> class. For example:</p>
<pre>
import tv.amwa.maj.io.aaf.AAFFactory;
import tv.amwa.maj.iface.Preface;
import tv.amwa.maj.extensions.avid.AvidFactory;
...
AvidFactory.registerAvidExtensions();
Preface fromAAF = AAFFactory.readPreface("filename.aaf");
</pre>
<p>Some warning messages will be printed if extensions are unknown. These can be ignored unless the extension
data is important to your application.</p>
<h3>Writing a metadata-only AAF file</h3>
<p>MAJ supports writing metadata-only AAF files, files that do not contain any essence data.
AAF is commonly used as a metadata-only representation so this limitation means MAJ still works in many
use cases.</p>
<p>To write an existing preface to an AAF file, make sure the Avid extensions are registered (as for
reading) and use the
<a href="tv/amwa/maj/io/aaf/AAFFactory.html" title="class in tv.amwa.maj.io.aaf"><code>AAFFactory#writePreface(tv.amwa.maj.model.Preface, java.lang.String) writePreface()</code></a>
method of the <a href="tv/amwa/maj/io/aaf/AAFFactory.html" title="class in tv.amwa.maj.io.aaf"><code>AAFFactory</code></a> class.</p>
<pre>
import tv.amwa.maj.io.AAFFactory;
import tv.amwa.maj.iface.Preface;
...
Preface prefaceToWrite = ...;
AAFFactory.writePreface(prefaceToWrite, "filename.aaf");
</pre>
<p>MAJ will create a dynamic meta dictionary and, if the preface does not contain a valid dictionary
already, add in all the required definitions to make the file valid.</p>
<h2 id="aaf-xml">Reg-XML files - AAF-XML</h2>
<p>AAF XML files are also known as registered data XML files (SMPTE draft standard 2001). MAJ uses
this format for the return value of <code>toString()</code> methods almost everywhere, so it is easy to get to learn
this format. When you use a debugger and hover over a variable that is a MAJ type, you will see the same XML format.</p>
<p>Support for reading
and writing XML files is provided in package
<code><a href="tv/amwa/maj/io/xml/package-summary.html">tv.amwa.maj.io.xml</a></code>. MAJ provides a helper
class <a href="tv/amwa/maj/io/xml/XMLBuilder.html" title="class in tv.amwa.maj.io.xml"><code>XMLBuilder</code></a> as a starting point for reading and writing
AAF fragments to and from XML.</p>
<p>The methods the serialize objects to and from XML are useful for providing RESTful and web service
interfaces to an AAF-based repository. Reading and writing complete files allows XML to be used in
file-based workflows in place of the harder-to-analyse MXF and AAF formats.</p>
<h3>Serializing an object to XML fragments</h3>
<p>To convert a single object and any of its contained strong referenced objects to XML, use method
<a href="tv/amwa/maj/io/xml/XMLBuilder.html#toXML-tv.amwa.maj.industry.MetadataObject-"><code>toXML()</code></a> methods
of the <a href="tv/amwa/maj/io/xml/XMLBuilder.html" title="class in tv.amwa.maj.io.xml">XML builder</a>.</p>
<pre>
import tv.amwa.maj.io.xml.XMLBuilder;
import tv.amwa.maj.iface.MaterialPackage;
...
MaterialPackage material = ...;
String packageAsXML = XMLBuilder.toXML(material);
</pre>
<p>Any objects that implement <a href="tv/amwa/maj/io/xml/XMLSerializable.html" title="interface in tv.amwa.maj.io.xml"><code>XMLSerializable</code></a> or
<a href="tv/amwa/maj/industry/MetadataObject.html" title="interface in tv.amwa.maj.industry"><code>MetadataObject</code></a> can be serialized to XML fragments.</p>
<h3>Creating objects from an XML fragment</h3>
<p>To read the XML representation of an object in XML and create an instance in memory,
use either the <a href="tv/amwa/maj/io/xml/XMLBuilder.html#createFromXML-org.xml.sax.InputSource-"><code>createFromXML()</code></a> or
<a href="tv/amwa/maj/io/xml/XMLBuilder.html#createFromXMLString-java.lang.String-"><code>createFromXMLString()</code></a> methods of the
<a href="tv/amwa/maj/io/xml/XMLBuilder.html" title="class in tv.amwa.maj.io.xml">XML builder</a>.</p>
<pre>
import tv.amwa.maj.io.xml.XMLBuilder;
import tv.amwa.maj.iface.MaterialPackage;
...
MaterialPackage material =
(MaterialPackage) XMLBulder.createFromXMLString(packageAsXML);
</pre>
<h3>Reading complete Reg XML files with MAJ</h3>
<p>Complete XML files have a root <code><AAF></code> root element.
To read a preface from an XML file, register all the required data types and then
use the <a href="tv/amwa/maj/io/xml/XMLFactory.html#readPreface-java.lang.String-"><code>readPreface()</code></a>
static method of the <a href="tv/amwa/maj/io/xml/XMLFactory.html" title="class in tv.amwa.maj.io.xml">XML factory</a>.</p>
<pre>
import tv.amwa.maj.io.xml.XMLFactory;
import tv.amwa.maj.model.Preface;
....
Preface preface = XMLFactory.readPreface("input_file.xml");
</pre>
<p>Catch <a href="http://docs.oracle.com/javase/8/docs/api/java/io/IOException.html?is-external=true" title="class or interface in java.io">IO exceptions</a> to find out about any problems
parsing the XML.</p>
<p>Note that the automatic processing of extension metadata that is not registered
with MAJ is not supported in the current version of the MAJ API.</p>
<h3>Writing complete Reg XML files with MAJ</h3>
<p>Complete XML files have a root <code><AAF></code> root element.
To write a complete Reg XML file, use the
<a href="tv/amwa/maj/io/xml/XMLFactory.html#writePreface-tv.amwa.maj.model.Preface-java.lang.String-"><code>writePreface()</code></a> static method
of the <a href="tv/amwa/maj/io/xml/XMLFactory.html" title="class in tv.amwa.maj.io.xml">XML factory</a>.</p>
<pre>
import tv.amwa.maj.io.xml.XMLFactory;
....
XMLFactory.writePreface(preface, "output_file.xml");
</pre>
<p>The <a href="tv/amwa/maj/model/Preface.html" title="interface in tv.amwa.maj.model">preface</a> will be automatically updated with a correct
<a href="tv/amwa/maj/model/Dictionary.html" title="interface in tv.amwa.maj.model">dictionary</a> and any extensions classes will
be added to the output. Note that an application is expected to have added an appropriate
<a href="tv/amwa/maj/model/Identification.html" title="interface in tv.amwa.maj.model">identification</a> to the preface to identify the
current version of the file before calling this method.</p>
<h2 id="extensions">Extensions</h2>
<p>Writing extensions, for example to represent your companies descriptive metadata scheme, can be
achieved by writing Java interfaces and classes that represent those extensions. How to do this
is described in the <a href="tv/amwa/maj/industry/package-summary.html">industry package</a> and
in particular in the description of the <a href="tv/amwa/maj/industry/MediaClass.html" title="annotation in tv.amwa.maj.industry"><code>MediaClass</code></a> and
<a href="tv/amwa/maj/industry/MediaProperty.html" title="annotation in tv.amwa.maj.industry"><code>MediaProperty</code></a> annotations. In fact, if you have some
existing Java beans, annotating them to work as media classes with MAJ may be quite simple.</p>
<p>If writing all that Java is a scary thought, MAJ provides an
<a href="tv/amwa/maj/util/AutoGeneration.html" title="class in tv.amwa.maj.util">auto generator</a> that can take
an XML description of metadata extensions and create Java package sourcecode that can be
compiled and used with MAJ.</p>
<p>Some Avid Media Composer extensions are provided in package
<code><a href="tv/amwa/maj/extensions/avid/package-summary.html">tv.amwa.maj.extensions.avid</a></code>.</p>
<h2 id="advanced">Advanced features</h2>
<p>MAJ provides a means for <a href="tv/amwa/maj/industry/JPAGenerator.html" title="class in tv.amwa.maj.industry">generating Java Persistence API
compatible object-relational mappings</a> from its own internal representation of media classes.</p>
<p>MAJ can generate an XML representation of classes, properties and types that it knows about
using static method MediaEngine.generateMetaDictionary().</p> <!-- TODO add a link in this comment --></div>
</div>
<!-- ======= START OF BOTTOM NAVBAR ====== -->
<div class="bottomNav"><a name="navbar.bottom">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.bottom" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.bottom.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li class="navBarCell1Rev">Overview</li>
<li>Package</li>
<li>Class</li>
<li><a href="overview-tree.html">Tree</a></li>
<li><a href="deprecated-list.html">Deprecated</a></li>
<li><a href="index-files/index-1.html">Index</a></li>
</ul>
<div class="aboutLanguage">Media Authoring with Java API (MAJ)</div>
</div>
<div class="subNav">
<ul class="navList">
<li>Prev</li>
<li>Next</li>
</ul>
<ul class="navList">
<li><a href="index.html?overview-summary.html" target="_top">Frames</a></li>
<li><a href="overview-summary.html" target="_top">No Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_bottom">
<li><a href="allclasses-noframe.html">All Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_bottom");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<a name="skip.navbar.bottom">
<!-- -->
</a></div>
<!-- ======== END OF BOTTOM NAVBAR ======= -->
<p class="legalCopy"><small>(c)2007-2016 Richard Cartwright, all rights reserved. Licensed under Apache 2 license and subject to the AMWA IPR policy.</small></p>
</body>
</html>