BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

55
BlackBerry Java SDK Multimedia Version: 6.0 Development Guide

description

Development Guide Version: 6.0 Published: 2010-11-1 SWD-1249411-1101032433-001 6 Document revision history......................................................................................................................................................... 50 4 Find more information................................................................................................................................................................ 48

Transcript of BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Page 1: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

BlackBerry Java SDKMultimediaVersion: 6.0

Development Guide

Page 2: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Published: 2010-11-1SWD-1249411-1101032433-001

Page 3: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Contents1 Working with audio on a BlackBerry device............................................................................................................................ 2

Playing audio................................................................................................................................................................................... 2

Play audio in a BlackBerry device application.................................................................................................................... 2

Play audio in the BlackBerry Browser.................................................................................................................................. 5

Code sample: Playing a sequence of tones......................................................................................................................... 5

Recording audio.............................................................................................................................................................................. 6

Record audio in a BlackBerry device application................................................................................................................ 7

2 Working with video on a BlackBerry device............................................................................................................................. 17

Playing video................................................................................................................................................................................... 17

Play a video in a UI field in a BlackBerry device application............................................................................................ 17

Recording video............................................................................................................................................................................... 22

Record video to a file in a BlackBerry device application.................................................................................................. 22

RIMM streaming video file............................................................................................................................................................. 34

RIM proprietary video format (RIMM streaming file)......................................................................................................... 34

3 Working with pictures on a BlackBerry device........................................................................................................................ 41

Taking pictures................................................................................................................................................................................ 41

Take a picture in a BlackBerry device application.............................................................................................................. 41

4 Find more information................................................................................................................................................................ 48

5 Provide feedback......................................................................................................................................................................... 49

6 Document revision history......................................................................................................................................................... 50

7 Legal notice.................................................................................................................................................................................. 51

Page 4: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Working with audio on a BlackBerry device 1

Playing audioYou can play audio on a BlackBerry® device through the BlackBerry® Browser, or by generating a series of discrete tones, byusing the javax.microedition.media.Player class in your BlackBerry device application.

You can use the Player class to open a file that is stored on the BlackBerry device's internal media storage or media card, byspecifying a URL, or by specifying a location in your .cod file and using the format: cod:///path. Player provides access tothe associated Control classes (for example, VolumeControl) that control the playback and recording functionality (forexample, the volume).

You can use the browser to play an audio file by creating a new BrowserSession object and opening the audio file as youwould any URI.

You can also create a series of tones to play in your application. For example, you can use these tones as a notification soundsin your application. You can define the frequencies and length of the discrete tones and play them in a sequence.

Play audio in a BlackBerry device application1. Import the required classes and interfaces.

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import javax.microedition.media.*;import javax.microedition.media.control.*;import java.io.*

2. Create the application framework by extending the UiApplication class. In main(), create an instance of the newclass and invoke enterEventDispatcher() to enable the application to receive events. In the application constructor,invoke pushScreen() to display the custom screen for the application. The AudioPlaybackDemoScreen class,described in step 3, represents the custom screen.

public class AudioPlaybackDemo extends UiApplication{ public static void main(String[] args) { AudioPlaybackDemo app = new AudioPlaybackDemo(); app.enterEventDispatcher(); } public AudioPlaybackDemo() {

Development Guide Working with audio on a BlackBerry device

2

Page 5: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

pushScreen(new AudioPlaybackDemoScreen()); }}

3. Create the framework for the custom screen by extending the MainScreen class.

class AudioPlaybackDemoScreen extends MainScreen{ public AudioPlaybackDemoScreen() { }}

4. In the screen constructor, in a try/catch block, create an instance of the Player class by invokingManager.createPlayer(String), and passing in the location of the audio file to play.

try { Player p = javax.microedition.media.Manager.createPlayer("http://abc .com/sounds/abc.wav"); }catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

5. To control an aspect of playback, retrieve the appropriate Control object. Invoke the Player object's realize()method to access its associated Control object. The following code sample demonstrates how to retrieve theVolumeControl object and set the volume level of playback.

try { Player p = javax.microedition.media.Manager.createPlayer("http://abc .com/sounds/abc.wav"); p.realize(); VolumeControl volume = (VolumeControl) p.getControl("VolumeControl"); volume.setLevel(30);}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

Development Guide Playing audio

3

Page 6: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

6. Invoke Player.start() to start playback. Invoking Player.start() implicitly performs all the necessary statetransitions. In the following code sample, both realize() and prefetch() are invoked to demonstrate how to explicitlyinitialize the Player object before starting playback.

try { Player p = javax.microedition.media.Manager.createPlayer("http://abc .com/sounds/abc.wav"); p.realize(); VolumeControl volume = (VolumeControl)p.getControl("VolumeControl"); volume.setLevel(30); p.prefetch(); p.start();

}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

Code sample: Playing media in a BlackBerry device application

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import javax.microedition.media.*;import javax.microedition.media.control.*;import java.io.*

public class AudioPlaybackDemo extends UiApplication{ public static void main(String[] args) { AudioPlaybackDemo app = new AudioPlaybackDemo(); app.enterEventDispatcher(); } public AudioPlaybackDemo() { pushScreen(new AudioPlaybackDemoScreen()); }

private class AudioPlaybackDemoScreen extends MainScreen { public AudioPlaybackDemoScreen() {

Development Guide Playing audio

4

Page 7: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

try { Player p = javax.microedition.media.Manager.createPlayer("http://abc .com/sounds/abc.wav"); p.realize(); VolumeControl volume = (VolumeControl)p.getControl("VolumeControl"); volume.setLevel(30); p.prefetch(); p.start(); } catch(MediaException me) { Dialog.alert(me.toString()); } catch(IOException ioe) { Dialog.alert(ioe.toString()); } } }}

Play audio in the BlackBerry Browser1. Import the required classes.

import net.rim.blackberry.api.browser.Browser;import net.rim.blackberry.api.browser.BrowserSession;

2. Invoke Browser.getDefaultSession().

BrowserSession soundclip = Browser.getDefaultSession();

3. Invoke BrowserSession.displaypage().

soundclip.displayPage("file:///SDCard/BlackBerry/music/yourFile .mp3");

Code sample: Playing a sequence of tonesToneControl is used to play a user-defined sequence of notes at a specific duration and tempo on a BlackBerry® device.

// "Mary Had A Little Lamb" has "ABAC" structure// Use block to repeat "A" section// Tempos ranging from 20 to 508 beats per minute are divided by 4// to create a tempo modifier range of 5 to 127.byte tempo_mod = 30; // 120 bpm// Note duration ranges from 128 (1/2 note) to 0 (128th of a note)// with a default resolution of 64.

Development Guide Playing audio

5

Page 8: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

byte duration = 8; // Note length 8 (quaver) = 1/8th of a note duration// Notes are determined from ToneControl.C4 (Middle C),// which has a value of 60 and a frequency of 261.6 Hz.byte C4 = ToneControl.C4; // C note value = 60 (middle C)byte D4 = (byte)(C4 + 2); // D note value = 62 (a whole step)byte E4 = (byte)(C4 + 4); // E note value = 64 (a major third)byte G4 = (byte)(C4 + 7); // G note value = 67 (a fifth)byte rest = ToneControl.SILENCE; // rest byte[] mySequence = { ToneControl.VERSION, 1, // version 1 ToneControl.TEMPO, tempo_mod, // // Start define "A" section ToneControl.BLOCK_START, 0, // // Content of "A" section E4, duration, D4, duration, C4, duration, E4, duration, E4, duration, E4, duration, E4, duration, rest, duration, // // End define "A" section ToneControl.BLOCK_END, 0, // end of block number 0 // // Play "A" section ToneControl.PLAY_BLOCK, 0, // // Play "B" section D4, duration, D4, duration, D4, duration, rest, duration, E4, duration, G4, duration, G4, duration, rest, duration, // // Repeat "A" section ToneControl.PLAY_BLOCK, 0, // // Play "C" section D4, duration, D4, duration, E4, duration, D4, duration, C4, duration};try{ Player p = Manager.createPlayer(Manager.TONE_DEVICE_LOCATOR); p.realize(); ToneControl c = (ToneControl)p.getControl("ToneControl"); c.setSequence(mySequence); p.start(); } catch (IOException ioe) { } } catch (MediaException me) { }

Recording audioYou can record audio in a BlackBerry® device application by using the javax.microedition.media.Player class andthe associated RecordControl interface. The recording is saved to a file in built-in media storage, media card storage, or toa stream.

Development Guide Recording audio

6

Page 9: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Record audio in a BlackBerry device applicationBlackBerry® devices that operate on CDMA networks can record audio in the following formats: AMR 8 kHz mono, 16-bit PCM,GSM 6.10, and QCELP. The default audio recording format is AMR.

1. Import the required classes.

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import java.io.*;import java.lang.*;import javax.microedition.media.*;import javax.microedition.media.control.*;

2. Create the application framework by extending the UiApplication class. In main(), create an instance of the newclass and invoke enterEventDispatcher() to enable the application to receive events. In the application constructor,invoke pushScreen() to display the custom screen for the application. The AudioRecordingDemoScreen class,which is described in step 3, represents the custom screen.

public class AudioRecordingDemo extends UiApplication{ public static void main(String[] args) { AudioRecordingDemo app = new AudioRecordingDemo(); app.enterEventDispatcher(); } public AudioRecordingDemo() { pushScreen(new AudioRecordingDemoScreen()); }}

3. Create the framework for the custom screen by extending the MainScreen class. Declare an instance of theAudioRecorderThread class, which is described in step 5.

private class AudioRecordingDemoScreen extends MainScreen{ private AudioRecorderThread _recorderThread;

public AudioRecordingDemoScreen() { }}

4. In the AudioRecordingDemoScreen constructor, invoke setTitle() to specify the title for the screen. InvokeaddMenuItem() twice to add the menu items to start and stop the recording. which is described in step 5.

Development Guide Recording audio

7

Page 10: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public AudioRecordingDemoScreen(){ setTitle("Audio recording demo");

addMenuItem(new StartRecording()); addMenuItem(new StopRecording()); }

5. In the AudioRecordingDemoScreen class, define the menu items to start the recording and to stop recording byinvoking the start() and stop() methods of the AudioRecorderThread class respectively, which is described instep 6. in the following code sample, Player starts in its own thread to increase the responsiveness of the menu items.

private class StartRecording extends MenuItem { public StartRecording() { super("Start recording", 0, 100); }

public void run() { try { AudioRecorderThread newRecorderThread = new AudioRecorderThread(); newRecorderThread.start(); _recorderThread = newRecorderThread; } catch (Exception e) { Dialog.alert(e.toString()); } }} private class StopRecording extends MenuItem { public StopRecording() { super("Stop recording", 0, 100); }

public void run() { try { if (_recorderThread != null) { _recorderThread.stop(); } }

Development Guide Recording audio

8

Page 11: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

catch (Exception e) { Dialog.alert(e.toString()); } }}

6. Inside the AudioRecordingDemo screen class, define an inner class that extends Thread and implementsPlayerListener. In the inner class, create a variable of type Player and a variable of type RecordControl forrecording media.

Note: You are not required to record audio in a separate thread because recording operations are threaded by design.

private class AudioRecorderThread extends Thread implements javax.microedition.media.PlayerListener{ private Player _player; private RecordControl _recordControl;

AudioRecorderThread() { }

}

7. In the AudioRecorderThread class, implement the Thread interface's run() method. In run() create a try/catchblock and invoke Manager.createPlayer(String locator) to create a Player object to record audio, using asa parameter a value that specifies the encoding to use.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr"); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

8. Invoke Player.addPlayerListener() specifying this as a parameter because AudioRecorderThreadimplements PlayerListener.

Development Guide Recording audio

9

Page 12: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr");

_player.addPlayerListener(this); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

9. To record, invoke Player.realize() method to access the RecordControl object. Then, invokePlayer.getControl(), passing in the string, RecordControl, to retrieve the RecordControl object.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr");

_player.addPlayerListener(this);

_player.realize(); _recordControl = (RecordControl) _player.getControl( "RecordControl" ); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

10. Invoke RecordControl.setRecordLocation() to set the location on the device to save the audio recording.

public void run() { try {

Development Guide Recording audio

10

Page 13: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

_player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr");

_player.addPlayerListener(this);

_player.realize(); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

_recordControl.setRecordLocation("file:///store/home/user/AudioRecordingTest .amr" ); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

11. Invoke RecordControl.startRecord() to start recording the audio and start playing the media. InvokePlayer.start() to start Player.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr");

_player.addPlayerListener(this);

_player.realize(); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

_recordControl.setRecordLocation("file:///store/home/user/AudioRecordingTest .amr" );

_recordControl.startRecord(); _player.start(); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) {

Development Guide Recording audio

11

Page 14: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Dialog.alert(e.toString()); }}

12. In AudioRecorder, implement the Thread interface's stop() method. Check that Player is not null and invokePlayer.close() to release the Player object's resources. Set Player to null.

public void stop() { if (_player != null) { _player.close(); _player = null; }}

13. Check that RecordControl is not null and invoke RecordControl.stopRecord() to stop recording. In a try/catch block, invoke RecordControl.commit() to save the recording to a specified file. Set RecordControl to null.

public void stop() { if (_player != null) { _player.close(); _player = null; }

if (_recordControl != null) { _recordControl.stopRecord(); try { _recordControl.commit(); } catch (Exception e) { Dialog.alert(e.toString()); } _recordControl = null; }}

14. In AudioRecorderThread, implement the PlayerListener interface's playerUpdate() method which isinvoked whenever the Player object generates an event. In the following code sample, the application outputs informationabout the event.

public void playerUpdate(Player player, String event, Object eventData) {

Development Guide Recording audio

12

Page 15: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Dialog.alert("Player " + player.hashCode() + " got event " + event + ": " + eventData);}

Code sample: Recording audio in a BlackBerry device application

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import java.lang.*;import javax.microedition.media.*;import java.io.*;import javax.microedition.media.control.*;

public class AudioRecordingDemo extends UiApplication{ public static void main(String[] args) { AudioRecordingDemo app = new AudioRecordingDemo(); app.enterEventDispatcher(); } public AudioRecordingDemo() { pushScreen(new AudioRecordingDemoScreen()); }

private class AudioRecordingDemoScreen extends MainScreen { private AudioRecorderThread _recorderThread;

public AudioRecordingDemoScreen() { setTitle("Audio recording demo");

addMenuItem(new StartRecording()); addMenuItem(new StopRecording()); }

private class StartRecording extends MenuItem { public StartRecording() { super("Start recording", 0, 100); }

public void run() { try {

Development Guide Recording audio

13

Page 16: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

AudioRecorderThread newRecorderThread = new AudioRecorderThread(); newRecorderThread.start(); _recorderThread = newRecorderThread; } catch (Exception e) { Dialog.alert(e.toString()); } } } private class StopRecording extends MenuItem { public StopRecording() { super("Stop recording", 0, 100); }

public void run() { try { if (_recorderThread != null) { _recorderThread.stop(); } } catch (Exception e) { Dialog.alert(e.toString()); } } }

private class AudioRecorderThread extends Thread implements javax.microedition.media.PlayerListener { private Player _player; private RecordControl _recordControl;

AudioRecorderThread() { }

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://audio?encoding=audio/amr");

Development Guide Recording audio

14

Page 17: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

_player.addPlayerListener(this);

_player.realize(); _recordControl = (RecordControl) _player.getControl( "RecordControl" ); _recordControl .setRecordLocation("file:///store/home/user/AudioRecordingTest.amr"); _recordControl.startRecord(); _player.start(); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); } } public void stop() { if (_player != null) { _player.close(); _player = null; }

if (_recordControl != null) { _recordControl.stopRecord(); try { _recordControl.commit(); } catch (Exception e) { Dialog.alert(e.toString()); } _recordControl = null; } }

public void playerUpdate(Player player, String event, Object eventData) { Dialog.alert("Player " + player.hashCode() + " got event " + event + ": " + eventData); }

Development Guide Recording audio

15

Page 18: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

} }}

Development Guide Recording audio

16

Page 19: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Working with video on a BlackBerry device 2

Playing videoYou can play video in your application on a BlackBerry® device by using the javax.microedition.media.Player class.

The Player class lets you open a file that is stored on the BlackBerry device's built-in media storage or media card storage, byspecifying a URL, or by specifying a location in your .cod file using the format: cod:///path. Player can retrieve the associatedControl classes that you can use to control various aspects of playback (for example, the volume of the audio track).

To create a UI component that displays the video playback, you can invoke VideoControl.initDisplay() to retrieve aField object that is added to your UI.

Play a video in a UI field in a BlackBerry device application1. Import the required classes and interfaces.

import net.rim.device.api.ui.*;import net.rim.device.api.ui.component.*;import net.rim.device.api.ui.container.*;

import java.io.*;import javax.microedition.media.*;import javax.microedition.media.control.*;

2. Create the application framework by extending the UiApplication class. In main(), create an instance of the newclass and invoke enterEventDispatcher() to enable the application to receive events. In the application constructor,invoke pushScreen() to display the custom screen for the application. The VideoPlaybackDemoScreen class, whichis described in step 3, represents the custom screen.

public class VideoPlaybackDemo extends UiApplication{ public static void main(String[] args) { VideoPlaybackDemo app = new VideoPlaybackDemo(); app.enterEventDispatcher(); } public VideoPlaybackDemo() { pushScreen(new VideoPlaybackDemoScreen()); }}

3. Create the framework for the custom screen by extending the MainScreen class.

Development Guide Working with video on a BlackBerry device

17

Page 20: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

private class VideoPlaybackDemoScreen extends MainScreen{ public VideoPlaybackDemoScreen() { }}

4. In the screen constructor, in a try/catch block, create an instance of the Player class by invokingManager.createPlayer(String), passing in the location of the video file to play.

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); }catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

5. To control an aspect of playback, retrieve the appropriate Control object. First, invoke the Player object's realize() method to access its associated Control object. Next , invoke Player.getControl() passing in the string,VideoControl, to retrieve the VideoControl object that is associated with Player.

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl");}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

6. Invoke VideoControl.initDisplayMode(int mode, Object arg) passing an arg parameter specifying the UIprimitive that displays the video to initialize the mode that a video field uses. Cast the returned object as a Field object.

Note: You can invoke initDisplayMode() in different ways to return a Field , an Item for use with MIDlets, or todisplay a video on a Canvas class.

Development Guide Playing video

18

Page 21: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl"); Field videoField = (Field)videoControl.initDisplayMode( VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field" );

}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

7. Invoke add() to add the returned Field object to your Screen or Manager, as you would add any other componentto your UI.

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl"); Field videoField = (Field)videoControl.initDisplayMode( VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field" );

add(videoField);}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

8. To set the volume of playback, invoke Player.getControl() passing in the string, VolumeControl, to retrieve theVolumeControl object that is associated with Player. Invoke VolumeControl.setLevel() to specify the volumeof playback.

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl");

Development Guide Playing video

19

Page 22: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Field videoField = (Field)videoControl.initDisplayMode( VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field" );

add(videoField);

VolumeControl volume = (VolumeControl) player.getControl("VolumeControl"); volume.setLevel(30);}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

9. Invoke Player.start() to start playback.

try { Player player = javax.microedition.media.Manager .createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl"); Field videoField = (Field)videoControl.initDisplayMode( VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field" );

add(videoField);

VolumeControl volume = (VolumeControl) player.getControl("VolumeControl"); volume.setLevel(30);

player.start();}catch(MediaException me){ Dialog.alert(me.toString());}catch(IOException ioe){ Dialog.alert(ioe.toString());}

Code sample: Playing video in a UI field in a BlackBerry device application

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import javax.microedition.media.*;import javax.microedition.media.control.*;

Development Guide Playing video

20

Page 23: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

import java.io.*;

public class VideoPlaybackDemo extends UiApplication{ public static void main(String[] args) { VideoPlaybackDemo app = new VideoPlaybackDemo(); app.enterEventDispatcher(); } public VideoPlaybackDemo() { pushScreen(new VideoPlaybackDemoScreen()); }

private class VideoPlaybackDemoScreen extends MainScreen { public VideoPlaybackDemoScreen() { try { Player player = javax.microedition.media.Manager.createPlayer("file:///SDCard/BlackBerry/videos/soccer1.avi"); player.realize(); VideoControl videoControl = (VideoControl) player.getControl("VideoControl"); Field videoField = (Field)videoControl.initDisplayMode( VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field" );

add(videoField);

VolumeControl volume = (VolumeControl) player.getControl("VolumeControl"); volume.setLevel(30);

player.start(); } catch(MediaException me) { Dialog.alert(me.toString()); } catch(IOException ioe) { Dialog.alert(ioe.toString()); } } }}

Development Guide

21

Page 24: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Recording videoYou can record video in BlackBerry® device application by using the Player class and the associated RecordControlinterface. The recording is saved to a file in built-in storage, media card storage, or to a stream.

To create a viewfinder to monitor what the camera is recording, you can use the VideoControl.initDisplay() methodto retrieve a Field object that is added to your UI.

Record video to a file in a BlackBerry device application1. Import the required classes.

import net.rim.device.api.ui.*;import net.rim.device.api.ui.component.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.system.*;import java.io.*;import java.lang.*;import javax.microedition.media.*;import javax.microedition.media.control.*;

2. Create the application framework by extending the UiApplication class. In main(), create an instance of the newclass and invoke enterEventDispatcher() to enable the application to receive events. In the application constructor,invoke pushScreen() to display the custom screen for the application. The VideoRecordingDemoScreen class,which is described in step 3, represents the custom screen.

public class VideoRecordingDemo extends UiApplication{ public static void main(String[] args) { VideoRecordingDemo app = new VideoRecordingDemo(); app.enterEventDispatcher(); } public VideoPlaybackDemo() { pushScreen(new VideoRecordingDemoScreen()); }}

3. Create the framework for the custom screen by extending the MainScreen class. Declare an instance of theVideoRecorderThread class, which is described in step 5.

class VideoRecordingDemoScreen extends MainScreen{ private VideoRecorderThread _recorderThread;

public VideoRecordingDemoScreen()

Development Guide Recording video

22

Page 25: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

{ }}

4. In the VideoRecordingDemoScreen constructor, invoke setTitle() to specify the title for the screen. InvokeaddMenuItem() twice to add the menu items to start and stop the recording, which is described in step 5.

public VideoRecordingDemoScreen(){ setTitle("Video recording demo");

addMenuItem(new StartRecording()); addMenuItem(new StopRecording()); }

5. In the VideoRecordingDemoScreen class, define the menu items to start recording and to stop recording by invokingthe start() and stop() methods of the VideoRecorderThread class respectively, which is described in step 6.

private class StartRecording extends MenuItem { public StartRecording() { super("Start recording", 0, 100); }

public void run() { try { VideoRecorderThread newRecorderThread = new VideoRecorderThread(); newRecorderThread.start(); _recorderThread = newRecorderThread; } catch (Exception e) { Dialog.alert(e.toString()); } }} private class StopRecording extends MenuItem { public StopRecording() { super("Stop recording", 0, 100); }

public void run() { try {

Development Guide Recording video

23

Page 26: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

if (_recorderThread != null) { _recorderThread.stop(); } } catch (Exception e) { Dialog.alert(e.toString()); } }}

6. Inside the VideoRecordingDemo screen class, define an inner class that extends Thread and implementsPlayerListener. In the class, create a variable of type Player, and a variable of type RecordControl for recordingmedia from Player.

Note: You are not required to record video in a separate thread because recording operations are threaded by design.

private class VideoRecorderThread extends Thread implements javax.microedition.media.PlayerListener{ private Player _player; private RecordControl _recordControl;

VideoRecorderThread() { }

}

7. In the VideoRecorderThread class, implement run(). In run() create a try/catch block and invokeManager.createPlayer(String locator) to create a Player object to capture video, using as a parameter avalue that specifies the encoding to use to record video. Only the encoding video/3gpp is currently supported.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp"); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

Development Guide Recording video

24

Page 27: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

8. Invoke Player.addPlayerListener() specifying this as a parameter because VideoRecorderThreadimplements the PlayerListener interface.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

9. Invoke Player.realize() to access the Control object. Then , invoke Player.getControl() passing in thestring, VideoControl, to retrieve the VideoControl object that is associated with Player.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

10. Invoke Player.getControl(), passing in the string, RecordControl, to retrieve the RecordControl object.

Development Guide Recording video

25

Page 28: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" ); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

11. Invoke VideoControl.initDisplayMode(int mode, Object arg) passing an arg parameter specifying the UIprimitive that displays the video to initialize the mode that a video field uses. Cast the returned object as a Field object.

Note: You can invoke initDisplayMode() in different ways to return a Field, an Item for use with MIDlets, or todisplay a video on a Canvas class.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

Field videoField = (Field) videoControl.initDisplayMode(VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); } catch( IOException e ) {

Development Guide Recording video

26

Page 29: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

12. In a try/catch block, invoke VideoControl.setDisplaySize() to set the size of the viewfinder to monitor yourrecording. In the following code sample, the size is set to the full screen of the device. Invoke add() to add the viewfinderto the screen.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

Field videoField = (Field) videoControl.initDisplayMode(VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field");

try { videoControl.setDisplaySize( Display.getWidth(), Display.getHeight() ); } catch( MediaException me ) { // setDisplaySize is not supported } add(videoField); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

13. Invoke RecordControl.setRecordLocation() to specify the location on the device to save the video recording.

Development Guide Recording video

27

Page 30: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

Field videoField = (Field) videoControl.initDisplayMode(VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field");

try { videoControl.setDisplaySize( Display.getWidth(), Display.getHeight() ); } catch( MediaException me ) { // setDisplaySize is not supported }

add(videoField); _recordControl.setRecordLocation("file:///store/home/user/VideoRecordingTest .3gpp" ); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

14. Invoke RecordControl.startRecord() to start recording the video and start playing the media from Player.Invoke Player.start() to start Player.

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

Development Guide Recording video

28

Page 31: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

Field videoField = (Field) videoControl.initDisplayMode(VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field");

try { videoControl.setDisplaySize( Display.getWidth(), Display.getHeight() ); } catch( MediaException me ) { // setDisplaySize is not supported } add(videoField);

_recordControl.setRecordLocation("file:///store/home/user/VideoRecordingTest .3gpp" );

_recordControl.startRecord(); _player.start(); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); }}

15. In VideoRecorderThread, implement the Thread interface's stop() method. Check that Player is not null andinvoke Player.close() to release the Player object's resources. Set the Player to null.

public void stop() { if (_player != null) { _player.close(); _player = null; }}

Development Guide Recording video

29

Page 32: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

16. Check that RecordControl is not null and invoke RecordControl.stopRecord() to stop recording. In a try/catch block, invoke RecordControl.commit() to save the recording to a specified file. Set RecordControl to null.

public void stop() { if (_player != null) { _player.close(); _player = null; }

if (_recordControl != null) { _recordControl.stopRecord(); try { _recordControl.commit(); } catch (Exception e) { Dialog.alert(e.toString()); } _recordControl = null; }}

17. In VideoRecorderThread, implement the PlayerListener interface's playerUpdate() method which isinvoked when the Player object generates an event. In the following code sample, information about the event is displayed.

public void playerUpdate(Player player, String event, Object eventData) { Dialog.alert("Player " + player.hashCode() + " got event " + event + ": " + eventData);}

Code sample: Recording video to a file in a BlackBerry device application

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import net.rim.device.api.system.*;import java.lang.*;import javax.microedition.media.*;import java.io.*;import javax.microedition.media.control.*;

public class VideoRecordingDemo extends UiApplication{

Development Guide Recording video

30

Page 33: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public static void main(String[] args) { VideoRecordingDemo app = new VideoRecordingDemo(); app.enterEventDispatcher(); } public VideoRecordingDemo() { pushScreen(new VideoRecordingDemoScreen()); }

private class VideoRecordingDemoScreen extends MainScreen { private VideoRecorderThread _recorderThread;

public VideoRecordingDemoScreen() { setTitle("Video recording demo");

addMenuItem(new StartRecording()); addMenuItem(new StopRecording()); }

private class StartRecording extends MenuItem { public StartRecording() { super("Start recording", 0, 100); }

public void run() { try { VideoRecorderThread newRecorderThread = new VideoRecorderThread(); newRecorderThread.start(); _recorderThread = newRecorderThread; } catch (Exception e) { Dialog.alert(e.toString()); } } } private class StopRecording extends MenuItem { public StopRecording() { super("Stop recording", 0, 100); }

Development Guide Recording video

31

Page 34: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

public void run() { try { if (_recorderThread != null) { _recorderThread.stop(); } } catch (Exception e) { Dialog.alert(e.toString()); } } }

private class VideoRecorderThread extends Thread implements javax.microedition.media.PlayerListener { private Player _player; private RecordControl _recordControl;

VideoRecorderThread() { }

public void run() { try { _player = javax.microedition.media.Manager .createPlayer("capture://video?encoding=video/3gpp");

_player.addPlayerListener(this);

_player.realize(); VideoControl videoControl = (VideoControl) _player.getControl("VideoControl"); _recordControl = (RecordControl) _player.getControl( "RecordControl" );

Field videoField = (Field) videoControl.initDisplayMode(VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field");

try { videoControl.setDisplaySize( Display.getWidth(), Display.getHeight() ); } catch( MediaException me )

Development Guide Recording video

32

Page 35: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

{ // setDisplaySize is not supported } add(videoField);

_recordControl .setRecordLocation("file:///store/home/user/VideoRecordingTest.3gpp" );

_recordControl.startRecord(); _player.start(); } catch( IOException e ) { Dialog.alert(e.toString()); } catch( MediaException e ) { Dialog.alert(e.toString()); } } public void stop() { if (_player != null) { _player.close(); _player = null; }

if (_recordControl != null) { _recordControl.stopRecord(); try { _recordControl.commit(); } catch (Exception e) { Dialog.alert(e.toString()); } _recordControl = null; } }

public void playerUpdate(Player player, String event, Object eventData) { Dialog.alert("Player " + player.hashCode() + " got event " + event + ": " + eventData); }

Development Guide Recording video

33

Page 36: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

} }}

RIMM streaming video fileThe RIM proprietary video format (RIMM streaming file) consists of a header, a list of frames, and a footer.

The file also contains a descriptor which stores additional metadata. The location of this descriptor depends on the recordingdestination. If the recording destination is a file, the descriptor is located at the end of the header, before the list of frames. Ifthe recording destination is a stream, the descriptor is located after the list of frames in the footer.

RIM proprietary video format (RIMM streaming file)The RIM proprietary video format consists of a header, a list of frames, and a footer. When parsing this file, all values of typeint or short are little-endian.

Header

Field Value Size

ID tag RIMM 4 B

version 0 3 B

descriptor location • 0 if recording to a file

• 1 if recording to a stream

1 B

descriptor descriptor values • 75 B if recording to a file

• 0 B if recording to a stream

Frames

Field Value Size

stream type • 0 if this is a frame of audio

• 1 if this is a frame of video

1 B

key frame • 1 if this is a key frame

• 0 otherwise

1 b

config frame • 1 if this is a config frame

• 0 otherwise

1 b

Development Guide RIMM streaming video file

34

Page 37: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Field Value Size

size frame size, in bytes 30 b

duration length of video, in milliseconds 2 B

data the actual frame data <size> B

stream type • 0 if this is a frame of audio

• 1 if this is a frame of video

1 B

key frame • 1 if this is a key frame

• 0 otherwise

1 b

config frame • 1 if this is a config frame

• 0 otherwise

1 b

size frame size, in bytes 30 b

duration length of video, in milliseconds 2 B

Note: The key frame, config frame, and size fields are stored in one 32-bit int with the key frame and config frame fields storedin the first two bits.

Footer

Field Value Size

Descriptor descriptor values • 75 bytes if recording to a stream

• 0 bytes if recording to a file

Descriptor

Field Value Size

audio frames number of audio frames 4 B

video frames number of video frames 4 B

audio key frames number of audio key frames 4 B

video key frames number of video key frames 4 B

audio frame rates number of audio frame rates (number of frame

rate changes + 1)

4 B

video frame rates number of video frame rates (number of frame

rate changes + 1)

4 B

audio size size of audio stream in bytes 4 B

video size size of video stream in bytes 4 B

Development Guide RIMM streaming video file

35

Page 38: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Field Value Size

video frame rate the initial video frame rate, in frames per second 4 B

video max frame size size of largest video frame, in bytes 4 B

audio duration length of audio stream, in milliseconds 4 B

video duration length of video stream, in milliseconds 4 B

RESERVED undefined 20 B

width the width of the video, in pixels 2 B

height the height of the video, in pixels 2 B

video codec • 2 if this video codec is mpeg4

• 5 if this video codec is H.263

• 6 if this video codec is H.264

2 B

audio codec • 0 if this audio codec is PCM

• 7 if this audio codec is AMR

• 0xA if this audio codec is AAC

1 B

Code sample: Parsing a RIMM streaming video file

import java.io.*;import java.util.*;import javax.microedition.io.*;import javax.microedition.io.file.*;

/** * */public class KeyFrameOutputStream extends OutputStream { // output locations on the sd card private static final String OUT_DIR = "file:///SDCard/securitycam/"; private static final String OUT_FILE = "output.frames"; // some size constants private static final int HEADER_SIZE = 8; private static final int CHUNK_INFO_SIZE = 7; // parsing states private static final int STATE_HEADER = 0; private static final int STATE_CHUNK_INFO = 1; private static final int STATE_DATA = 2; private static final int STATE_WAIT_FOR_NEXT = 3; // member variables private int _state;

Development Guide RIMM streaming video file

36

Page 39: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

private int _pos; private boolean _isVideoFrame; private boolean _isKeyFrame; private boolean _isConfigFrame; private boolean _startSaving; private boolean _saveFrame; private int _dataSize; private int _duration; // temp buffer ref private byte[] _buf; private FileConnection _file; private OutputStream _out; private WriteThread _writer; private boolean _reading; public KeyFrameOutputStream() { _state = STATE_HEADER; _pos = 0; } public void open() { _reading = true; try { // create the file connection for our frame destination FileConnection dir = (FileConnection)Connector.open( OUT_DIR ); if( !dir.exists() ) { dir.mkdir(); } dir.close(); _file = (FileConnection)Connector.open( OUT_DIR + OUT_FILE ); if( !_file.exists() ) { _file.create(); } else { _file.truncate( 0L ); } _out = _file.openOutputStream(); } catch ( Exception e ) { } // start the write thread _writer = new WriteThread( _out ); _writer.start(); } public void startClosing() { // shuts down the write thread _reading = false; if( _writer != null ) _writer.stop();

Development Guide RIMM streaming video file

37

Page 40: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

} public void write( int b ) throws IOException { if( _reading ) { switch( _state ) { case STATE_HEADER: // read the video stream header _pos++; if( _pos == HEADER_SIZE ) { _state = STATE_CHUNK_INFO; _buf = new byte[CHUNK_INFO_SIZE]; _pos = 0; } break; case STATE_CHUNK_INFO: // parse the information about the next chunk _buf[_pos] = (byte)b; _pos++; if( _pos == CHUNK_INFO_SIZE ) { // 1 indicates video frame, 0 indicates audio _isVideoFrame = (_buf[0] != 0); // key frame and config frame flags are in the top two bits// of the data size value _isKeyFrame = ((_buf[4] & 0x80) != 0); _isConfigFrame = ((_buf[4] & 0x40) != 0); _dataSize = ((int)(_buf[4] & 0x3f) << 24) | ((int)(_buf[3] & 0xff) << 16) | ((int)(_buf[2] & 0xff) << 8) | ((int)(_buf[1] & 0xff)); // duration is stored in the next two bytes _duration = ((int)(_buf[6] & 0xff) << 8) | ((int)(_buf[5] & 0xff)); // we want the config frame to be the first frame in our// output file if( !_startSaving ) { if( _isVideoFrame && _isConfigFrame ) { _startSaving = true; } } // after that only save the key frames _saveFrame = _startSaving && _isVideoFrame && ( _isConfigFrame || _isKeyFrame ); _state = STATE_DATA; if( _saveFrame ) { _buf = new byte[_dataSize]; } _pos = 0;

Development Guide RIMM streaming video file

38

Page 41: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

} break; case STATE_DATA: // buffer the frame for writing to file if( _saveFrame ) _buf[_pos] = (byte)b; _pos++; if( _pos == _dataSize ) { if( _saveFrame ) { _writer.addFrame( _buf ); } _state = STATE_WAIT_FOR_NEXT; _buf = new byte[CHUNK_INFO_SIZE]; _pos = 0; } break; case STATE_WAIT_FOR_NEXT: // skip over the chunk footer _pos++; if( _pos == CHUNK_INFO_SIZE ) { _state = STATE_CHUNK_INFO; _buf = new byte[CHUNK_INFO_SIZE]; _pos = 0; } break; } } } public void close() throws IOException { // shut down the write thread and close our file try { _writer.join(); } catch ( InterruptedException ie ) { } _out.close(); _file.close(); } private static final class WriteThread extends Thread { // writes key frames to a file as they are found by our parser private Vector _frames; private boolean _running; private OutputStream _out; public WriteThread( OutputStream out ) { _frames = new Vector(); _running = true; _out = out; } public void run() { for( ;; ) {

Development Guide RIMM streaming video file

39

Page 42: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

ByteArray frame = null; synchronized( this ) { if( _frames.size() > 0 ) { frame = (ByteArray)_frames.elementAt( 0 ); if( frame == null ) break; _frames.removeElementAt( 0 ); } else { if( !_running ) break; try { wait(); if( _running ) continue; } catch ( InterruptedException ie ) { } } } if( frame == null ) break; try { byte[] bytes = frame.array; _out.write( bytes, 0, bytes.length ); _out.flush(); } catch ( Exception e ) { } } } public synchronized void addFrame( byte[] frame ) { _frames.addElement( new ByteArray( frame ) ); notifyAll(); } public synchronized void stop() { _running = false; notifyAll(); } } private static final class ByteArray { public byte[] array; public ByteArray( byte[] array ) { this.array = array; } }}

Development Guide RIMM streaming video file

40

Page 43: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Working with pictures on a BlackBerry device 3

Taking picturesYou can take a picture on a BlackBerry® device by using the javax.microedition.media.Player class and the associatedVideoControl interface in your BlackBerry device application. When you create an instance of the Player class, you canspecify the appropriate file encoding and resolution of the picture.

You can invoke VideoControl.getSnapshot() to take the picture. The image is returned as a byte array (the unprocessedimage), which you can display on the device, save to a file, or process as required.

To create a viewfinder to monitor the picture the camera is taking, you can invoke VideoControl.initDisplay() toretrieve a Field object that is added to your UI.

Take a picture in a BlackBerry device application1. Import the required classes and interfaces.

import net.rim.device.api.amms.control.camera.*;import net.rim.device.api.ui.*;import net.rim.device.api.ui.component.*;import net.rim.device.api.ui.container.*;

import javax.microedition.media.*;import javax.microedition.media.control.*;

2. Create the application framework by extending the UiApplication class. In main(), create an instance of the newclass and invoke enterEventDispatcher() to enable the application to receive events. In the application constructor,invoke pushScreen() to display the custom screen for the application. The ImageCaptureDemoScreen class, whichis described in step 3, represents the custom screen.

public class ImageCaptureDemo extends UiApplication{ public static void main(String[] args) { ImageCaptureDemo app = new ImageCaptureDemo(); app.enterEventDispatcher(); } public ImageCaptureDemo() { pushScreen(new ImageCaptureDemoScreen()); }}

Development Guide Working with pictures on a BlackBerry device

41

Page 44: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

3. Create the framework for the custom screen by extending the MainScreen class. Declare class variables for thePlayer and VideoControl classes that you create in the screen's constructor, which is described in step 4.

class ImageCaptureDemoScreen extends MainScreen{ Player _p; VideoControl _videoControl; public ImageCaptureDemoScreen() { }}

4. In the screen constructor, initialize the camera. In a try/catch block, create an instance of the Player class by invokingManager.createPlayer(String), passing in the encoding parameter. The jpeg and image/jpeg parametersare supported. If you do not specify the encoding parameter, by default the encoding parameter is image/jpeg.

try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); }catch(Exception e){ Dialog.alert(e.toString());}

5. To control an aspect of taking the picture, retrieve the appropriate Control object. Invoke the Player object's realize() method to access the associated Control object. Next, invoke Player.getControl() to retrieve the Playerobject's VideoControl.

try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");}catch(Exception e){ Dialog.alert(e.toString());}

6. Create a viewfinder in your application by invoking VideoControl.initDisplayMode(int mode, Object arg)and passing in a parameter specifying the UI primitive that displays the picture to initialize the mode that a video field uses.Cast the returned object as a Field object. Invoke VideoControl.setDisplayFullScreen() passing in trueto set the viewfinder to take up the full screen of the device. Invoke VideoControl.setVisible() passing intrue to display the viewfinder.

Development Guide Taking pictures

42

Page 45: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");

if (videoControl != null) { Field videoField = (Field) _videoControl.initDisplayMode (VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); _videoControl.setDisplayFullScreen(true); _videoControl.setVisible(true); }}catch(Exception e){ Dialog.alert(e.toString());}

7. Invoke Player.start() to set the player to the STARTED state.

try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");

if (videoControl != null) { Field videoField = (Field) _videoControl.initDisplayMode (VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); _videoControl.setDisplayFullScreen(true); _videoControl.setVisible(true);

_p.start(); }

}catch(Exception e){ Dialog.alert(e.toString());}

8. To enable autofocus for the camera, invoke Player.getContol() to retrieve the Player object'sEnhancedFocusControl interface. Iinvoke EnhancedFocusControl.startAutoFocus().

try { _p = javax.microedition.media.Manager

Development Guide Taking pictures

43

Page 46: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

.createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");

if (videoControl != null) { Field videoField = (Field) _videoControl.initDisplayMode (VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); _videoControl.setDisplayFullScreen(true); _videoControl.setVisible(true);

_p.start();

EnhancedFocusControl efc = (EnhancedFocusControl)p.getControl("net.rim.device.api.amms.control.camera .EnhancedFocusControl"); efc.startAutoFocus(); } }catch(Exception e){ Dialog.alert(e.toString());}

9. Check that videoField is not null and invoke add() to add the viewfinder to the screen.

try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");

if (videoControl != null) { Field videoField = (Field) _videoControl.initDisplayMode (VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); _videoControl.setDisplayFullScreen(true); _videoControl.setVisible(true);

_p.start();

EnhancedFocusControl efc = (EnhancedFocusControl)p.getControl("net.rim.device.api.amms.control.camera .EnhancedFocusControl"); efc.startAutoFocus();

if(videoField != null) { add(videoField); } }

Development Guide Taking pictures

44

Page 47: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

}catch(Exception e){ Dialog.alert(e.toString());}

10. In ImageCaptureDemoScreen, invoke net.rim.device.api.ui.Screen.invokeAction(). Thisimplementation takes the picture when the user clicks the trackpad, trackball, or touch screen. Return a boolean specifyingif the action is consumed.

protected boolean invokeAction(int action){ boolean handled = super.invokeAction(action); if(!handled) { if(action == ACTION_INVOKE) { } } return handled; }

11. In the if(action == ACTION_INVOKE) statement, in a try/catch block, invoke VideoControl.getSnapshot() to take the picture, passing in null to use the encoding setting that you specified in step 4. The image is returned asa byte array.

protected boolean invokeAction(int action){ boolean handled = super.invokeAction(action); if(!handled) { if(action == ACTION_INVOKE) { try { byte[] rawImage = _videoControl.getSnapshot(null); } catch(Exception e) { Dialog.alert(e.toString()); } } } return handled; }

Development Guide Taking pictures

45

Page 48: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Code sample: Taking a picture in a BlackBerry device application

import net.rim.device.api.ui.*;import net.rim.device.api.ui.container.*;import net.rim.device.api.ui.component.*;import net.rim.device.api.amms.control.camera.*;import javax.microedition.media.*;import javax.microedition.media.control.*;

public class ImageCaptureDemo extends UiApplication{ public static void main(String[] args) { ImageCaptureDemo app = new ImageCaptureDemo(); app.enterEventDispatcher(); } public ImageCaptureDemo() { pushScreen(new ImageCaptureDemoScreen()); }

class ImageCaptureDemoScreen extends MainScreen { Player _p; VideoControl _videoControl; public ImageCaptureDemoScreen() { try { _p = javax.microedition.media.Manager .createPlayer("capture://video?encoding=jpeg&width=1024&height=768"); _p.realize(); _videoControl = (VideoControl) _p.getControl("VideoControl");

if (videoControl != null) { Field videoField = (Field) _videoControl.initDisplayMode (VideoControl.USE_GUI_PRIMITIVE, "net.rim.device.api.ui.Field"); _videoControl.setDisplayFullScreen(true); _videoControl.setVisible(true); _p.start();

EnhancedFocusControl efc = (EnhancedFocusControl)p.getControl("net.rim.device.api.amms.control.camera .EnhancedFocusControl"); efc.startAutoFocus();

if(videoField != null)

Development Guide Taking pictures

46

Page 49: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

{ add(videoField); } } } catch(Exception e) { Dialog.alert(e.toString()); } }

protected boolean invokeAction(int action) { boolean handled = super.invokeAction(action); if(!handled) { if(action == ACTION_INVOKE) { try { byte[] rawImage = _videoControl.getSnapshot(null); } catch(Exception e); { Dialog.alert(e.toString()); } } } return handled; } } }

Development Guide Taking pictures

47

Page 50: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Find more information 4

• www.blackberry.com/go/apiref: View the latest version of the API reference for the BlackBerry® Java® SDK.• www.blackberry.com/go/devguides: Find development guides, release notes, and sample application overviews for the

BlackBerry Java SDK.• www.blackberry.com/developers: Visit the BlackBerry® Developer Zone for resources on developing BlackBerry device

applications.• www.blackberry.com/go/developerkb: View knowledge base articles on the BlackBerry Development Knowledge Base.• www.blackberry.com/developers/downloads: Find the latest development tools and downloads for developing BlackBerry

device applications.

Development Guide Find more information

48

Page 51: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Provide feedback 5

To provide feedback on this deliverable, visit www.blackberry.com/docsfeedback.

Development Guide Provide feedback

49

Page 52: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Document revision history 6

Date Description

25 October 2010 Changed code samples in the topics:

• Record video to a file in a BlackBerry device application

• Recording video to a file in a BlackBerry device application

3 August 2010 Moved the following topics to the BlackBerry® Java® SDK UI and Navigation

Development Guide:

• Access an encoded image through an input stream

• Code sample: Displaying a row of images for scrolling

• Code sample: Displaying an image for zooming and panning

• Display a row of images for scrolling

• Display an encoded image

• Display an image for zooming and panning

• Displaying a row of images for scrolling

• Displaying an image for zooming and panning

• Encode an image

• Specify the decoding mode for an image

• Specify the display size of an encoded image

• Using encoded images

Development Guide Document revision history

50

Page 53: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Legal notice 7

©2010 Research In Motion Limited. All rights reserved. BlackBerry®, RIM®, Research In Motion®, and related trademarks, names,and logos are the property of Research In Motion Limited and are registered and/or used in the U.S. and countries around theworld.

Bluetooth is a trademark of Bluetooth SIG. Java and Javadoc are trademarks of Oracle America, Inc. Plazmic is a trademark ofPlazmic Inc. All other trademarks are the property of their respective owners.

This documentation including all documentation incorporated by reference herein such as documentation provided or madeavailable at www.blackberry.com/go/docs is provided or made accessible "AS IS" and "AS AVAILABLE" and without condition,endorsement, guarantee, representation, or warranty of any kind by Research In Motion Limited and its affiliated companies("RIM") and RIM assumes no responsibility for any typographical, technical, or other inaccuracies, errors, or omissions in thisdocumentation. In order to protect RIM proprietary and confidential information and/or trade secrets, this documentation maydescribe some aspects of RIM technology in generalized terms. RIM reserves the right to periodically change information thatis contained in this documentation; however, RIM makes no commitment to provide any such changes, updates, enhancements,or other additions to this documentation to you in a timely manner or at all.

This documentation might contain references to third-party sources of information, hardware or software, products or servicesincluding components and content such as content protected by copyright and/or third-party web sites (collectively the "ThirdParty Products and Services"). RIM does not control, and is not responsible for, any Third Party Products and Services including,without limitation the content, accuracy, copyright compliance, compatibility, performance, trustworthiness, legality, decency,links, or any other aspect of Third Party Products and Services. The inclusion of a reference to Third Party Products and Servicesin this documentation does not imply endorsement by RIM of the Third Party Products and Services or the third party in any way.

EXCEPT TO THE EXTENT SPECIFICALLY PROHIBITED BY APPLICABLE LAW IN YOUR JURISDICTION, ALL CONDITIONS,ENDORSEMENTS, GUARANTEES, REPRESENTATIONS, OR WARRANTIES OF ANY KIND, EXPRESS OR IMPLIED, INCLUDINGWITHOUT LIMITATION, ANY CONDITIONS, ENDORSEMENTS, GUARANTEES, REPRESENTATIONS OR WARRANTIES OFDURABILITY, FITNESS FOR A PARTICULAR PURPOSE OR USE, MERCHANTABILITY, MERCHANTABLE QUALITY, NON-INFRINGEMENT, SATISFACTORY QUALITY, OR TITLE, OR ARISING FROM A STATUTE OR CUSTOM OR A COURSE OF DEALINGOR USAGE OF TRADE, OR RELATED TO THE DOCUMENTATION OR ITS USE, OR PERFORMANCE OR NON-PERFORMANCEOF ANY SOFTWARE, HARDWARE, SERVICE, OR ANY THIRD PARTY PRODUCTS AND SERVICES REFERENCED HEREIN, AREHEREBY EXCLUDED. YOU MAY ALSO HAVE OTHER RIGHTS THAT VARY BY STATE OR PROVINCE. SOME JURISDICTIONSMAY NOT ALLOW THE EXCLUSION OR LIMITATION OF IMPLIED WARRANTIES AND CONDITIONS. TO THE EXTENTPERMITTED BY LAW, ANY IMPLIED WARRANTIES OR CONDITIONS RELATING TO THE DOCUMENTATION TO THE EXTENTTHEY CANNOT BE EXCLUDED AS SET OUT ABOVE, BUT CAN BE LIMITED, ARE HEREBY LIMITED TO NINETY (90) DAYS FROMTHE DATE YOU FIRST ACQUIRED THE DOCUMENTATION OR THE ITEM THAT IS THE SUBJECT OF THE CLAIM.

TO THE MAXIMUM EXTENT PERMITTED BY APPLICABLE LAW IN YOUR JURISDICTION, IN NO EVENT SHALL RIM BE LIABLEFOR ANY TYPE OF DAMAGES RELATED TO THIS DOCUMENTATION OR ITS USE, OR PERFORMANCE OR NON-PERFORMANCE OF ANY SOFTWARE, HARDWARE, SERVICE, OR ANY THIRD PARTY PRODUCTS AND SERVICES REFERENCEDHEREIN INCLUDING WITHOUT LIMITATION ANY OF THE FOLLOWING DAMAGES: DIRECT, CONSEQUENTIAL, EXEMPLARY,INCIDENTAL, INDIRECT, SPECIAL, PUNITIVE, OR AGGRAVATED DAMAGES, DAMAGES FOR LOSS OF PROFITS OR REVENUES,FAILURE TO REALIZE ANY EXPECTED SAVINGS, BUSINESS INTERRUPTION, LOSS OF BUSINESS INFORMATION, LOSS OF

Development Guide Legal notice

51

Page 54: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

BUSINESS OPPORTUNITY, OR CORRUPTION OR LOSS OF DATA, FAILURES TO TRANSMIT OR RECEIVE ANY DATA, PROBLEMSASSOCIATED WITH ANY APPLICATIONS USED IN CONJUNCTION WITH RIM PRODUCTS OR SERVICES, DOWNTIME COSTS,LOSS OF THE USE OF RIM PRODUCTS OR SERVICES OR ANY PORTION THEREOF OR OF ANY AIRTIME SERVICES, COST OFSUBSTITUTE GOODS, COSTS OF COVER, FACILITIES OR SERVICES, COST OF CAPITAL, OR OTHER SIMILAR PECUNIARYLOSSES, WHETHER OR NOT SUCH DAMAGES WERE FORESEEN OR UNFORESEEN, AND EVEN IF RIM HAS BEEN ADVISEDOF THE POSSIBILITY OF SUCH DAMAGES.

TO THE MAXIMUM EXTENT PERMITTED BY APPLICABLE LAW IN YOUR JURISDICTION, RIM SHALL HAVE NO OTHEROBLIGATION, DUTY, OR LIABILITY WHATSOEVER IN CONTRACT, TORT, OR OTHERWISE TO YOU INCLUDING ANY LIABILITYFOR NEGLIGENCE OR STRICT LIABILITY.

THE LIMITATIONS, EXCLUSIONS, AND DISCLAIMERS HEREIN SHALL APPLY: (A) IRRESPECTIVE OF THE NATURE OF THECAUSE OF ACTION, DEMAND, OR ACTION BY YOU INCLUDING BUT NOT LIMITED TO BREACH OF CONTRACT, NEGLIGENCE,TORT, STRICT LIABILITY OR ANY OTHER LEGAL THEORY AND SHALL SURVIVE A FUNDAMENTAL BREACH OR BREACHESOR THE FAILURE OF THE ESSENTIAL PURPOSE OF THIS AGREEMENT OR OF ANY REMEDY CONTAINED HEREIN; AND (B)TO RIM AND ITS AFFILIATED COMPANIES, THEIR SUCCESSORS, ASSIGNS, AGENTS, SUPPLIERS (INCLUDING AIRTIMESERVICE PROVIDERS), AUTHORIZED RIM DISTRIBUTORS (ALSO INCLUDING AIRTIME SERVICE PROVIDERS) AND THEIRRESPECTIVE DIRECTORS, EMPLOYEES, AND INDEPENDENT CONTRACTORS.

IN ADDITION TO THE LIMITATIONS AND EXCLUSIONS SET OUT ABOVE, IN NO EVENT SHALL ANY DIRECTOR, EMPLOYEE,AGENT, DISTRIBUTOR, SUPPLIER, INDEPENDENT CONTRACTOR OF RIM OR ANY AFFILIATES OF RIM HAVE ANY LIABILITYARISING FROM OR RELATED TO THE DOCUMENTATION.

Prior to subscribing for, installing, or using any Third Party Products and Services, it is your responsibility to ensure that yourairtime service provider has agreed to support all of their features. Some airtime service providers might not offer Internet browsingfunctionality with a subscription to the BlackBerry® Internet Service. Check with your service provider for availability, roamingarrangements, service plans and features. Installation or use of Third Party Products and Services with RIM's products and servicesmay require one or more patent, trademark, copyright, or other licenses in order to avoid infringement or violation of third partyrights. You are solely responsible for determining whether to use Third Party Products and Services and if any third party licensesare required to do so. If required you are responsible for acquiring them. You should not install or use Third Party Products andServices until all necessary licenses have been acquired. Any Third Party Products and Services that are provided with RIM'sproducts and services are provided as a convenience to you and are provided "AS IS" with no express or implied conditions,endorsements, guarantees, representations, or warranties of any kind by RIM and RIM assumes no liability whatsoever, in relationthereto. Your use of Third Party Products and Services shall be governed by and subject to you agreeing to the terms of separatelicenses and other agreements applicable thereto with third parties, except to the extent expressly covered by a license or otheragreement with RIM.

Certain features outlined in this documentation require a minimum version of BlackBerry® Enterprise Server, BlackBerry® DesktopSoftware, and/or BlackBerry® Device Software.

The terms of use of any RIM product or service are set out in a separate license or other agreement with RIM applicable thereto.NOTHING IN THIS DOCUMENTATION IS INTENDED TO SUPERSEDE ANY EXPRESS WRITTEN AGREEMENTS OR WARRANTIESPROVIDED BY RIM FOR PORTIONS OF ANY RIM PRODUCT OR SERVICE OTHER THAN THIS DOCUMENTATION.

Research In Motion Limited295 Phillip Street

Development Guide Legal notice

52

Page 55: BlackBerry_Java_SDK-Development_Guide--1249411-0803110230-001-6.0-US

Waterloo, ON N2L 3W8Canada

Research In Motion UK Limited Centrum House 36 Station Road Egham, Surrey TW20 9LF United Kingdom

Published in Canada

Development Guide Legal notice

53