Multimedia
The IMu API provides a number of special mechanisms to handle access to the multimedia stored in the EMu Database management system (DBMS). These mechanisms fall into three rough categories:
- Mechanisms to select Multimedia module records that are attached to another module. This is covered in the Multimedia Attachments section.
- Mechanisms to select multimedia files from a Multimedia module record. This is covered in the Multimedia Files and Filters sections.
- Mechanisms to apply modifications to multimedia files. This is covered in the Modifiers section.
It is important to note that a single record in the EMu DBMS can have multiple Multimedia module records associated with it. Each Multimedia module record can have multiple multimedia files associated with it. The separate mechanisms for handling multimedia access can be composed so that it is possible to, for example:
- Select a specific Multimedia module record from a group of attached Multimedia module records.
- Select a specific multimedia file from the selected Multimedia record.
- Apply a modification to the selected multimedia file.
Information about the multimedia attached to an EMu record from any module
(except the Multimedia module itself) can be retrieved using the
IMuModule
class Fetch
method by specifying one of the following
virtual columns.
The following virtual columns return information about a single multimedia attachment of the current record. The information is returned as a associative array:
- application
- audio
- image
- video
The following virtual columns return information about a set of multimedia attachments of the current record. The information is returned as an array. Each array member is an associative array containing the information for a single multimedia attachment from the set:
- applications
- audios
- images
- multimedia
- videos
All of these virtual columns return the irn, type and format of the Multimedia record attached to the current record. They also act as reference columns to the Multimedia module. This means that other columns from the Multimedia module (including virtual columns) can also be requested from the corresponding Multimedia record, for example:
- Include the title for all attached multimedia:
multimedia.MulTitle
- Include the title for all attached images:
images.MulTitle
- Include details about the master multimedia file for all attached images
(using the virtual Multimedia module column master):
images.master
- Include multiple columns for all attached images:
images.(master,MulTitle,MulDescription)
- Include and rename multiple columns for all attached images:
images.(master,title=MulTitle,description=MulDescription)
Example
This example shows the retrieval of the base information and the title for all multimedia images attached to a parties record:
String[] columns =
{
"images.MulTitle"
};
ModuleFetchResult result = parties.Fetch("start", 0, 1, columns);
foreach (IMu.Map row in result.Rows)
{
foreach (IMu.Map image in row.GetMaps("images"))
{
int irn = image.GetInt("irn");
String type = image.GetString("type");
String format = image.GetString("format");
String title = image.GetString("MulTitle");
Console.WriteLine("irn {0}: {1} - {2}/{3}",
irn, title, type, format);
}
}
This will produce output similar to the following:
irn 100105: Signature of Luciano Pavarotti - image/jpeg
irn 100096: Luciano Pavarotti - image/gif
irn 100100: Luciano Pavarotti with Celine Dion - image/gif
irn 100101: Luciano Pavarotti with Natalie Cole - image/gif
irn 100102: Luciano Pavarotti with the Spice Girls - image/gif
Similarly, information about the multimedia files associated with a Multimedia
module record can be retrieved using the IMuModule
class Fetch
method
by specifying one of the following virtual columns.
The following virtual columns return information about a single multimedia file from the current Multimedia record. The information is returned as a associative array.
- master
- resource
- thumbnail
The following virtual columns return information about a set of multimedia files of the current Multimedia record. The information is returned as an array. Each array member is a associative array containing the information for a single multimedia file from the set:
- resolutions
- resources
- supplementary
The master, thumbnail, resolutions and supplementary virtual columns all return the same type of information. That information differs for image and non-image multimedia as follows:
For non-image multimedia they return:
Returns |
Details |
---|---|
fileSize |
The size of the file in bytes. |
identifier |
The name of the multimedia file. |
index |
An integer that specifies the multimedia files position in the list of the master, thumbnail, resolutions and supplementary (in that order) multimedia files numbered from 0. |
kind |
The kind (master, thumbnail, resolution, or supplementary) of the multimedia. |
md5Checksum |
The MD5 checksum of the multimedia file. |
md5Sum |
The same as md5Checksum (included for backwards compatibility). |
mimeFormat |
The media format. |
mimeType |
The media type. |
size |
The same as fileSize (included for backwards compatibility). |
For image multimedia they return all of the values specified for non-image multimedia and also include:
Returns |
Details |
---|---|
bitsPerPixel |
The colour depth of the image. |
colourSpace |
The colour space of the image. |
compression |
The type of compression used on the image. |
height |
The height of the image in pixels. |
imageType |
The type classification of the image. For example:
Some more information can be found here. |
numberColours |
The number of colours in the image. |
numberPages |
The number of images within the main image - a feature that is supported only in certain file types, e.g. TIFF. |
planes |
The number of planes in an image. |
quality |
An integer value from 1 to 100 that indicates the quality of the image. A lower value indicates a lower image quality and higher compression and a higher value indicates a higher image quality but a lower compression. Only applicable to JPEG and MPEG image formats. |
resolution |
The resolution of the image in PPI (Pixels per inch). |
width |
The width of the image in pixels. |
The resource and resources virtual columns both return the same type of information as follows:
Returns |
Details |
---|---|
identifier |
The name of the multimedia file. |
mimeType |
The media type. |
mimeFormat |
The media format. |
size |
The size of the file in bytes. |
|
|
height |
The height of the image in pixels. |
width |
The width of the image in pixels. |
This example shows the retrieval of the multimedia title and resource information about all multimedia files for all multimedia images attached to a parties record:
String[] columns =
{
"images.(MulTitle, resources)"
};
ModuleFetchResult result = parties.Fetch("start", 0, 1, columns);
foreach (IMu.Map row in result.Rows)
{
foreach (IMu.Map image in row.GetMaps("images"))
{
int irn = image.GetInt("irn");
String type = image.GetString("type");
String format = image.GetString("format");
String title = image.GetString("MulTitle");
Console.WriteLine("irn {0}: {1} - {2}/{3}",
irn, title, type, format);
foreach (IMu.Map resource in image.GetMaps("resources"))
{
int height = resource.GetInt("height");
String identifier = resource.GetString("identifier");
String mimeFormat = resource.GetString("mimeFormat");
String mimeType = resource.GetString("mimeType");
int size = resource.GetInt("size");
int width = resource.GetInt("width");
Console.WriteLine(" {0}: {1}/{2} - {3}x{4} - {5} bytes",
identifier, mimeType, mimeFormat, height, width, size);
}
Console.WriteLine();
}
}
This will produce output similar to the following:
irn 100105: Signature of Luciano Pavarotti - image/jpeg
signature.jpg: image/jpeg - 85x300 - 6535 bytes
signature.thumb.jpg: image/jpeg - 25x90 - 1127 bytes
irn 100096: Luciano Pavarotti - image/gif
LucianoPavarotti.gif: image/gif - 400x273 - 19931 bytes
LucianoPavarotti.thumb.jpg: image/jpeg - 90x61 - 1354 bytes
LucianoPavarotti.300x300.jpg: image/jpeg - 300x205 - 41287 bytes
irn 100100: Luciano Pavarotti with Celine Dion - image/gif
PavarottiWithCelineDion.gif: image/gif - 400x381 - 66682 bytes
PavarottiWithCelineDion.thumb.jpg: image/jpeg - 90x85 - 2393 bytes
PavarottiWithCelineDion.300x300.jpg: image/jpeg - 300x286 - 76091 bytes
irn 100101: Luciano Pavarotti with Natalie Cole - image/gif
PavarottiWithNatalieCole.gif: image/gif - 251x400 - 44551 bytes
PavarottiWithNatalieCole.thumb.jpg: image/jpeg - 56x90 - 1768 bytes
PavarottiWithNatalieCole.300x300.jpg: image/jpeg - 188x300 - 49698 bytes
irn 100102: Luciano Pavarotti with the Spice Girls - image/gif
PavarottiWithSpiceGirls.gif: image/gif - 326x400 - 64703 bytes
PavarottiWithSpiceGirls.thumb.jpg: image/jpeg - 73x90 - 2294 bytes
PavarottiWithSpiceGirls.300x300.jpg: image/jpeg - 245x300 - 65370 bytes
The actual bytes of the multimedia file can be accessed using the file handle from the file value returned using the resource or resources virtual columns. We can use the file handle to copy the file from the IMu server:
String[] columns =
{
"image.resource{resource:inclue}"
};
ModuleFetchResult result = parties.Fetch("start", 0, 1, columns);
foreach (IMu.Map row in result.Rows)
{
IMu.Map image = row.GetMap("image");
IMu.Map resource = image.GetMap("resource");
String name = resource.GetString("identifier");
FileStream temp = (FileStream) resource["file"];
FileStream copy = new FileStream(name, FileMode.OpenOrCreate,
FileAccess.Write);
byte[] buffer = new byte[4096]; // 4k buffer
int length = 0;
while ((length = temp.Read(buffer, 0, 4096)) > 0)
{
copy.Write(buffer, 0, length);
}
copy.Close();
temp.Close();
}
This copies the multimedia file from the IMu server to a local file with the
same name, in this case signature.jpg
:
While the Multimedia module virtual columns provide a reasonably fine-grained method for selecting specific multimedia files associated with a multimedia record, in some circumstances it is useful to have even more control over the selection of multimedia files, particularly when specifying the resolutions, resources or supplementary virtual columns.
Filters provide a mechanism to specify particular files associated with a multimedia record based on certain characteristics of the files. Filters consist of three parts; a name, a operator and a value. They are specified in round brackets after a virtual column:
column(nameoperatorvalue)
Multiple values can be specified by separating each filter with a comma:
column(nameoperatorvalue, nameoperatorvalue)
- name
The filter name specifies the characteristic of the multimedia file to filter on. Unless noted otherwise the meaning of the filter names is as specified in the Multimedia files section.
The following filter names can be used to filter any multimedia file:
fileSize
(orsize
)height
identifier
index
kind
mimeFormat
(orformat
)mimeType
(ortype
)width
The following filter names can be used to filter multimedia image files:
bitsPerPixel
colourSpace
compression
imageType
md5Checksum
(ormd5sum
)numberColours
numberPages
planes
quality
resolution
The following filter name can be used to filter supplementary multimedia files:
-
usage
The value of the supplementary attributes usage (SupUsage_tab) column.
-
operator
The operator specifies how the filter
value
should relate to the multimedia file characteristic specified by the filtername
.The available values are:
Value
Name
Details
==
Equals
Selects the multimedia files where the characteristic specified by the filter
name
is the same as the filtervalue
.!=
Not equals
Selects the multimedia files where the characteristic specified by the filter
name
is not the same as the filtervalue
.<
Less than
Selects the multimedia files where the characteristic specified by the filter
name
is less than the filtervalue
. Only applies to numeric values.>
Greater than
Selects the multimedia files where the characteristic specified by the filter
name
is greater than the filtervalue
. Only applies to numeric values.<=
Less than or equal to
Selects the multimedia files where the characteristic specified by the filter
name
is less that or equal to the filtervalue
. Only applies to numeric values.>=
Greater than or equal to
Selects the multimedia files where the characteristic specified by the filter name is greater that or equal to the filter value. Only applies to numeric values.
@
Closest to (also called best fit).
Selects the single multimedia file where the characteristic specified by the filter
name
is closest to the filtervalue
. Only applies to numeric values.^
Closest to but greater than
Selects the single multimedia file where the characteristic specified by the filter
name
is closest to but greater than the filtervalue
. Only applies to numeric values. - value
The value to filter by. Any value can be used but, obviously, only certain values make sense for each filter. For example, if the
fileSize
filter is being used then only a numericvalue
is useful. Similarly, if themimeType
filter is being used then only a textvalue
that corresponds to a valid MIME type is useful.
For example:
- Select multimedia resolutions with a width greater that 300 pixels:
resolutions(width > 300)
- Select the single multimedia resource with a width closest to 600:
resources(width @ 600)
- Select the thumbnail resource:
resources(kind == thumbnail)
- Specify multiple filters to select the single multimedia resource with a
width and height closest to 600:
resources(width @ 600, height @ 600)
This example shows the retrieval of the multimedia title and resource information about the single multimedia file with a width closest to 300 for all multimedia images attached to a parties record:
String[] columns =
{
"images.(MulTitle, resources(width @ 300))"
};
ModuleFetchResult result = parties.Fetch("start", 0, 1, columns);
foreach (IMu.Map row in result.Rows)
{
foreach (IMu.Map image in row.GetMaps("images"))
{
int irn = image.GetInt("irn");
String type = image.GetString("type");
String format = image.GetString("format");
String title = image.GetString("MulTitle");
Console.WriteLine("irn {0}: {1} - {2}/{3}",
irn, title, type, format);
foreach (IMu.Map resource in image.GetMaps("resources"))
{
long height = resource.GetInt("height");
String identifier = resource.GetString("identifier");
String mimeFormat = resource.GetString("mimeFormat");
String mimeType = resource.GetString("mimeType");
long size = resource.GetInt("size");
long width = resource.GetInt("width");
Console.WriteLine(" {0}: {1}/{2} - {3}x{4} - {5} bytes",
identifier, mimeType, mimeFormat, height, width, size);
}
Console.WriteLine();
}
}
Note: The only difference from the previous example is the inclusion of a filter on the resources Multimedia virtual column.
This will produce output similar to the following:
irn 100105: Signature of Luciano Pavarotti - image/jpeg
signature.jpg: image/jpeg - 85x300 - 6535 bytes
irn 100096: Luciano Pavarotti - image/gif
LucianoPavarotti.gif: image/gif - 400x273 - 19931 bytes
irn 100100: Luciano Pavarotti with Celine Dion - image/gif
PavarottiWithCelineDion.300x300.jpg: image/jpeg - 300x286 - 76091 bytes
irn 100101: Luciano Pavarotti with Natalie Cole - image/gif
PavarottiWithNatalieCole.300x300.jpg: image/jpeg - 188x300 - 49698 bytes
irn 100102: Luciano Pavarotti with the Spice Girls - image/gif
PavarottiWithSpiceGirls.300x300.jpg: image/jpeg - 245x300 - 65370 bytes
While the IMu API provides a number of ways to select particular multimedia files from a Multimedia record sometimes none of the available files fulfill the required characteristics. Sometimes it is necessary to modify an existing multimedia file to achieve the desired result.
Modifiers provide a mechanism to convert multimedia images returned by the IMu server in a number of ways. The modifications are performed on-the-fly and do not affect the multimedia stored in the Multimedia database; they only apply to the temporary copy of multimedia returned by the IMu API. Modifiers consist of two parts; a name and a value separated by a colon. They are specified in braces (curly brackets) after a resource or resources virtual column:
column{name:value}
Multiple values can be specified by seperating each filter with a comma:
column{name:value, name:value}
Modifiers can also be specified after a filter:
column(…){name:value}
The supported values for name
are:
Value |
Details |
---|---|
checksum
|
Include a checksum value with the resource (or resources) virtual column response. While this does not actually apply any modifications to a multimedia file it is useful when you require a checksum for multimedia that has had a modifier applied to it (cf. original multimedia). The allowed When the |
|
Specifies that the actual bytes (available via the file value of the resource or resources virtual column response) of the multimedia should be encoded. By default it is returned as raw binary data. The allowed
|
|
Specifies that the multimedia file should be converted to the specified format. If the multimedia is not already in the required format it is reformatted on-the-fly. The IMu server uses ImageMagick to process the image and the range of supported formats is very large. The complete list is available from: http://www.imagemagick.org/script/formats.php. Any of the supported formats can be used as the value part of this modifier. |
|
Specifies that a multimedia file handle should be returned. The allowed
|
|
Specifies that the multimedia image file should be converted to the specified height (in pixels). If the Multimedia record contains a resolution with this height, this resolution is returned instead (i.e. no modification is applied). Otherwise the closest matching larger resolution is resized to the requested height on-the-fly. The allowed |
|
Specifies that the multimedia image file should be converted to the specified width (in pixels). If the Multimedia record contains a resolution with this width, this resolution is returned instead (i.e. no modification is applied). Otherwise the closest matching larger resolution is resized to the requested width on-the-fly. The allowed |
|
Controls whether the image's aspect ratio should be maintained when both a
The allowed
|
Note: Modifiers currently only apply to multimedia images and can only be
specified after the Multimedia virtual resource or resources columns.
Only the resource or resources parts of the returned results are
affected by modifiers. By design, all other response parts include the
information for the original, unmodified multimedia.
For example:
- Specify a Base64 encoding modifier:
resource{encoding:base64}
- Include a CRC32 checksum in the response:
resource{checksum:crc32}
- Reformat the multimedia image to the gif format:
resource{format:gif}
- Resize the multimedia image to a height of 300 pixels:
resource{height:300}
- Resize the multimedia image to a width of 300 pixels:
resource{width:300}
- Resize the multimedia image to a height & width of 300 pixels and do not
maintain aspect ratio:
resource{height:300, width:300, aspectratio:no}
Modifying a multimedia file is computationally expensive, it should only be used when absolutely necessary. For example, it is better to use the filtering mechanism to select multimedia image files of the desired dimensions rather than modifying them to fit:
Good:
resource(height @ 300, width @ 300)
Not so good:
resource{height:300, width:300)
Obviously, this only works if you have image file resolutions that are close to the desired dimensions.
Modifying a multimedia image file that is closer to the desired dimensions is less computationally expensive than modifying a larger image, so selecting the appropriate image prior to modification is preferable:
Good:
resource(height ^ 299, width ^ 299){height:300, width:300}
Not so good:
resource{height:300, width:300}
This example shows the retrieval of the multimedia title and setting a format, width & height modifier to the resource information for the master multimedia image attached to a narratives record:
Terms terms = new Terms();
terms.Add("NarTitle", "Angus Young");
long hits = narratives.FindTerms(terms);
String[] columns =
{
"image.(MulTitle, resource{format:jpeg, height:600, width:600, checksum:md5})"
};
ModuleFetchResult result = narratives.Fetch("start", 0, 1, columns);
foreach (IMu.Map row in result.Rows)
{
IMu.Map image = row.GetMap("image");
int irn = image.GetInt("irn");
String type = image.GetString("type");
String format = image.GetString("format");
String title = image.GetString("MulTitle");
Console.WriteLine("irn {0}: {1} - {2}/{3}",
irn, title, type, format);IMu.Map resource = image.GetMap("resource");
long height = resource.GetInt("height");
String identifier = resource.GetString("identifier");
String mimeFormat = resource.GetString("mimeFormat");
String mimeType = resource.GetString("mimeType");
long size = resource.GetInt("size");
long width = resource.GetInt("width");
Console.WriteLine(" {0}: {1}/{2} - {3}x{4} - {5} bytes",
identifier, mimeType, mimeFormat, height, width, size);}
This will produce output similar to the following:
irn 165: Angus Young, AC/DC Jacket - image/tiff
00033320.jpeg: image/jpeg - 599x401 - 77396 bytes - d94a9f46bd6274bcd20154bc513cf61f
The bytes of the modified multimedia can be accessed in the usual way via the resource response file value.
Note
- Only the resource response part has been affected by the modifier. The image response part still reports the format as tiff. This is by design.
- Because the aspect ratio has been maintained the image does not have the exact height and width specified.