MediaArtistNativeHelper.java revision a6714ce2bbb593efdfb53e071607df2a5117a643
1/* 2 * Copyright (C) 2010 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.media.videoeditor; 18 19import java.io.File; 20import java.io.IOException; 21import java.math.BigDecimal; 22import java.nio.IntBuffer; 23import java.util.ArrayList; 24import java.util.Iterator; 25import java.util.List; 26import android.graphics.Bitmap; 27import android.media.videoeditor.VideoEditor.ExportProgressListener; 28import android.media.videoeditor.VideoEditor.PreviewProgressListener; 29import android.media.videoeditor.VideoEditor.MediaProcessingProgressListener; 30import android.util.Log; 31import android.util.Pair; 32import android.view.Surface; 33import android.graphics.Canvas; 34import android.graphics.Paint; 35import android.graphics.Rect; 36 37/** 38 *This class provide Native methods to be used by MediaArtist {@hide} 39 */ 40class MediaArtistNativeHelper { 41 42 static { 43 System.loadLibrary("videoeditor_jni"); 44 } 45 46 private final int MAX_THUMBNAIL_PERMITTED = 8; 47 48 private final VideoEditor mVideoEditor; 49 50 public EditSettings mStoryBoardSettings; 51 52 private String mOutputFilename; 53 54 EditSettings mEditSettings = null; 55 56 PreviewClipProperties mClipProperties = null; 57 58 private EditSettings mPreviewEditSettings; 59 60 private AudioSettings mAudioSettings = null; 61 62 private AudioTrack mAudioTrack = null; 63 64 public boolean mInvalidatePreviewArray = true; 65 66 private boolean mRegenerateAudio = true; 67 68 private String mExportFilename = null; 69 70 private boolean mExportDone = false; 71 72 private int mProgressToApp; 73 /** 74 * The resize paint 75 */ 76 private static final Paint sResizePaint = new Paint(Paint.FILTER_BITMAP_FLAG); 77 78 public static final int TASK_LOADING_SETTINGS = 1; 79 80 public static final int TASK_ENCODING = 2; 81 82 private static final String AUDIO_TRACK_PCM_FILE = "AudioPcm.pcm"; 83 84 // Processing indication 85 public static final int PROCESSING_NONE = 0; 86 public static final int PROCESSING_AUDIO_PCM = 1; 87 public static final int PROCESSING_TRANSITION = 2; 88 public static final int PROCESSING_KENBURNS = 3; 89 public static final int PROCESSING_INTERMEDIATE1 = 11; 90 public static final int PROCESSING_INTERMEDIATE2 = 12; 91 public static final int PROCESSING_INTERMEDIATE3 = 13; 92 public static final int PROCESSING_EXPORT = 20; 93 94 private int mProcessingState; 95 private Object mProcessingObject; 96 97 private PreviewProgressListener mPreviewProgressListener; 98 private ExportProgressListener mExportProgressListener; 99 private ExtractAudioWaveformProgressListener mExtractAudioWaveformProgressListener; 100 private MediaProcessingProgressListener mMediaProcessingProgressListener; 101 private final String mProjectPath; 102 103 private long mPreviewProgress; 104 105 private String mAudioTrackPCMFilePath; 106 107 int mTotalClips = 0; 108 109 int mPreviewEffectsSize = 0; 110 111 private boolean mErrorFlagSet = false; 112 113 @SuppressWarnings("unused") 114 private int mManualEditContext; 115 116 117 List<Effect> mMediaEffectList; 118 119 List<Overlay> mMediaOverLayList; 120 121 /* Listeners */ 122 123 /** 124 * Interface definition for a listener to be invoked when there is an update 125 * in a running task. 126 */ 127 public interface OnProgressUpdateListener { 128 /** 129 * Called when there is an update. 130 * 131 * @param taskId id of the task reporting an update. 132 * @param progress progress of the task [0..100]. 133 * @see BasicEdit#TASK_ENCODING 134 */ 135 public void OnProgressUpdate(int taskId, int progress); 136 } 137 138 /** Defines the version. */ 139 public final class Version { 140 141 /** Major version number */ 142 public int major; 143 144 /** Minor version number */ 145 public int minor; 146 147 /** Revision number */ 148 public int revision; 149 150 /** VIDEOEDITOR major version number */ 151 private static final int VIDEOEDITOR_MAJOR_VERSION = 0; 152 153 /** VIDEOEDITOR minor version number */ 154 private static final int VIDEOEDITOR_MINOR_VERSION = 0; 155 156 /** VIDEOEDITOR revision number */ 157 private static final int VIDEOEDITOR_REVISION_VERSION = 1; 158 159 /** Method which returns the current VIDEOEDITOR version */ 160 public Version getVersion() { 161 Version version = new Version(); 162 163 version.major = Version.VIDEOEDITOR_MAJOR_VERSION; 164 version.minor = Version.VIDEOEDITOR_MINOR_VERSION; 165 version.revision = Version.VIDEOEDITOR_REVISION_VERSION; 166 167 return version; 168 } 169 } 170 171 /** 172 * Defines output audio formats. 173 */ 174 public final class AudioFormat { 175 /** No audio present in output clip. Used to generate video only clip */ 176 public static final int NO_AUDIO = 0; 177 178 /** AMR Narrow Band. */ 179 public static final int AMR_NB = 1; 180 181 /** Advanced Audio Coding (AAC). */ 182 public static final int AAC = 2; 183 184 /** Advanced Audio Codec Plus (HE-AAC v1). */ 185 public static final int AAC_PLUS = 3; 186 187 /** Advanced Audio Codec Plus (HE-AAC v2). */ 188 public static final int ENHANCED_AAC_PLUS = 4; 189 190 /** MPEG layer 3 (MP3). */ 191 public static final int MP3 = 5; 192 193 /** Enhanced Variable RateCodec (EVRC). */ 194 public static final int EVRC = 6; 195 196 /** PCM (PCM). */ 197 public static final int PCM = 7; 198 199 /** No transcoding. Output audio format is same as input audio format */ 200 public static final int NULL_AUDIO = 254; 201 202 /** Unsupported audio format. */ 203 public static final int UNSUPPORTED_AUDIO = 255; 204 } 205 206 /** 207 * Defines audio sampling frequencies. 208 */ 209 public final class AudioSamplingFrequency { 210 /** 211 * Default sampling frequency. Uses the default frequency for a specific 212 * audio format. For AAC the only supported (and thus default) sampling 213 * frequency is 16 kHz. For this audio format the sampling frequency in 214 * the OutputParams. 215 **/ 216 public static final int FREQ_DEFAULT = 0; 217 218 /** Audio sampling frequency of 8000 Hz. */ 219 public static final int FREQ_8000 = 8000; 220 221 /** Audio sampling frequency of 11025 Hz. */ 222 public static final int FREQ_11025 = 11025; 223 224 /** Audio sampling frequency of 12000 Hz. */ 225 public static final int FREQ_12000 = 12000; 226 227 /** Audio sampling frequency of 16000 Hz. */ 228 public static final int FREQ_16000 = 16000; 229 230 /** Audio sampling frequency of 22050 Hz. */ 231 public static final int FREQ_22050 = 22050; 232 233 /** Audio sampling frequency of 24000 Hz. */ 234 public static final int FREQ_24000 = 24000; 235 236 /** Audio sampling frequency of 32000 Hz. */ 237 public static final int FREQ_32000 = 32000; 238 239 /** Audio sampling frequency of 44100 Hz. */ 240 public static final int FREQ_44100 = 44100; 241 242 /** Audio sampling frequency of 48000 Hz. Not available for output file. */ 243 public static final int FREQ_48000 = 48000; 244 } 245 246 /** 247 * Defines the supported fixed audio and video bitrates. These values are 248 * for output audio video only. 249 */ 250 public final class Bitrate { 251 /** Variable bitrate. Means no bitrate regulation */ 252 public static final int VARIABLE = -1; 253 254 /** An undefined bitrate. */ 255 public static final int UNDEFINED = 0; 256 257 /** A bitrate of 9.2 kbits/s. */ 258 public static final int BR_9_2_KBPS = 9200; 259 260 /** A bitrate of 12.2 kbits/s. */ 261 public static final int BR_12_2_KBPS = 12200; 262 263 /** A bitrate of 16 kbits/s. */ 264 public static final int BR_16_KBPS = 16000; 265 266 /** A bitrate of 24 kbits/s. */ 267 public static final int BR_24_KBPS = 24000; 268 269 /** A bitrate of 32 kbits/s. */ 270 public static final int BR_32_KBPS = 32000; 271 272 /** A bitrate of 48 kbits/s. */ 273 public static final int BR_48_KBPS = 48000; 274 275 /** A bitrate of 64 kbits/s. */ 276 public static final int BR_64_KBPS = 64000; 277 278 /** A bitrate of 96 kbits/s. */ 279 public static final int BR_96_KBPS = 96000; 280 281 /** A bitrate of 128 kbits/s. */ 282 public static final int BR_128_KBPS = 128000; 283 284 /** A bitrate of 192 kbits/s. */ 285 public static final int BR_192_KBPS = 192000; 286 287 /** A bitrate of 256 kbits/s. */ 288 public static final int BR_256_KBPS = 256000; 289 290 /** A bitrate of 288 kbits/s. */ 291 public static final int BR_288_KBPS = 288000; 292 293 /** A bitrate of 384 kbits/s. */ 294 public static final int BR_384_KBPS = 384000; 295 296 /** A bitrate of 512 kbits/s. */ 297 public static final int BR_512_KBPS = 512000; 298 299 /** A bitrate of 800 kbits/s. */ 300 public static final int BR_800_KBPS = 800000; 301 302 /** A bitrate of 2 Mbits/s. */ 303 public static final int BR_2_MBPS = 2000000; 304 305 /** A bitrate of 5 Mbits/s. */ 306 public static final int BR_5_MBPS = 5000000; 307 308 /** A bitrate of 8 Mbits/s. */ 309 public static final int BR_8_MBPS = 8000000; 310 } 311 312 /** 313 * Defines all supported file types. 314 */ 315 public final class FileType { 316 /** 3GPP file type. */ 317 public static final int THREE_GPP = 0; 318 319 /** MP4 file type. */ 320 public static final int MP4 = 1; 321 322 /** AMR file type. */ 323 public static final int AMR = 2; 324 325 /** MP3 audio file type. */ 326 public static final int MP3 = 3; 327 328 /** PCM audio file type. */ 329 public static final int PCM = 4; 330 331 /** JPEG image file type. */ 332 public static final int JPG = 5; 333 334 /** GIF image file type. */ 335 public static final int GIF = 6; 336 337 /** PNG image file type. */ 338 public static final int PNG = 7; 339 340 /** Unsupported file type. */ 341 public static final int UNSUPPORTED = 255; 342 } 343 344 /** 345 * Defines rendering types. Rendering can only be applied to files 346 * containing video streams. 347 **/ 348 public final class MediaRendering { 349 /** 350 * Resize to fit the output video with changing the aspect ratio if 351 * needed. 352 */ 353 public static final int RESIZING = 0; 354 355 /** 356 * Crop the input video to fit it with the output video resolution. 357 **/ 358 public static final int CROPPING = 1; 359 360 /** 361 * Resize to fit the output video resolution but maintain the aspect 362 * ratio. This framing type adds black borders if needed. 363 */ 364 public static final int BLACK_BORDERS = 2; 365 } 366 367 /** 368 * Defines the results. 369 */ 370 public final class Result { 371 /** No error. result OK */ 372 public static final int NO_ERROR = 0; 373 374 /** File not found */ 375 public static final int ERR_FILE_NOT_FOUND = 1; 376 377 /** 378 * In case of UTF8 conversion, the size of the converted path will be 379 * more than the corresponding allocated buffer. 380 */ 381 public static final int ERR_BUFFER_OUT_TOO_SMALL = 2; 382 383 /** Invalid file type. */ 384 public static final int ERR_INVALID_FILE_TYPE = 3; 385 386 /** Invalid effect kind. */ 387 public static final int ERR_INVALID_EFFECT_KIND = 4; 388 389 /** Invalid video effect. */ 390 public static final int ERR_INVALID_VIDEO_EFFECT_TYPE = 5; 391 392 /** Invalid audio effect. */ 393 public static final int ERR_INVALID_AUDIO_EFFECT_TYPE = 6; 394 395 /** Invalid video transition. */ 396 public static final int ERR_INVALID_VIDEO_TRANSITION_TYPE = 7; 397 398 /** Invalid audio transition. */ 399 public static final int ERR_INVALID_AUDIO_TRANSITION_TYPE = 8; 400 401 /** Invalid encoding frame rate. */ 402 public static final int ERR_INVALID_VIDEO_ENCODING_FRAME_RATE = 9; 403 404 /** External effect is called but this function is not set. */ 405 public static final int ERR_EXTERNAL_EFFECT_NULL = 10; 406 407 /** External transition is called but this function is not set. */ 408 public static final int ERR_EXTERNAL_TRANSITION_NULL = 11; 409 410 /** Begin time cut is larger than the video clip duration. */ 411 public static final int ERR_BEGIN_CUT_LARGER_THAN_DURATION = 12; 412 413 /** Begin cut time is larger or equal than end cut. */ 414 public static final int ERR_BEGIN_CUT_LARGER_THAN_END_CUT = 13; 415 416 /** Two consecutive transitions are overlapping on one clip. */ 417 public static final int ERR_OVERLAPPING_TRANSITIONS = 14; 418 419 /** Internal error, type size mismatch. */ 420 public static final int ERR_ANALYSIS_DATA_SIZE_TOO_SMALL = 15; 421 422 /** An input 3GPP file is invalid/corrupted. */ 423 public static final int ERR_INVALID_3GPP_FILE = 16; 424 425 /** A file contains an unsupported video format. */ 426 public static final int ERR_UNSUPPORTED_INPUT_VIDEO_FORMAT = 17; 427 428 /** A file contains an unsupported audio format. */ 429 public static final int ERR_UNSUPPORTED_INPUT_AUDIO_FORMAT = 18; 430 431 /** A file format is not supported. */ 432 public static final int ERR_AMR_EDITING_UNSUPPORTED = 19; 433 434 /** An input clip has an unexpectedly large Video AU. */ 435 public static final int ERR_INPUT_VIDEO_AU_TOO_LARGE = 20; 436 437 /** An input clip has an unexpectedly large Audio AU. */ 438 public static final int ERR_INPUT_AUDIO_AU_TOO_LARGE = 21; 439 440 /** An input clip has a corrupted Audio AU. */ 441 public static final int ERR_INPUT_AUDIO_CORRUPTED_AU = 22; 442 443 /** The video encoder encountered an Access Unit error. */ 444 public static final int ERR_ENCODER_ACCES_UNIT_ERROR = 23; 445 446 /** Unsupported video format for Video Editing. */ 447 public static final int ERR_EDITING_UNSUPPORTED_VIDEO_FORMAT = 24; 448 449 /** Unsupported H263 profile for Video Editing. */ 450 public static final int ERR_EDITING_UNSUPPORTED_H263_PROFILE = 25; 451 452 /** Unsupported MPEG-4 profile for Video Editing. */ 453 public static final int ERR_EDITING_UNSUPPORTED_MPEG4_PROFILE = 26; 454 455 /** Unsupported MPEG-4 RVLC tool for Video Editing. */ 456 public static final int ERR_EDITING_UNSUPPORTED_MPEG4_RVLC = 27; 457 458 /** Unsupported audio format for Video Editing. */ 459 public static final int ERR_EDITING_UNSUPPORTED_AUDIO_FORMAT = 28; 460 461 /** File contains no supported stream. */ 462 public static final int ERR_EDITING_NO_SUPPORTED_STREAM_IN_FILE = 29; 463 464 /** File contains no video stream or an unsupported video stream. */ 465 public static final int ERR_EDITING_NO_SUPPORTED_VIDEO_STREAM_IN_FILE = 30; 466 467 /** Internal error, clip analysis version mismatch. */ 468 public static final int ERR_INVALID_CLIP_ANALYSIS_VERSION = 31; 469 470 /** 471 * At least one of the clip analysis has been generated on another 472 * platform (WIN32, ARM, etc.). 473 */ 474 public static final int ERR_INVALID_CLIP_ANALYSIS_PLATFORM = 32; 475 476 /** Clips don't have the same video format (H263 or MPEG4). */ 477 public static final int ERR_INCOMPATIBLE_VIDEO_FORMAT = 33; 478 479 /** Clips don't have the same frame size. */ 480 public static final int ERR_INCOMPATIBLE_VIDEO_FRAME_SIZE = 34; 481 482 /** Clips don't have the same MPEG-4 time scale. */ 483 public static final int ERR_INCOMPATIBLE_VIDEO_TIME_SCALE = 35; 484 485 /** Clips don't have the same use of MPEG-4 data partitioning. */ 486 public static final int ERR_INCOMPATIBLE_VIDEO_DATA_PARTITIONING = 36; 487 488 /** MP3 clips can't be assembled. */ 489 public static final int ERR_UNSUPPORTED_MP3_ASSEMBLY = 37; 490 491 /** 492 * The input 3GPP file does not contain any supported audio or video 493 * track. 494 */ 495 public static final int ERR_NO_SUPPORTED_STREAM_IN_FILE = 38; 496 497 /** 498 * The Volume of the added audio track (AddVolume) must be strictly 499 * superior than zero. 500 */ 501 public static final int ERR_ADDVOLUME_EQUALS_ZERO = 39; 502 503 /** 504 * The time at which an audio track is added can't be higher than the 505 * input video track duration.. 506 */ 507 public static final int ERR_ADDCTS_HIGHER_THAN_VIDEO_DURATION = 40; 508 509 /** The audio track file format setting is undefined. */ 510 public static final int ERR_UNDEFINED_AUDIO_TRACK_FILE_FORMAT = 41; 511 512 /** The added audio track stream has an unsupported format. */ 513 public static final int ERR_UNSUPPORTED_ADDED_AUDIO_STREAM = 42; 514 515 /** The audio mixing feature doesn't support the audio track type. */ 516 public static final int ERR_AUDIO_MIXING_UNSUPPORTED = 43; 517 518 /** The audio mixing feature doesn't support MP3 audio tracks. */ 519 public static final int ERR_AUDIO_MIXING_MP3_UNSUPPORTED = 44; 520 521 /** 522 * An added audio track limits the available features: uiAddCts must be 523 * 0 and bRemoveOriginal must be true. 524 */ 525 public static final int ERR_FEATURE_UNSUPPORTED_WITH_AUDIO_TRACK = 45; 526 527 /** 528 * An added audio track limits the available features: uiAddCts must be 529 * 0 and bRemoveOriginal must be true. 530 */ 531 public static final int ERR_FEATURE_UNSUPPORTED_WITH_AAC = 46; 532 533 /** Input audio track is not of a type that can be mixed with output. */ 534 public static final int ERR_AUDIO_CANNOT_BE_MIXED = 47; 535 536 /** Input audio track is not AMR-NB, so it can't be mixed with output. */ 537 public static final int ERR_ONLY_AMRNB_INPUT_CAN_BE_MIXED = 48; 538 539 /** 540 * An added EVRC audio track limit the available features: uiAddCts must 541 * be 0 and bRemoveOriginal must be true. 542 */ 543 public static final int ERR_FEATURE_UNSUPPORTED_WITH_EVRC = 49; 544 545 /** H263 profiles other than 0 are not supported. */ 546 public static final int ERR_H263_PROFILE_NOT_SUPPORTED = 51; 547 548 /** File contains no video stream or an unsupported video stream. */ 549 public static final int ERR_NO_SUPPORTED_VIDEO_STREAM_IN_FILE = 52; 550 551 /** Transcoding of the input file(s) is necessary. */ 552 public static final int WAR_TRANSCODING_NECESSARY = 53; 553 554 /** 555 * The size of the output file will exceed the maximum configured value. 556 */ 557 public static final int WAR_MAX_OUTPUT_SIZE_EXCEEDED = 54; 558 559 /** The time scale is too big. */ 560 public static final int WAR_TIMESCALE_TOO_BIG = 55; 561 562 /** The year is out of range */ 563 public static final int ERR_CLOCK_BAD_REF_YEAR = 56; 564 565 /** The directory could not be opened */ 566 public static final int ERR_DIR_OPEN_FAILED = 57; 567 568 /** The directory could not be read */ 569 public static final int ERR_DIR_READ_FAILED = 58; 570 571 /** There are no more entries in the current directory */ 572 public static final int ERR_DIR_NO_MORE_ENTRY = 59; 573 574 /** The input parameter/s has error */ 575 public static final int ERR_PARAMETER = 60; 576 577 /** There is a state machine error */ 578 public static final int ERR_STATE = 61; 579 580 /** Memory allocation failed */ 581 public static final int ERR_ALLOC = 62; 582 583 /** Context is invalid */ 584 public static final int ERR_BAD_CONTEXT = 63; 585 586 /** Context creation failed */ 587 public static final int ERR_CONTEXT_FAILED = 64; 588 589 /** Invalid stream ID */ 590 public static final int ERR_BAD_STREAM_ID = 65; 591 592 /** Invalid option ID */ 593 public static final int ERR_BAD_OPTION_ID = 66; 594 595 /** The option is write only */ 596 public static final int ERR_WRITE_ONLY = 67; 597 598 /** The option is read only */ 599 public static final int ERR_READ_ONLY = 68; 600 601 /** The feature is not implemented in this version */ 602 public static final int ERR_NOT_IMPLEMENTED = 69; 603 604 /** The media type is not supported */ 605 public static final int ERR_UNSUPPORTED_MEDIA_TYPE = 70; 606 607 /** No data to be encoded */ 608 public static final int WAR_NO_DATA_YET = 71; 609 610 /** No data to be decoded */ 611 public static final int WAR_NO_MORE_STREAM = 72; 612 613 /** Time stamp is invalid */ 614 public static final int WAR_INVALID_TIME = 73; 615 616 /** No more data to be decoded */ 617 public static final int WAR_NO_MORE_AU = 74; 618 619 /** Semaphore timed out */ 620 public static final int WAR_TIME_OUT = 75; 621 622 /** Memory buffer is full */ 623 public static final int WAR_BUFFER_FULL = 76; 624 625 /** Server has asked for redirection */ 626 public static final int WAR_REDIRECT = 77; 627 628 /** Too many streams in input */ 629 public static final int WAR_TOO_MUCH_STREAMS = 78; 630 631 /** The file cannot be opened/ written into as it is locked */ 632 public static final int ERR_FILE_LOCKED = 79; 633 634 /** The file access mode is invalid */ 635 public static final int ERR_FILE_BAD_MODE_ACCESS = 80; 636 637 /** The file pointer points to an invalid location */ 638 public static final int ERR_FILE_INVALID_POSITION = 81; 639 640 /** Invalid string */ 641 public static final int ERR_STR_BAD_STRING = 94; 642 643 /** The input string cannot be converted */ 644 public static final int ERR_STR_CONV_FAILED = 95; 645 646 /** The string size is too large */ 647 public static final int ERR_STR_OVERFLOW = 96; 648 649 /** Bad string arguments */ 650 public static final int ERR_STR_BAD_ARGS = 97; 651 652 /** The string value is larger than maximum size allowed */ 653 public static final int WAR_STR_OVERFLOW = 98; 654 655 /** The string value is not present in this comparison operation */ 656 public static final int WAR_STR_NOT_FOUND = 99; 657 658 /** The thread is not started */ 659 public static final int ERR_THREAD_NOT_STARTED = 100; 660 661 /** Trancoding done warning */ 662 public static final int WAR_TRANSCODING_DONE = 101; 663 664 /** Unsupported mediatype */ 665 public static final int WAR_MEDIATYPE_NOT_SUPPORTED = 102; 666 667 /** Input file contains invalid/unsupported streams */ 668 public static final int ERR_INPUT_FILE_CONTAINS_NO_SUPPORTED_STREAM = 103; 669 670 /** Invalid input file */ 671 public static final int ERR_INVALID_INPUT_FILE = 104; 672 673 /** Invalid output video format */ 674 public static final int ERR_UNDEFINED_OUTPUT_VIDEO_FORMAT = 105; 675 676 /** Invalid output video frame size */ 677 public static final int ERR_UNDEFINED_OUTPUT_VIDEO_FRAME_SIZE = 106; 678 679 /** Invalid output video frame rate */ 680 public static final int ERR_UNDEFINED_OUTPUT_VIDEO_FRAME_RATE = 107; 681 682 /** Invalid output audio format */ 683 public static final int ERR_UNDEFINED_OUTPUT_AUDIO_FORMAT = 108; 684 685 /** Invalid video frame size for H.263 */ 686 public static final int ERR_INVALID_VIDEO_FRAME_SIZE_FOR_H263 = 109; 687 688 /** Invalid video frame rate for H.263 */ 689 public static final int ERR_INVALID_VIDEO_FRAME_RATE_FOR_H263 = 110; 690 691 /** invalid playback duration */ 692 public static final int ERR_DURATION_IS_NULL = 111; 693 694 /** Invalid H.263 profile in file */ 695 public static final int ERR_H263_FORBIDDEN_IN_MP4_FILE = 112; 696 697 /** Invalid AAC sampling frequency */ 698 public static final int ERR_INVALID_AAC_SAMPLING_FREQUENCY = 113; 699 700 /** Audio conversion failure */ 701 public static final int ERR_AUDIO_CONVERSION_FAILED = 114; 702 703 /** Invalid trim start and end times */ 704 public static final int ERR_BEGIN_CUT_EQUALS_END_CUT = 115; 705 706 /** End time smaller than start time for trim */ 707 public static final int ERR_END_CUT_SMALLER_THAN_BEGIN_CUT = 116; 708 709 /** Output file size is small */ 710 public static final int ERR_MAXFILESIZE_TOO_SMALL = 117; 711 712 /** Output video bitrate is too low */ 713 public static final int ERR_VIDEOBITRATE_TOO_LOW = 118; 714 715 /** Output audio bitrate is too low */ 716 public static final int ERR_AUDIOBITRATE_TOO_LOW = 119; 717 718 /** Output video bitrate is too high */ 719 public static final int ERR_VIDEOBITRATE_TOO_HIGH = 120; 720 721 /** Output audio bitrate is too high */ 722 public static final int ERR_AUDIOBITRATE_TOO_HIGH = 121; 723 724 /** Output file size is too small */ 725 public static final int ERR_OUTPUT_FILE_SIZE_TOO_SMALL = 122; 726 727 /** Unknown stream type */ 728 public static final int ERR_READER_UNKNOWN_STREAM_TYPE = 123; 729 730 /** Invalid metadata in input stream */ 731 public static final int WAR_READER_NO_METADATA = 124; 732 733 /** Invalid file reader info warning */ 734 public static final int WAR_READER_INFORMATION_NOT_PRESENT = 125; 735 736 /** Warning to indicate the the writer is being stopped */ 737 public static final int WAR_WRITER_STOP_REQ = 131; 738 739 /** Video decoder failed to provide frame for transcoding */ 740 public static final int WAR_VIDEORENDERER_NO_NEW_FRAME = 132; 741 742 /** Video deblocking filter is not implemented */ 743 public static final int WAR_DEBLOCKING_FILTER_NOT_IMPLEMENTED = 133; 744 745 /** H.263 decoder profile not supported */ 746 public static final int ERR_DECODER_H263_PROFILE_NOT_SUPPORTED = 134; 747 748 /** The input file contains unsupported H.263 profile */ 749 public static final int ERR_DECODER_H263_NOT_BASELINE = 135; 750 751 /** There is no more space to store the output file */ 752 public static final int ERR_NOMORE_SPACE_FOR_FILE = 136; 753 754 /** Internal error. */ 755 public static final int ERR_INTERNAL = 255; 756 757 } 758 759 /** 760 * Defines output video formats. 761 */ 762 public final class VideoFormat { 763 /** No video present in output clip. Used to generate audio only clip */ 764 public static final int NO_VIDEO = 0; 765 766 /** H263 baseline format. */ 767 public static final int H263 = 1; 768 769 /** MPEG4 video Simple Profile format. */ 770 public static final int MPEG4 = 2; 771 772 /** MPEG4 video Simple Profile format with support for EMP. */ 773 public static final int MPEG4_EMP = 3; 774 775 /** H264 video */ 776 public static final int H264 = 4; 777 778 /** No transcoding. Output video format is same as input video format */ 779 public static final int NULL_VIDEO = 254; 780 781 /** Unsupported video format. */ 782 public static final int UNSUPPORTED = 255; 783 } 784 785 /** Defines video profiles and levels. */ 786 public final class VideoProfile { 787 /** MPEG4, Simple Profile, Level 0. */ 788 public static final int MPEG4_SP_LEVEL_0 = 0; 789 790 /** MPEG4, Simple Profile, Level 0B. */ 791 public static final int MPEG4_SP_LEVEL_0B = 1; 792 793 /** MPEG4, Simple Profile, Level 1. */ 794 public static final int MPEG4_SP_LEVEL_1 = 2; 795 796 /** MPEG4, Simple Profile, Level 2. */ 797 public static final int MPEG4_SP_LEVEL_2 = 3; 798 799 /** MPEG4, Simple Profile, Level 3. */ 800 public static final int MPEG4_SP_LEVEL_3 = 4; 801 802 /** H263, Profile 0, Level 10. */ 803 public static final int H263_PROFILE_0_LEVEL_10 = 5; 804 805 /** H263, Profile 0, Level 20. */ 806 public static final int H263_PROFILE_0_LEVEL_20 = 6; 807 808 /** H263, Profile 0, Level 30. */ 809 public static final int H263_PROFILE_0_LEVEL_30 = 7; 810 811 /** H263, Profile 0, Level 40. */ 812 public static final int H263_PROFILE_0_LEVEL_40 = 8; 813 814 /** H263, Profile 0, Level 45. */ 815 public static final int H263_PROFILE_0_LEVEL_45 = 9; 816 817 /** MPEG4, Simple Profile, Level 4A. */ 818 public static final int MPEG4_SP_LEVEL_4A = 10; 819 820 /** MPEG4, Simple Profile, Level 0. */ 821 public static final int MPEG4_SP_LEVEL_5 = 11; 822 823 /** H264, Profile 0, Level 1. */ 824 public static final int H264_PROFILE_0_LEVEL_1 = 12; 825 826 /** H264, Profile 0, Level 1b. */ 827 public static final int H264_PROFILE_0_LEVEL_1b = 13; 828 829 /** H264, Profile 0, Level 1.1 */ 830 public static final int H264_PROFILE_0_LEVEL_1_1 = 14; 831 832 /** H264, Profile 0, Level 1.2 */ 833 public static final int H264_PROFILE_0_LEVEL_1_2 = 15; 834 835 /** H264, Profile 0, Level 1.3 */ 836 public static final int H264_PROFILE_0_LEVEL_1_3 = 16; 837 838 /** H264, Profile 0, Level 2. */ 839 public static final int H264_PROFILE_0_LEVEL_2 = 17; 840 841 /** H264, Profile 0, Level 2.1 */ 842 public static final int H264_PROFILE_0_LEVEL_2_1 = 18; 843 844 /** H264, Profile 0, Level 2.2 */ 845 public static final int H264_PROFILE_0_LEVEL_2_2 = 19; 846 847 /** H264, Profile 0, Level 3. */ 848 public static final int H264_PROFILE_0_LEVEL_3 = 20; 849 850 /** H264, Profile 0, Level 3.1 */ 851 public static final int H264_PROFILE_0_LEVEL_3_1 = 21; 852 853 /** H264, Profile 0, Level 3.2 */ 854 public static final int H264_PROFILE_0_LEVEL_3_2 = 22; 855 856 /** H264, Profile 0, Level 4. */ 857 public static final int H264_PROFILE_0_LEVEL_4 = 23; 858 859 /** H264, Profile 0, Level 4.1 */ 860 public static final int H264_PROFILE_0_LEVEL_4_1 = 24; 861 862 /** H264, Profile 0, Level 4.2 */ 863 public static final int H264_PROFILE_0_LEVEL_4_2 = 25; 864 865 /** H264, Profile 0, Level 5. */ 866 public static final int H264_PROFILE_0_LEVEL_5 = 26; 867 868 /** H264, Profile 0, Level 5.1 */ 869 public static final int H264_PROFILE_0_LEVEL_5_1 = 27; 870 871 /** Profile out of range. */ 872 public static final int OUT_OF_RANGE = 255; 873 } 874 875 /** Defines video frame sizes. */ 876 public final class VideoFrameSize { 877 878 public static final int SIZE_UNDEFINED = -1; 879 880 /** SQCIF 128 x 96 pixels. */ 881 public static final int SQCIF = 0; 882 883 /** QQVGA 160 x 120 pixels. */ 884 public static final int QQVGA = 1; 885 886 /** QCIF 176 x 144 pixels. */ 887 public static final int QCIF = 2; 888 889 /** QVGA 320 x 240 pixels. */ 890 public static final int QVGA = 3; 891 892 /** CIF 352 x 288 pixels. */ 893 public static final int CIF = 4; 894 895 /** VGA 640 x 480 pixels. */ 896 public static final int VGA = 5; 897 898 /** WVGA 800 X 480 pixels */ 899 public static final int WVGA = 6; 900 901 /** NTSC 720 X 480 pixels */ 902 public static final int NTSC = 7; 903 904 /** 640 x 360 */ 905 public static final int nHD = 8; 906 907 /** 854 x 480 */ 908 public static final int WVGA16x9 = 9; 909 910 /** 720p 1280 X 720 */ 911 public static final int V720p = 10; 912 913 /** 1080 x 720 */ 914 public static final int W720p = 11; 915 916 /** 1080 960 x 720 */ 917 public static final int S720p = 12; 918 } 919 920 /** 921 * Defines output video frame rates. 922 */ 923 public final class VideoFrameRate { 924 /** Frame rate of 5 frames per second. */ 925 public static final int FR_5_FPS = 0; 926 927 /** Frame rate of 7.5 frames per second. */ 928 public static final int FR_7_5_FPS = 1; 929 930 /** Frame rate of 10 frames per second. */ 931 public static final int FR_10_FPS = 2; 932 933 /** Frame rate of 12.5 frames per second. */ 934 public static final int FR_12_5_FPS = 3; 935 936 /** Frame rate of 15 frames per second. */ 937 public static final int FR_15_FPS = 4; 938 939 /** Frame rate of 20 frames per second. */ 940 public static final int FR_20_FPS = 5; 941 942 /** Frame rate of 25 frames per second. */ 943 public static final int FR_25_FPS = 6; 944 945 /** Frame rate of 30 frames per second. */ 946 public static final int FR_30_FPS = 7; 947 } 948 949 /** 950 * Defines Video Effect Types. 951 */ 952 public static class VideoEffect { 953 954 public static final int NONE = 0; 955 956 public static final int FADE_FROM_BLACK = 8; 957 958 public static final int CURTAIN_OPENING = 9; 959 960 public static final int FADE_TO_BLACK = 16; 961 962 public static final int CURTAIN_CLOSING = 17; 963 964 public static final int EXTERNAL = 256; 965 966 public static final int BLACK_AND_WHITE = 257; 967 968 public static final int PINK = 258; 969 970 public static final int GREEN = 259; 971 972 public static final int SEPIA = 260; 973 974 public static final int NEGATIVE = 261; 975 976 public static final int FRAMING = 262; 977 978 public static final int TEXT = 263; 979 980 public static final int ZOOM_IN = 264; 981 982 public static final int ZOOM_OUT = 265; 983 984 public static final int FIFTIES = 266; 985 986 public static final int COLORRGB16 = 267; 987 988 public static final int GRADIENT = 268; 989 } 990 991 /** 992 * Defines the video transitions. 993 */ 994 public static class VideoTransition { 995 /** No transition */ 996 public static final int NONE = 0; 997 998 /** Cross fade transition */ 999 public static final int CROSS_FADE = 1; 1000 1001 /** External transition. Currently not available. */ 1002 public static final int EXTERNAL = 256; 1003 1004 /** AlphaMagic transition. */ 1005 public static final int ALPHA_MAGIC = 257; 1006 1007 /** Slide transition. */ 1008 public static final int SLIDE_TRANSITION = 258; 1009 1010 /** Fade to black transition. */ 1011 public static final int FADE_BLACK = 259; 1012 } 1013 1014 /** 1015 * Defines settings for the AlphaMagic transition 1016 */ 1017 public static class AlphaMagicSettings { 1018 /** Name of the alpha file (JPEG file). */ 1019 public String file; 1020 1021 /** Blending percentage [0..100] 0 = no blending. */ 1022 public int blendingPercent; 1023 1024 /** Invert the default rotation direction of the AlphaMagic effect. */ 1025 public boolean invertRotation; 1026 1027 public int rgbWidth; 1028 public int rgbHeight; 1029 } 1030 1031 /** Defines the direction of the Slide transition. */ 1032 public static final class SlideDirection { 1033 1034 /** Right out left in. */ 1035 public static final int RIGHT_OUT_LEFT_IN = 0; 1036 1037 /** Left out right in. */ 1038 public static final int LEFT_OUT_RIGTH_IN = 1; 1039 1040 /** Top out bottom in. */ 1041 public static final int TOP_OUT_BOTTOM_IN = 2; 1042 1043 /** Bottom out top in */ 1044 public static final int BOTTOM_OUT_TOP_IN = 3; 1045 } 1046 1047 /** Defines the Slide transition settings. */ 1048 public static class SlideTransitionSettings { 1049 /** 1050 * Direction of the slide transition. See {@link SlideDirection 1051 * SlideDirection} for valid values. 1052 */ 1053 public int direction; 1054 } 1055 1056 /** 1057 * Defines the settings of a single clip. 1058 */ 1059 public static class ClipSettings { 1060 1061 /** 1062 * The path to the clip file. 1063 * <p> 1064 * File format of the clip, it can be: 1065 * <ul> 1066 * <li>3GP file containing MPEG4/H263/H264 video and AAC/AMR audio 1067 * <li>JPG file 1068 * </ul> 1069 */ 1070 1071 public String clipPath; 1072 1073 /** 1074 * The path of the decoded file. This is used only for image files. 1075 */ 1076 public String clipDecodedPath; 1077 1078 /** 1079 * The path of the Original file. This is used only for image files. 1080 */ 1081 public String clipOriginalPath; 1082 1083 /** 1084 * File type of the clip. See {@link FileType FileType} for valid 1085 * values. 1086 */ 1087 public int fileType; 1088 1089 /** Begin of the cut in the clip in milliseconds. */ 1090 public int beginCutTime; 1091 1092 /** 1093 * End of the cut in the clip in milliseconds. Set both 1094 * <code>beginCutTime</code> and <code>endCutTime</code> to 1095 * <code>0</code> to get the full length of the clip without a cut. In 1096 * case of JPG clip, this is the duration of the JPEG file. 1097 */ 1098 public int endCutTime; 1099 1100 /** 1101 * Begin of the cut in the clip in percentage of the file duration. 1102 */ 1103 public int beginCutPercent; 1104 1105 /** 1106 * End of the cut in the clip in percentage of the file duration. Set 1107 * both <code>beginCutPercent</code> and <code>endCutPercent</code> to 1108 * <code>0</code> to get the full length of the clip without a cut. 1109 */ 1110 public int endCutPercent; 1111 1112 /** Enable panning and zooming. */ 1113 public boolean panZoomEnabled; 1114 1115 /** Zoom percentage at start of clip. 0 = no zoom, 100 = full zoom */ 1116 public int panZoomPercentStart; 1117 1118 /** Top left X coordinate at start of clip. */ 1119 public int panZoomTopLeftXStart; 1120 1121 /** Top left Y coordinate at start of clip. */ 1122 public int panZoomTopLeftYStart; 1123 1124 /** Zoom percentage at start of clip. 0 = no zoom, 100 = full zoom */ 1125 public int panZoomPercentEnd; 1126 1127 /** Top left X coordinate at end of clip. */ 1128 public int panZoomTopLeftXEnd; 1129 1130 /** Top left Y coordinate at end of clip. */ 1131 public int panZoomTopLeftYEnd; 1132 1133 /** 1134 * Set The media rendering. See {@link MediaRendering MediaRendering} 1135 * for valid values. 1136 */ 1137 public int mediaRendering; 1138 1139 /** 1140 * RGB width and Height 1141 */ 1142 public int rgbWidth; 1143 public int rgbHeight; 1144 } 1145 1146 /** 1147 * Defines settings for a transition. 1148 */ 1149 public static class TransitionSettings { 1150 1151 /** Duration of the transition in msec. */ 1152 public int duration; 1153 1154 /** 1155 * Transition type for video. See {@link VideoTransition 1156 * VideoTransition} for valid values. 1157 */ 1158 public int videoTransitionType; 1159 1160 /** 1161 * Transition type for audio. See {@link AudioTransition 1162 * AudioTransition} for valid values. 1163 */ 1164 public int audioTransitionType; 1165 1166 /** 1167 * Transition behaviour. See {@link TransitionBehaviour 1168 * TransitionBehaviour} for valid values. 1169 */ 1170 public int transitionBehaviour; 1171 1172 /** 1173 * Settings for AlphaMagic transition. Only needs to be set if 1174 * <code>videoTransitionType</code> is set to 1175 * <code>VideoTransition.ALPHA_MAGIC</code>. See 1176 * {@link AlphaMagicSettings AlphaMagicSettings}. 1177 */ 1178 public AlphaMagicSettings alphaSettings; 1179 1180 /** 1181 * Settings for the Slide transition. See 1182 * {@link SlideTransitionSettings SlideTransitionSettings}. 1183 */ 1184 public SlideTransitionSettings slideSettings; 1185 } 1186 1187 public static final class AudioTransition { 1188 /** No audio transition. */ 1189 public static final int NONE = 0; 1190 1191 /** Cross-fade audio transition. */ 1192 public static final int CROSS_FADE = 1; 1193 } 1194 1195 /** 1196 * Defines transition behaviours. 1197 **/ 1198 1199 public static final class TransitionBehaviour { 1200 1201 /** The transition uses an increasing speed. */ 1202 public static final int SPEED_UP = 0; 1203 1204 /** The transition uses a linear (constant) speed. */ 1205 public static final int LINEAR = 1; 1206 1207 /** The transition uses a decreasing speed. */ 1208 public static final int SPEED_DOWN = 2; 1209 1210 /** 1211 * The transition uses a constant speed, but slows down in the middle 1212 * section. 1213 */ 1214 public static final int SLOW_MIDDLE = 3; 1215 1216 /** 1217 * The transition uses a constant speed, but increases speed in the 1218 * middle section. 1219 */ 1220 public static final int FAST_MIDDLE = 4; 1221 } 1222 1223 /** Defines settings for the background music. */ 1224 public static class BackgroundMusicSettings { 1225 1226 /** Background music file. */ 1227 public String file; 1228 1229 /** File type. See {@link FileType FileType} for valid values. */ 1230 public int fileType; 1231 1232 /** 1233 * Insertion time in milliseconds, in the output video where the 1234 * background music must be inserted. 1235 */ 1236 public long insertionTime; 1237 1238 /** 1239 * Volume, as a percentage of the background music track, to use. If 1240 * this field is set to 100, the background music will replace the audio 1241 * from the video input file(s). 1242 */ 1243 public int volumePercent; 1244 1245 /** 1246 * Start time in milliseconds in the background muisc file from where 1247 * the background music should loop. Set both <code>beginLoop</code> and 1248 * <code>endLoop</code> to <code>0</code> to disable looping. 1249 */ 1250 public long beginLoop; 1251 1252 /** 1253 * End time in milliseconds in the background music file to where the 1254 * background music should loop. Set both <code>beginLoop</code> and 1255 * <code>endLoop</code> to <code>0</code> to disable looping. 1256 */ 1257 public long endLoop; 1258 1259 public boolean enableDucking; 1260 1261 public int duckingThreshold; 1262 1263 public int lowVolume; 1264 1265 public boolean isLooping; 1266 1267 } 1268 1269 /** Defines settings for an effect. */ 1270 public static class AudioEffect { 1271 /** No audio effect. */ 1272 public static final int NONE = 0; 1273 1274 /** Fade-in effect. */ 1275 public static final int FADE_IN = 8; 1276 1277 /** Fade-out effect. */ 1278 public static final int FADE_OUT = 16; 1279 } 1280 1281 /** Defines the effect settings. */ 1282 public static class EffectSettings { 1283 1284 /** Start time of the effect in milliseconds. */ 1285 public int startTime; 1286 1287 /** Duration of the effect in milliseconds. */ 1288 public int duration; 1289 1290 /** 1291 * Video effect type. See {@link VideoEffect VideoEffect} for valid 1292 * values. 1293 */ 1294 public int videoEffectType; 1295 1296 /** 1297 * Audio effect type. See {@link AudioEffect AudioEffect} for valid 1298 * values. 1299 */ 1300 public int audioEffectType; 1301 1302 /** 1303 * Start time of the effect in percents of the duration of the clip. A 1304 * value of 0 percent means start time is from the beginning of the 1305 * clip. 1306 */ 1307 public int startPercent; 1308 1309 /** 1310 * Duration of the effect in percents of the duration of the clip. 1311 */ 1312 public int durationPercent; 1313 1314 /** 1315 * Framing file. 1316 * <p> 1317 * This field is only used when the field <code>videoEffectType</code> 1318 * is set to {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise 1319 * this field is ignored. 1320 */ 1321 public String framingFile; 1322 1323 /** 1324 * Framing buffer. 1325 * <p> 1326 * This field is only used when the field <code>videoEffectType</code> 1327 * is set to {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise 1328 * this field is ignored. 1329 */ 1330 public int[] framingBuffer; 1331 1332 /** 1333 * Bitmap type Can be from RGB_565 (4), ARGB_4444 (5), ARGB_8888 (6); 1334 **/ 1335 1336 public int bitmapType; 1337 1338 public int width; 1339 1340 public int height; 1341 1342 /** 1343 * Top left x coordinate. This coordinate is used to set the x 1344 * coordinate of the picture in the framing file when the framing file 1345 * is selected. The x coordinate is also used to set the location of the 1346 * text in the text effect. 1347 * <p> 1348 * This field is only used when the field <code>videoEffectType</code> 1349 * is set to {@link VideoEffect#FRAMING VideoEffect.FRAMING} or 1350 * {@link VideoEffect#TEXT VideoEffect.TEXT}. Otherwise this field is 1351 * ignored. 1352 */ 1353 public int topLeftX; 1354 1355 /** 1356 * Top left y coordinate. This coordinate is used to set the y 1357 * coordinate of the picture in the framing file when the framing file 1358 * is selected. The y coordinate is also used to set the location of the 1359 * text in the text effect. 1360 * <p> 1361 * This field is only used when the field <code>videoEffectType</code> 1362 * is set to {@link VideoEffect#FRAMING VideoEffect.FRAMING} or 1363 * {@link VideoEffect#TEXT VideoEffect.TEXT}. Otherwise this field is 1364 * ignored. 1365 */ 1366 public int topLeftY; 1367 1368 /** 1369 * Should the frame be resized or not. If this field is set to 1370 * <link>true</code> then the frame size is matched with the output 1371 * video size. 1372 * <p> 1373 * This field is only used when the field <code>videoEffectType</code> 1374 * is set to {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise 1375 * this field is ignored. 1376 */ 1377 public boolean framingResize; 1378 1379 /** 1380 * Size to which the framing buffer needs to be resized to 1381 * This is valid only if framingResize is true 1382 */ 1383 public int framingScaledSize; 1384 /** 1385 * Text to insert in the video. 1386 * <p> 1387 * This field is only used when the field <code>videoEffectType</code> 1388 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT}. Otherwise this 1389 * field is ignored. 1390 */ 1391 public String text; 1392 1393 /** 1394 * Text attributes for the text to insert in the video. 1395 * <p> 1396 * This field is only used when the field <code>videoEffectType</code> 1397 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT}. Otherwise this 1398 * field is ignored. For more details about this field see the 1399 * integration guide. 1400 */ 1401 public String textRenderingData; 1402 1403 /** Width of the text buffer in pixels. */ 1404 public int textBufferWidth; 1405 1406 /** Height of the text buffer in pixels. */ 1407 public int textBufferHeight; 1408 1409 /** 1410 * Processing rate for the fifties effect. A high value (e.g. 30) 1411 * results in high effect strength. 1412 * <p> 1413 * This field is only used when the field <code>videoEffectType</code> 1414 * is set to {@link VideoEffect#FIFTIES VideoEffect.FIFTIES}. Otherwise 1415 * this field is ignored. 1416 */ 1417 public int fiftiesFrameRate; 1418 1419 /** 1420 * RGB 16 color of the RGB16 and gradient color effect. 1421 * <p> 1422 * This field is only used when the field <code>videoEffectType</code> 1423 * is set to {@link VideoEffect#COLORRGB16 VideoEffect.COLORRGB16} or 1424 * {@link VideoEffect#GRADIENT VideoEffect.GRADIENT}. Otherwise this 1425 * field is ignored. 1426 */ 1427 public int rgb16InputColor; 1428 1429 /** 1430 * Start alpha blending percentage. 1431 * <p> 1432 * This field is only used when the field <code>videoEffectType</code> 1433 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT} or 1434 * {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise this field 1435 * is ignored. 1436 */ 1437 public int alphaBlendingStartPercent; 1438 1439 /** 1440 * Middle alpha blending percentage. 1441 * <p> 1442 * This field is only used when the field <code>videoEffectType</code> 1443 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT} or 1444 * {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise this field 1445 * is ignored. 1446 */ 1447 public int alphaBlendingMiddlePercent; 1448 1449 /** 1450 * End alpha blending percentage. 1451 * <p> 1452 * This field is only used when the field <code>videoEffectType</code> 1453 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT} or 1454 * {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise this field 1455 * is ignored. 1456 */ 1457 public int alphaBlendingEndPercent; 1458 1459 /** 1460 * Duration, in percentage of effect duration of the fade-in phase. 1461 * <p> 1462 * This field is only used when the field <code>videoEffectType</code> 1463 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT} or 1464 * {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise this field 1465 * is ignored. 1466 */ 1467 public int alphaBlendingFadeInTimePercent; 1468 1469 /** 1470 * Duration, in percentage of effect duration of the fade-out phase. 1471 * <p> 1472 * This field is only used when the field <code>videoEffectType</code> 1473 * is set to {@link VideoEffect#TEXT VideoEffect.TEXT} or 1474 * {@link VideoEffect#FRAMING VideoEffect.FRAMING}. Otherwise this field 1475 * is ignored. 1476 */ 1477 public int alphaBlendingFadeOutTimePercent; 1478 } 1479 1480 /** Defines the clip properties for preview */ 1481 public static class PreviewClips { 1482 1483 /** 1484 * The path to the clip file. 1485 * <p> 1486 * File format of the clip, it can be: 1487 * <ul> 1488 * <li>3GP file containing MPEG4/H263 video and AAC/AMR audio 1489 * <li>JPG file 1490 * </ul> 1491 */ 1492 1493 public String clipPath; 1494 1495 /** 1496 * File type of the clip. See {@link FileType FileType} for valid 1497 * values. 1498 */ 1499 public int fileType; 1500 1501 /** Begin of the cut in the clip in milliseconds. */ 1502 public long beginPlayTime; 1503 1504 public long endPlayTime; 1505 1506 /** 1507 * Set The media rendering. See {@link MediaRendering MediaRendering} 1508 * for valid values. 1509 */ 1510 public int mediaRendering; 1511 1512 } 1513 1514 /** Defines the audio settings. */ 1515 public static class AudioSettings { 1516 1517 String pFile; 1518 1519 /** < PCM file path */ 1520 String Id; 1521 1522 boolean bRemoveOriginal; 1523 1524 /** < If true, the original audio track is not taken into account */ 1525 int channels; 1526 1527 /** < Number of channels (1=mono, 2=stereo) of BGM clip */ 1528 int Fs; 1529 1530 /** 1531 * < Sampling audio frequency (8000 for amr, 16000 or more for aac) of 1532 * BGM clip 1533 */ 1534 int ExtendedFs; 1535 1536 /** < Extended frequency for AAC+, eAAC+ streams of BGM clip */ 1537 long startMs; 1538 1539 /** < Time, in milliseconds, at which the added audio track is inserted */ 1540 long beginCutTime; 1541 1542 long endCutTime; 1543 1544 int fileType; 1545 1546 int volume; 1547 1548 /** < Volume, in percentage, of the added audio track */ 1549 boolean loop; 1550 1551 /** < Looping on/off > **/ 1552 1553 /** Audio mix and Duck **/ 1554 int ducking_threshold; 1555 1556 int ducking_lowVolume; 1557 1558 boolean bInDucking_enable; 1559 1560 String pcmFilePath; 1561 1562 } 1563 1564 /** Encapsulates preview clips and effect settings */ 1565 public static class PreviewSettings { 1566 1567 public PreviewClips[] previewClipsArray; 1568 1569 /** The effect settings. */ 1570 public EffectSettings[] effectSettingsArray; 1571 1572 } 1573 1574 /** Encapsulates clip properties */ 1575 public static class PreviewClipProperties { 1576 1577 public Properties[] clipProperties; 1578 1579 } 1580 1581 /** Defines the editing settings. */ 1582 public static class EditSettings { 1583 1584 /** 1585 * Array of clip settings. There is one <code>clipSetting</code> for 1586 * each clip. 1587 */ 1588 public ClipSettings[] clipSettingsArray; 1589 1590 /** 1591 * Array of transition settings. If there are n clips (and thus n 1592 * <code>clipSettings</code>) then there are (n-1) transitions and (n-1) 1593 * <code>transistionSettings</code> in 1594 * <code>transistionSettingsArray</code>. 1595 */ 1596 public TransitionSettings[] transitionSettingsArray; 1597 1598 /** The effect settings. */ 1599 public EffectSettings[] effectSettingsArray; 1600 1601 /** 1602 * Video frame rate of the output clip. See {@link VideoFrameRate 1603 * VideoFrameRate} for valid values. 1604 */ 1605 public int videoFrameRate; 1606 1607 /** Output file name. Must be an absolute path. */ 1608 public String outputFile; 1609 1610 /** 1611 * Size of the video frames in the output clip. See 1612 * {@link VideoFrameSize VideoFrameSize} for valid values. 1613 */ 1614 public int videoFrameSize; 1615 1616 /** 1617 * Format of the video stream in the output clip. See 1618 * {@link VideoFormat VideoFormat} for valid values. 1619 */ 1620 public int videoFormat; 1621 1622 /** 1623 * Format of the audio stream in the output clip. See 1624 * {@link AudioFormat AudioFormat} for valid values. 1625 */ 1626 public int audioFormat; 1627 1628 /** 1629 * Sampling frequency of the audio stream in the output clip. See 1630 * {@link AudioSamplingFrequency AudioSamplingFrequency} for valid 1631 * values. 1632 */ 1633 public int audioSamplingFreq; 1634 1635 /** 1636 * Maximum file size. By setting this you can set the maximum size of 1637 * the output clip. Set it to <code>0</code> to let the class ignore 1638 * this filed. 1639 */ 1640 public int maxFileSize; 1641 1642 /** 1643 * Number of audio channels in output clip. Use <code>0</code> for none, 1644 * <code>1</code> for mono or <code>2</code> for stereo. None is only 1645 * allowed when the <code>audioFormat</code> field is set to 1646 * {@link AudioFormat#NO_AUDIO AudioFormat.NO_AUDIO} or 1647 * {@link AudioFormat#NULL_AUDIO AudioFormat.NULL_AUDIO} Mono is only 1648 * allowed when the <code>audioFormat</code> field is set to 1649 * {@link AudioFormat#AAC AudioFormat.AAC} 1650 */ 1651 public int audioChannels; 1652 1653 /** Video bitrate. See {@link Bitrate Bitrate} for valid values. */ 1654 public int videoBitrate; 1655 1656 /** Audio bitrate. See {@link Bitrate Bitrate} for valid values. */ 1657 public int audioBitrate; 1658 1659 /** 1660 * Background music settings. See {@link BackgroundMusicSettings 1661 * BackgroundMusicSettings} for valid values. 1662 */ 1663 public BackgroundMusicSettings backgroundMusicSettings; 1664 1665 public int primaryTrackVolume; 1666 1667 } 1668 1669 /** 1670 * Defines the media properties. 1671 **/ 1672 1673 public static class Properties { 1674 1675 /** 1676 * Duration of the media in milliseconds. 1677 */ 1678 1679 public int duration; 1680 1681 /** 1682 * File type. 1683 */ 1684 1685 public int fileType; 1686 1687 /** 1688 * Video format. 1689 */ 1690 1691 public int videoFormat; 1692 1693 /** 1694 * Duration of the video stream of the media in milliseconds. 1695 */ 1696 1697 public int videoDuration; 1698 1699 /** 1700 * Bitrate of the video stream of the media. 1701 */ 1702 1703 public int videoBitrate; 1704 1705 /** 1706 * Width of the video frames or the width of the still picture in 1707 * pixels. 1708 */ 1709 1710 public int width; 1711 1712 /** 1713 * Height of the video frames or the height of the still picture in 1714 * pixels. 1715 */ 1716 1717 public int height; 1718 1719 /** 1720 * Average frame rate of video in the media in frames per second. 1721 */ 1722 1723 public float averageFrameRate; 1724 1725 /** 1726 * Profile and level of the video in the media. 1727 */ 1728 1729 public int profileAndLevel; 1730 1731 /** 1732 * Audio format. 1733 */ 1734 1735 public int audioFormat; 1736 1737 /** 1738 * Duration of the audio stream of the media in milliseconds. 1739 */ 1740 1741 public int audioDuration; 1742 1743 /** 1744 * Bitrate of the audio stream of the media. 1745 */ 1746 1747 public int audioBitrate; 1748 1749 /** 1750 * Number of audio channels in the media. 1751 */ 1752 1753 public int audioChannels; 1754 1755 /** 1756 * Sampling frequency of the audio stream in the media in samples per 1757 * second. 1758 */ 1759 1760 public int audioSamplingFrequency; 1761 1762 /** 1763 * Volume value of the audio track as percentage. 1764 */ 1765 public int audioVolumeValue; 1766 1767 public String Id; 1768 1769 } 1770 1771 /** 1772 * Constructor 1773 * 1774 * @param projectPath The path where the VideoEditor stores all files 1775 * related to the project 1776 * @param veObj The video editor reference 1777 */ 1778 public MediaArtistNativeHelper(String projectPath, VideoEditor veObj) { 1779 mProjectPath = projectPath; 1780 if (veObj != null) { 1781 mVideoEditor = veObj; 1782 } else { 1783 mVideoEditor = null; 1784 throw new IllegalArgumentException("video editor object is null"); 1785 } 1786 if (mStoryBoardSettings == null) 1787 mStoryBoardSettings = new EditSettings(); 1788 1789 mMediaEffectList = new ArrayList<Effect>(); 1790 mMediaOverLayList = new ArrayList<Overlay>(); 1791 _init(mProjectPath, "null"); 1792 mAudioTrackPCMFilePath = null; 1793 } 1794 1795 /** 1796 * @return The project path 1797 */ 1798 String getProjectPath() { 1799 return mProjectPath; 1800 } 1801 1802 /** 1803 * @return The Audio Track PCM file path 1804 */ 1805 String getProjectAudioTrackPCMFilePath() { 1806 return mAudioTrackPCMFilePath; 1807 } 1808 1809 /** 1810 * Invalidates the PCM file 1811 */ 1812 void invalidatePcmFile() { 1813 if (mAudioTrackPCMFilePath != null) { 1814 new File(mAudioTrackPCMFilePath).delete(); 1815 mAudioTrackPCMFilePath = null; 1816 } 1817 } 1818 1819 @SuppressWarnings("unused") 1820 private void onProgressUpdate(int taskId, int progress) { 1821 if (mProcessingState == PROCESSING_EXPORT) { 1822 if (mExportProgressListener != null) { 1823 if (mProgressToApp < progress) { 1824 mExportProgressListener.onProgress(mVideoEditor, mOutputFilename, progress); 1825 /* record previous progress */ 1826 mProgressToApp = progress; 1827 } 1828 } 1829 } 1830 else { 1831 // Adapt progress depending on current state 1832 int actualProgress = 0; 1833 int action = 0; 1834 1835 if (mProcessingState == PROCESSING_AUDIO_PCM) { 1836 action = MediaProcessingProgressListener.ACTION_DECODE; 1837 } else { 1838 action = MediaProcessingProgressListener.ACTION_ENCODE; 1839 } 1840 1841 switch (mProcessingState) { 1842 case PROCESSING_AUDIO_PCM: 1843 actualProgress = progress; 1844 break; 1845 case PROCESSING_TRANSITION: 1846 actualProgress = progress; 1847 break; 1848 case PROCESSING_KENBURNS: 1849 actualProgress = progress; 1850 break; 1851 case PROCESSING_INTERMEDIATE1: 1852 if ((progress == 0) && (mProgressToApp != 0)) { 1853 mProgressToApp = 0; 1854 } 1855 if ((progress != 0) || (mProgressToApp != 0)) { 1856 actualProgress = progress/4; 1857 } 1858 break; 1859 case PROCESSING_INTERMEDIATE2: 1860 if ((progress != 0) || (mProgressToApp != 0)) { 1861 actualProgress = 25 + progress/4; 1862 } 1863 break; 1864 case PROCESSING_INTERMEDIATE3: 1865 if ((progress != 0) || (mProgressToApp != 0)) { 1866 actualProgress = 50 + progress/2; 1867 } 1868 break; 1869 case PROCESSING_NONE: 1870 1871 default: 1872 Log.e("MediaArtistNativeHelper", "ERROR unexpected State=" + mProcessingState); 1873 return; 1874 } 1875 if ((mProgressToApp != actualProgress) && (actualProgress != 0)) { 1876 1877 mProgressToApp = actualProgress; 1878 1879 if (mMediaProcessingProgressListener != null) { 1880 // Send the progress indication 1881 mMediaProcessingProgressListener.onProgress(mProcessingObject, 1882 action, 1883 actualProgress); 1884 } 1885 } 1886 /* avoid 0 in next intermediate call */ 1887 if (mProgressToApp == 0) { 1888 if (mMediaProcessingProgressListener != null) { 1889 /* 1890 * Send the progress indication 1891 */ 1892 mMediaProcessingProgressListener.onProgress(mProcessingObject, 1893 action, 1894 actualProgress); 1895 } 1896 mProgressToApp = 1; 1897 } 1898 } 1899 } 1900 1901 @SuppressWarnings("unused") 1902 private void onPreviewProgressUpdate(int progress, boolean isFinished) { 1903 if (mPreviewProgressListener != null) { 1904 mPreviewProgressListener.onProgress(mVideoEditor, progress, isFinished); 1905 if (progress != 0) { 1906 mPreviewProgress = progress; 1907 } 1908 } 1909 } 1910 1911 /** 1912 * Release the native helper object 1913 */ 1914 public void releaseNativeHelper() { 1915 try { 1916 release(); 1917 } catch (IllegalStateException ex) { 1918 Log.e("MediaArtistNativeHelper", 1919 "Illegal State exeption caught in releaseNativeHelper"); 1920 throw ex; 1921 } catch (RuntimeException ex) { 1922 Log.e("MediaArtistNativeHelper", "Runtime exeption caught in releaseNativeHelper"); 1923 throw ex; 1924 } 1925 } 1926 1927 /** 1928 * Release the native helper to end the Audio Graph process 1929 */ 1930 @SuppressWarnings("unused") 1931 private void onAudioGraphExtractProgressUpdate(int progress, boolean isVideo) { 1932 1933 if ((mExtractAudioWaveformProgressListener != null) && (progress > 0)) 1934 { 1935 mExtractAudioWaveformProgressListener.onProgress(progress); 1936 } 1937 } 1938 1939 /** 1940 * Populates the Effect Settings in EffectSettings 1941 * 1942 * @param effects The reference of EffectColor 1943 * 1944 * @return The populated effect settings in EffectSettings 1945 * reference 1946 */ 1947 EffectSettings getEffectSettings(EffectColor effects) { 1948 EffectSettings effectSettings = new EffectSettings(); 1949 effectSettings.startTime = (int)effects.getStartTime(); 1950 effectSettings.duration = (int)effects.getDuration(); 1951 effectSettings.videoEffectType = getEffectColorType(effects); 1952 effectSettings.audioEffectType = 0; 1953 effectSettings.startPercent = 0; 1954 effectSettings.durationPercent = 0; 1955 effectSettings.framingFile = null; 1956 effectSettings.topLeftX = 0; 1957 effectSettings.topLeftY = 0; 1958 effectSettings.framingResize = false; 1959 effectSettings.text = null; 1960 effectSettings.textRenderingData = null; 1961 effectSettings.textBufferWidth = 0; 1962 effectSettings.textBufferHeight = 0; 1963 if (effects.getType() == EffectColor.TYPE_FIFTIES) { 1964 effectSettings.fiftiesFrameRate = 15; 1965 } else { 1966 effectSettings.fiftiesFrameRate = 0; 1967 } 1968 1969 if ((effectSettings.videoEffectType == VideoEffect.COLORRGB16) 1970 || (effectSettings.videoEffectType == VideoEffect.GRADIENT)) { 1971 effectSettings.rgb16InputColor = effects.getColor(); 1972 } 1973 1974 effectSettings.alphaBlendingStartPercent = 0; 1975 effectSettings.alphaBlendingMiddlePercent = 0; 1976 effectSettings.alphaBlendingEndPercent = 0; 1977 effectSettings.alphaBlendingFadeInTimePercent = 0; 1978 effectSettings.alphaBlendingFadeOutTimePercent = 0; 1979 return effectSettings; 1980 } 1981 1982 /** 1983 * Populates the Overlay Settings in EffectSettings 1984 * 1985 * @param overlay The reference of OverlayFrame 1986 * 1987 * @return The populated overlay settings in EffectSettings 1988 * reference 1989 */ 1990 EffectSettings getOverlaySettings(OverlayFrame overlay) { 1991 EffectSettings effectSettings = new EffectSettings(); 1992 Bitmap bitmap = null; 1993 1994 effectSettings.startTime = (int)overlay.getStartTime(); 1995 effectSettings.duration = (int)overlay.getDuration(); 1996 effectSettings.videoEffectType = VideoEffect.FRAMING; 1997 effectSettings.audioEffectType = 0; 1998 effectSettings.startPercent = 0; 1999 effectSettings.durationPercent = 0; 2000 effectSettings.framingFile = null; 2001 2002 if ((bitmap = overlay.getBitmap()) != null) { 2003 effectSettings.framingFile = overlay.getFilename(); 2004 2005 if (effectSettings.framingFile == null) { 2006 try { 2007 (overlay).save(mProjectPath); 2008 } catch (IOException e) { 2009 Log.e("MediaArtistNativeHelper","getOverlaySettings : File not found"); 2010 } 2011 effectSettings.framingFile = overlay.getFilename(); 2012 } 2013 if (bitmap.getConfig() == Bitmap.Config.ARGB_8888) 2014 effectSettings.bitmapType = 6; 2015 else if (bitmap.getConfig() == Bitmap.Config.ARGB_4444) 2016 effectSettings.bitmapType = 5; 2017 else if (bitmap.getConfig() == Bitmap.Config.RGB_565) 2018 effectSettings.bitmapType = 4; 2019 else if (bitmap.getConfig() == Bitmap.Config.ALPHA_8) 2020 throw new RuntimeException("Bitmap config not supported"); 2021 2022 effectSettings.width = bitmap.getWidth(); 2023 effectSettings.height = bitmap.getHeight(); 2024 effectSettings.framingBuffer = new int[effectSettings.width]; 2025 int tmp = 0; 2026 short maxAlpha = 0; 2027 short minAlpha = (short)0xFF; 2028 short alpha = 0; 2029 while (tmp < effectSettings.height) { 2030 bitmap.getPixels(effectSettings.framingBuffer, 0, 2031 effectSettings.width, 0, tmp, 2032 effectSettings.width, 1); 2033 for (int i = 0; i < effectSettings.width; i++) { 2034 alpha = (short)((effectSettings.framingBuffer[i] >> 24) & 0xFF); 2035 if (alpha > maxAlpha) { 2036 maxAlpha = alpha; 2037 } 2038 if (alpha < minAlpha) { 2039 minAlpha = alpha; 2040 } 2041 } 2042 tmp += 1; 2043 } 2044 alpha = (short)((maxAlpha + minAlpha) / 2); 2045 alpha = (short)((alpha * 100) / 256); 2046 effectSettings.alphaBlendingEndPercent = alpha; 2047 effectSettings.alphaBlendingMiddlePercent = alpha; 2048 effectSettings.alphaBlendingStartPercent = alpha; 2049 effectSettings.alphaBlendingFadeInTimePercent = 100; 2050 effectSettings.alphaBlendingFadeOutTimePercent = 100; 2051 effectSettings.framingBuffer = null; 2052 } 2053 2054 effectSettings.topLeftX = 0; 2055 effectSettings.topLeftY = 0; 2056 2057 effectSettings.framingResize = true; 2058 effectSettings.text = null; 2059 effectSettings.textRenderingData = null; 2060 effectSettings.textBufferWidth = 0; 2061 effectSettings.textBufferHeight = 0; 2062 effectSettings.fiftiesFrameRate = 0; 2063 effectSettings.rgb16InputColor = 0; 2064 int mediaItemHeight; 2065 int aspectRatio; 2066 if (overlay.getMediaItem() instanceof MediaImageItem) { 2067 if (((MediaImageItem)overlay.getMediaItem()).getGeneratedImageClip() != null) { 2068 //Kenburns was applied 2069 mediaItemHeight = ((MediaImageItem)overlay.getMediaItem()).getGeneratedClipHeight(); 2070 aspectRatio = getAspectRatio( 2071 ((MediaImageItem)overlay.getMediaItem()).getGeneratedClipWidth() 2072 , mediaItemHeight); 2073 } 2074 else { 2075 //For image get the scaled height. Aspect ratio would remain the same 2076 mediaItemHeight = ((MediaImageItem)overlay.getMediaItem()).getScaledHeight(); 2077 aspectRatio = overlay.getMediaItem().getAspectRatio(); 2078 effectSettings.framingResize = false; //since the image can be of odd size. 2079 } 2080 } else { 2081 aspectRatio = overlay.getMediaItem().getAspectRatio(); 2082 mediaItemHeight = overlay.getMediaItem().getHeight(); 2083 } 2084 effectSettings.framingScaledSize = findVideoResolution(aspectRatio, mediaItemHeight); 2085 return effectSettings; 2086 } 2087 2088 /** 2089 * Sets the audio regenerate flag 2090 * 2091 * @param flag The boolean to set the audio regenerate flag 2092 * 2093 */ 2094 void setAudioflag(boolean flag) { 2095 //check if the file exists. 2096 if (!(new File(String.format(mProjectPath + "/" + AUDIO_TRACK_PCM_FILE)).exists())) { 2097 flag = true; 2098 } 2099 mRegenerateAudio = flag; 2100 } 2101 2102 /** 2103 * Gets the audio regenerate flag 2104 * 2105 * @param return The boolean to get the audio regenerate flag 2106 * 2107 */ 2108 boolean getAudioflag() { 2109 return mRegenerateAudio; 2110 } 2111 2112 /** 2113 * Maps the average frame rate to one of the defined enum values 2114 * 2115 * @param averageFrameRate The average frame rate of video item 2116 * 2117 * @return The frame rate from one of the defined enum values 2118 */ 2119 public int GetClosestVideoFrameRate(int averageFrameRate) { 2120 if (averageFrameRate >= 25) { 2121 return VideoFrameRate.FR_30_FPS; 2122 } else if (averageFrameRate >= 20) { 2123 return VideoFrameRate.FR_25_FPS; 2124 } else if (averageFrameRate >= 15) { 2125 return VideoFrameRate.FR_20_FPS; 2126 } else if (averageFrameRate >= 12) { 2127 return VideoFrameRate.FR_15_FPS; 2128 } else if (averageFrameRate >= 10) { 2129 return VideoFrameRate.FR_12_5_FPS; 2130 } else if (averageFrameRate >= 7) { 2131 return VideoFrameRate.FR_10_FPS; 2132 } else if (averageFrameRate >= 5) { 2133 return VideoFrameRate.FR_7_5_FPS; 2134 } else { 2135 return -1; 2136 } 2137 } 2138 2139 /** 2140 * Helper function to adjust the effect or overlay start time 2141 * depending on the begin and end boundary time of meddia item 2142 */ 2143 public void adjustEffectsStartTimeAndDuration(EffectSettings lEffect, 2144 int beginCutTime, 2145 int endCutTime) { 2146 2147 int effectStartTime = 0; 2148 int effectDuration = 0; 2149 2150 /** 2151 * cbct -> clip begin cut time 2152 * cect -> clip end cut time 2153 **************************************** 2154 * | | 2155 * | cbct cect | 2156 * | <-1--> | | | 2157 * | <--|-2-> | | 2158 * | | <---3---> | | 2159 * | | <--|-4---> | 2160 * | | | <--5--> | 2161 * | <---|------6----|----> | 2162 * | | 2163 * < : effectStart 2164 * > : effectStart + effectDuration 2165 **************************************** 2166 **/ 2167 2168 /** 1 & 5 */ 2169 /** 2170 * Effect falls out side the trim duration. In such a case effects shall 2171 * not be applied. 2172 */ 2173 if ((lEffect.startTime > endCutTime) 2174 || ((lEffect.startTime + lEffect.duration) <= beginCutTime)) { 2175 2176 effectStartTime = 0; 2177 effectDuration = 0; 2178 2179 lEffect.startTime = effectStartTime; 2180 lEffect.duration = effectDuration; 2181 return; 2182 } 2183 2184 /** 2 */ 2185 if ((lEffect.startTime < beginCutTime) 2186 && ((lEffect.startTime + lEffect.duration) > beginCutTime) 2187 && ((lEffect.startTime + lEffect.duration) <= endCutTime)) { 2188 effectStartTime = 0; 2189 effectDuration = lEffect.duration; 2190 2191 effectDuration -= (beginCutTime - lEffect.startTime); 2192 lEffect.startTime = effectStartTime; 2193 lEffect.duration = effectDuration; 2194 return; 2195 } 2196 2197 /** 3 */ 2198 if ((lEffect.startTime >= beginCutTime) 2199 && ((lEffect.startTime + lEffect.duration) <= endCutTime)) { 2200 effectStartTime = lEffect.startTime - beginCutTime; 2201 lEffect.startTime = effectStartTime; 2202 lEffect.duration = lEffect.duration; 2203 return; 2204 } 2205 2206 /** 4 */ 2207 if ((lEffect.startTime >= beginCutTime) 2208 && ((lEffect.startTime + lEffect.duration) > endCutTime)) { 2209 effectStartTime = lEffect.startTime - beginCutTime; 2210 effectDuration = endCutTime - lEffect.startTime; 2211 lEffect.startTime = effectStartTime; 2212 lEffect.duration = effectDuration; 2213 return; 2214 } 2215 2216 /** 6 */ 2217 if ((lEffect.startTime < beginCutTime) 2218 && ((lEffect.startTime + lEffect.duration) > endCutTime)) { 2219 effectStartTime = 0; 2220 effectDuration = endCutTime - beginCutTime; 2221 lEffect.startTime = effectStartTime; 2222 lEffect.duration = effectDuration; 2223 return; 2224 } 2225 2226 } 2227 2228 /** 2229 * Generates the clip for preview or export 2230 * 2231 * @param editSettings The EditSettings reference for generating 2232 * a clip for preview or export 2233 * 2234 * @return error value 2235 */ 2236 public int generateClip(EditSettings editSettings) { 2237 int err = 0; 2238 2239 try { 2240 err = nativeGenerateClip(editSettings); 2241 } catch (IllegalArgumentException ex) { 2242 Log.e("MediaArtistNativeHelper","Illegal Argument exception in load settings"); 2243 return -1; 2244 } catch (IllegalStateException ex) { 2245 Log.e("MediaArtistNativeHelper","Illegal state exception in load settings"); 2246 return -1; 2247 } catch (RuntimeException ex) { 2248 Log.e("MediaArtistNativeHelper", "Runtime exception in load settings"); 2249 return -1; 2250 } 2251 return err; 2252 } 2253 2254 /** 2255 * Init function to initialise the ClipSettings reference to 2256 * default values 2257 * 2258 * @param lclipSettings The ClipSettings reference 2259 */ 2260 void initClipSettings(ClipSettings lclipSettings) { 2261 lclipSettings.clipPath = null; 2262 lclipSettings.clipDecodedPath = null; 2263 lclipSettings.clipOriginalPath = null; 2264 lclipSettings.fileType = 0; 2265 lclipSettings.endCutTime = 0; 2266 lclipSettings.beginCutTime = 0; 2267 lclipSettings.beginCutPercent = 0; 2268 lclipSettings.endCutPercent = 0; 2269 lclipSettings.panZoomEnabled = false; 2270 lclipSettings.panZoomPercentStart = 0; 2271 lclipSettings.panZoomTopLeftXStart = 0; 2272 lclipSettings.panZoomTopLeftYStart = 0; 2273 lclipSettings.panZoomPercentEnd = 0; 2274 lclipSettings.panZoomTopLeftXEnd = 0; 2275 lclipSettings.panZoomTopLeftYEnd = 0; 2276 lclipSettings.mediaRendering = 0; 2277 } 2278 2279 2280 /** 2281 * Populates the settings for generating an effect clip 2282 * 2283 * @param lMediaItem The media item for which the effect clip 2284 * needs to be generated 2285 * @param lclipSettings The ClipSettings reference containing 2286 * clips data 2287 * @param e The EditSettings reference containing effect specific data 2288 * @param uniqueId The unique id used in the name of the output clip 2289 * @param clipNo Used for internal purpose 2290 * 2291 * @return The name and path of generated clip 2292 */ 2293 String generateEffectClip(MediaItem lMediaItem, ClipSettings lclipSettings, 2294 EditSettings e,String uniqueId,int clipNo) { 2295 int err = 0; 2296 EditSettings editSettings = null; 2297 String EffectClipPath = null; 2298 2299 editSettings = new EditSettings(); 2300 2301 editSettings.clipSettingsArray = new ClipSettings[1]; 2302 editSettings.clipSettingsArray[0] = lclipSettings; 2303 2304 editSettings.backgroundMusicSettings = null; 2305 editSettings.transitionSettingsArray = null; 2306 editSettings.effectSettingsArray = e.effectSettingsArray; 2307 2308 EffectClipPath = String.format(mProjectPath + "/" + "ClipEffectIntermediate" + "_" 2309 + lMediaItem.getId() + uniqueId + ".3gp"); 2310 2311 File tmpFile = new File(EffectClipPath); 2312 if (tmpFile.exists()) { 2313 tmpFile.delete(); 2314 } 2315 2316 if (lMediaItem instanceof MediaVideoItem) { 2317 MediaVideoItem m = (MediaVideoItem)lMediaItem; 2318 2319 editSettings.audioFormat = AudioFormat.AAC; 2320 editSettings.audioChannels = 2; 2321 editSettings.audioBitrate = Bitrate.BR_64_KBPS; 2322 editSettings.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 2323 2324 editSettings.videoBitrate = Bitrate.BR_5_MBPS; 2325 //editSettings.videoFormat = VideoFormat.MPEG4; 2326 editSettings.videoFormat = VideoFormat.H264; 2327 editSettings.videoFrameRate = VideoFrameRate.FR_30_FPS; 2328 editSettings.videoFrameSize = findVideoResolution(mVideoEditor.getAspectRatio(), m 2329 .getHeight()); 2330 2331 } else { 2332 MediaImageItem m = (MediaImageItem)lMediaItem; 2333 editSettings.audioBitrate = Bitrate.BR_64_KBPS; 2334 editSettings.audioChannels = 2; 2335 editSettings.audioFormat = AudioFormat.AAC; 2336 editSettings.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 2337 2338 editSettings.videoBitrate = Bitrate.BR_5_MBPS; 2339 editSettings.videoFormat = VideoFormat.H264; 2340 editSettings.videoFrameRate = VideoFrameRate.FR_30_FPS; 2341 editSettings.videoFrameSize = findVideoResolution(mVideoEditor.getAspectRatio(), m 2342 .getScaledHeight()); 2343 } 2344 2345 editSettings.outputFile = EffectClipPath; 2346 2347 if (clipNo == 1) { 2348 mProcessingState = PROCESSING_INTERMEDIATE1; 2349 } else if (clipNo == 2) { 2350 mProcessingState = PROCESSING_INTERMEDIATE2; 2351 } 2352 mProcessingObject = lMediaItem; 2353 err = generateClip(editSettings); 2354 mProcessingState = PROCESSING_NONE; 2355 2356 if (err == 0) { 2357 lclipSettings.clipPath = EffectClipPath; 2358 lclipSettings.fileType = FileType.THREE_GPP; 2359 return EffectClipPath; 2360 } else { 2361 throw new RuntimeException("preview generation cannot be completed"); 2362 } 2363 } 2364 2365 2366 /** 2367 * Populates the settings for generating a Ken Burn effect clip 2368 * 2369 * @param m The media image item for which the Ken Burn effect clip 2370 * needs to be generated 2371 * @param e The EditSettings reference clip specific data 2372 * 2373 * @return The name and path of generated clip 2374 */ 2375 String generateKenBurnsClip(EditSettings e, MediaImageItem m) { 2376 String output = null; 2377 int err = 0; 2378 2379 e.backgroundMusicSettings = null; 2380 e.transitionSettingsArray = null; 2381 e.effectSettingsArray = null; 2382 output = String.format(mProjectPath + "/" + "ImageClip-" + m.getId() + ".3gp"); 2383 2384 File tmpFile = new File(output); 2385 if (tmpFile.exists()) { 2386 tmpFile.delete(); 2387 } 2388 2389 e.outputFile = output; 2390 e.audioBitrate = Bitrate.BR_64_KBPS; 2391 e.audioChannels = 2; 2392 e.audioFormat = AudioFormat.AAC; 2393 e.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 2394 2395 e.videoBitrate = Bitrate.BR_5_MBPS; 2396 e.videoFormat = VideoFormat.H264; 2397 e.videoFrameRate = VideoFrameRate.FR_30_FPS; 2398 e.videoFrameSize = findVideoResolution(mVideoEditor.getAspectRatio(), 2399 m.getScaledHeight()); 2400 mProcessingState = PROCESSING_KENBURNS; 2401 mProcessingObject = m; 2402 err = generateClip(e); 2403 // Reset the processing state and check for errors 2404 mProcessingState = PROCESSING_NONE; 2405 if (err != 0) { 2406 throw new RuntimeException("preview generation cannot be completed"); 2407 } 2408 return output; 2409 } 2410 2411 2412 /** 2413 * Calculates the output resolution for transition clip 2414 * 2415 * @param m1 First media item associated with transition 2416 * @param m2 Second media item associated with transition 2417 * 2418 * @return The transition resolution 2419 */ 2420 private int getTransitionResolution(MediaItem m1, MediaItem m2) { 2421 int clip1Height = 0; 2422 int clip2Height = 0; 2423 int videoSize = 0; 2424 2425 if (m1 != null && m2 != null) { 2426 if (m1 instanceof MediaVideoItem) { 2427 clip1Height = m1.getHeight(); 2428 } else if (m1 instanceof MediaImageItem) { 2429 clip1Height = ((MediaImageItem)m1).getScaledHeight(); 2430 } 2431 if (m2 instanceof MediaVideoItem) { 2432 clip2Height = m2.getHeight(); 2433 } else if (m2 instanceof MediaImageItem) { 2434 clip2Height = ((MediaImageItem)m2).getScaledHeight(); 2435 } 2436 if (clip1Height > clip2Height) { 2437 videoSize = findVideoResolution(mVideoEditor.getAspectRatio(), 2438 clip1Height); 2439 } else { 2440 videoSize = findVideoResolution(mVideoEditor.getAspectRatio(), 2441 clip2Height); 2442 } 2443 } else if (m1 == null && m2 != null) { 2444 if (m2 instanceof MediaVideoItem) { 2445 clip2Height = m2.getHeight(); 2446 } else if (m2 instanceof MediaImageItem) { 2447 clip2Height = ((MediaImageItem)m2).getScaledHeight(); 2448 } 2449 videoSize = findVideoResolution(mVideoEditor.getAspectRatio(), 2450 clip2Height); 2451 } else if (m1 != null && m2 == null) { 2452 if (m1 instanceof MediaVideoItem) { 2453 clip1Height = m1.getHeight(); 2454 } else if (m1 instanceof MediaImageItem) { 2455 clip1Height = ((MediaImageItem)m1).getScaledHeight(); 2456 } 2457 videoSize = findVideoResolution(mVideoEditor.getAspectRatio(), 2458 clip1Height); 2459 } 2460 return videoSize; 2461 } 2462 2463 /** 2464 * Populates the settings for generating an transition clip 2465 * 2466 * @param m1 First media item associated with transition 2467 * @param m2 Second media item associated with transition 2468 * @param e The EditSettings reference containing 2469 * clip specific data 2470 * @param uniqueId The unique id used in the name of the output clip 2471 * @param t The Transition specific data 2472 * 2473 * @return The name and path of generated clip 2474 */ 2475 String generateTransitionClip(EditSettings e, String uniqueId, 2476 MediaItem m1, MediaItem m2,Transition t) { 2477 String outputFilename = null; 2478 int err = 0; 2479 2480 outputFilename = String.format(mProjectPath + "/" + uniqueId + ".3gp"); 2481 e.outputFile = outputFilename; 2482 e.audioBitrate = Bitrate.BR_64_KBPS; 2483 e.audioChannels = 2; 2484 e.audioFormat = AudioFormat.AAC; 2485 e.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 2486 2487 e.videoBitrate = Bitrate.BR_5_MBPS; 2488 e.videoFormat = VideoFormat.H264; 2489 e.videoFrameRate = VideoFrameRate.FR_30_FPS; 2490 e.videoFrameSize = getTransitionResolution(m1, m2); 2491 2492 if (new File(outputFilename).exists()) { 2493 new File(outputFilename).delete(); 2494 } 2495 mProcessingState = PROCESSING_INTERMEDIATE3; 2496 mProcessingObject = t; 2497 err = generateClip(e); 2498 // Reset the processing state and check for errors 2499 mProcessingState = PROCESSING_NONE; 2500 if (err != 0) { 2501 throw new RuntimeException("preview generation cannot be completed"); 2502 } 2503 return outputFilename; 2504 } 2505 2506 /** 2507 * Populates effects and overlays in EffectSettings structure 2508 * and also adjust the start time and duration of effects and overlays 2509 * w.r.t to total story board time 2510 * 2511 * @param m1 Media item associated with effect 2512 * @param effectSettings The EffectSettings reference containing 2513 * effect specific data 2514 * @param beginCutTime The begin cut time of the clip associated with effect 2515 * @param endCutTime The end cut time of the clip associated with effect 2516 * @param storyBoardTime The current story board time 2517 * 2518 * @return The updated index 2519 */ 2520 private int populateEffects(MediaItem m, EffectSettings[] effectSettings, int i, 2521 int beginCutTime, int endCutTime, int storyBoardTime) { 2522 List<Effect> effects = m.getAllEffects(); 2523 List<Overlay> overlays = m.getAllOverlays(); 2524 2525 if (m.getBeginTransition() != null && m.getBeginTransition().getDuration() > 0 2526 && m.getEndTransition() != null && m.getEndTransition().getDuration() > 0) { 2527 beginCutTime += m.getBeginTransition().getDuration(); 2528 endCutTime -= m.getEndTransition().getDuration(); 2529 } else if (m.getBeginTransition() == null && m.getEndTransition() != null 2530 && m.getEndTransition().getDuration() > 0) { 2531 endCutTime -= m.getEndTransition().getDuration(); 2532 } else if (m.getEndTransition() == null && m.getBeginTransition() != null 2533 && m.getBeginTransition().getDuration() > 0) { 2534 beginCutTime += m.getBeginTransition().getDuration(); 2535 } 2536 2537 for (Effect effect : effects) { 2538 if (effect instanceof EffectColor) { 2539 effectSettings[i] = getEffectSettings((EffectColor)effect); 2540 adjustEffectsStartTimeAndDuration(effectSettings[i], 2541 beginCutTime, endCutTime); 2542 effectSettings[i].startTime += storyBoardTime; 2543 i++; 2544 } 2545 } 2546 for (Overlay overlay : overlays) { 2547 effectSettings[i] = getOverlaySettings((OverlayFrame)overlay); 2548 adjustEffectsStartTimeAndDuration(effectSettings[i], 2549 beginCutTime, endCutTime); 2550 effectSettings[i].startTime += storyBoardTime; 2551 i++; 2552 } 2553 return i; 2554 } 2555 2556 /** 2557 * Adjusts the media item boundaries for use in export or preview 2558 * 2559 * @param clipSettings The ClipSettings reference 2560 * @param clipProperties The Properties reference 2561 * @param m The media item 2562 */ 2563 private void adjustMediaItemBoundary(ClipSettings clipSettings, 2564 Properties clipProperties, MediaItem m) { 2565 if (m.getBeginTransition() != null && m.getBeginTransition().getDuration() > 0 2566 && m.getEndTransition() != null && m.getEndTransition().getDuration() > 0) { 2567 2568 clipSettings.beginCutTime += m.getBeginTransition().getDuration(); 2569 clipSettings.endCutTime -= m.getEndTransition().getDuration(); 2570 2571 } else if (m.getBeginTransition() == null && m.getEndTransition() != null 2572 && m.getEndTransition().getDuration() > 0) { 2573 2574 clipSettings.endCutTime -= m.getEndTransition().getDuration(); 2575 2576 } else if (m.getEndTransition() == null && m.getBeginTransition() != null 2577 && m.getBeginTransition().getDuration() > 0) { 2578 2579 clipSettings.beginCutTime += m.getBeginTransition().getDuration(); 2580 } 2581 clipProperties.duration = clipSettings.endCutTime - 2582 clipSettings.beginCutTime; 2583 2584 if (clipProperties.videoDuration != 0) { 2585 clipProperties.videoDuration = clipSettings.endCutTime - 2586 clipSettings.beginCutTime; 2587 } 2588 2589 if (clipProperties.audioDuration != 0) { 2590 clipProperties.audioDuration = clipSettings.endCutTime - 2591 clipSettings.beginCutTime; 2592 } 2593 } 2594 2595 /** 2596 * Generates the transition if transition is present 2597 * and is in invalidated state 2598 * 2599 * @param transition The Transition reference 2600 * @param editSettings The EditSettings reference 2601 * @param clipPropertiesArray The clip Properties array 2602 * @param i The index in clip Properties array for current clip 2603 */ 2604 private void generateTransition(Transition transition, EditSettings editSettings, 2605 PreviewClipProperties clipPropertiesArray, int index) { 2606 if (!(transition.isGenerated())) { 2607 transition.generate(); 2608 } 2609 editSettings.clipSettingsArray[index] = new ClipSettings(); 2610 editSettings.clipSettingsArray[index].clipPath = transition.getFilename(); 2611 editSettings.clipSettingsArray[index].fileType = FileType.THREE_GPP; 2612 editSettings.clipSettingsArray[index].beginCutTime = 0; 2613 editSettings.clipSettingsArray[index].endCutTime = 2614 (int)transition.getDuration(); 2615 editSettings.clipSettingsArray[index].mediaRendering = 2616 MediaRendering.BLACK_BORDERS; 2617 try { 2618 clipPropertiesArray.clipProperties[index] = 2619 getMediaProperties(transition.getFilename()); 2620 } catch (Exception e) { 2621 throw new IllegalArgumentException("Unsupported file or file not found"); 2622 } 2623 clipPropertiesArray.clipProperties[index].Id = null; 2624 clipPropertiesArray.clipProperties[index].audioVolumeValue = 100; 2625 clipPropertiesArray.clipProperties[index].duration = 2626 (int)transition.getDuration(); 2627 if (clipPropertiesArray.clipProperties[index].videoDuration != 0) { 2628 clipPropertiesArray.clipProperties[index].videoDuration = 2629 (int)transition.getDuration(); 2630 } 2631 if (clipPropertiesArray.clipProperties[index].audioDuration != 0) { 2632 clipPropertiesArray.clipProperties[index].audioDuration = 2633 (int)transition.getDuration(); 2634 } 2635 } 2636 2637 /** 2638 * Sets the volume for current media item in clip properties array 2639 * 2640 * @param m The media item 2641 * @param clipProperties The clip properties array reference 2642 * @param i The index in clip Properties array for current clip 2643 */ 2644 private void adjustVolume(MediaItem m, PreviewClipProperties clipProperties, 2645 int index) { 2646 if (m instanceof MediaVideoItem) { 2647 boolean videoMuted = ((MediaVideoItem)m).isMuted(); 2648 if (videoMuted == false) { 2649 mClipProperties.clipProperties[index].audioVolumeValue = ((MediaVideoItem)m) 2650 .getVolume(); 2651 } else { 2652 mClipProperties.clipProperties[index].audioVolumeValue = 0; 2653 } 2654 } else if (m instanceof MediaImageItem) { 2655 mClipProperties.clipProperties[index].audioVolumeValue = 0; 2656 } 2657 } 2658 2659 /** 2660 * Checks for odd size image width and height 2661 * 2662 * @param m The media item 2663 * @param clipProperties The clip properties array reference 2664 * @param i The index in clip Properties array for current clip 2665 */ 2666 private void checkOddSizeImage(MediaItem m, PreviewClipProperties clipProperties, int index) { 2667 if (m instanceof MediaImageItem) { 2668 int width = mClipProperties.clipProperties[index].width; 2669 int height = mClipProperties.clipProperties[index].height; 2670 2671 if ((width % 2) != 0) { 2672 width -= 1; 2673 } 2674 if ((height % 2) != 0) { 2675 height -= 1; 2676 } 2677 mClipProperties.clipProperties[index].width = width; 2678 mClipProperties.clipProperties[index].height = height; 2679 } 2680 } 2681 2682 /** 2683 * Populates the media item properties and calculates the maximum 2684 * height among all the clips 2685 * 2686 * @param m The media item 2687 * @param i The index in clip Properties array for current clip 2688 * @param maxHeight The max height from the clip properties 2689 * 2690 * @return Updates the max height if current clip's height is greater 2691 * than all previous clips height 2692 */ 2693 private int populateMediaItemProperties(MediaItem m, int index, int maxHeight) { 2694 mPreviewEditSettings.clipSettingsArray[index] = new ClipSettings(); 2695 if (m instanceof MediaVideoItem) { 2696 mPreviewEditSettings.clipSettingsArray[index] = ((MediaVideoItem)m) 2697 .getVideoClipProperties(); 2698 if (((MediaVideoItem)m).getHeight() > maxHeight) { 2699 maxHeight = ((MediaVideoItem)m).getHeight(); 2700 } 2701 } else if (m instanceof MediaImageItem) { 2702 mPreviewEditSettings.clipSettingsArray[index] = ((MediaImageItem)m) 2703 .getImageClipProperties(); 2704 if (((MediaImageItem)m).getScaledHeight() > maxHeight) { 2705 maxHeight = ((MediaImageItem)m).getScaledHeight(); 2706 } 2707 } 2708 /** + Handle the image files here */ 2709 if (mPreviewEditSettings.clipSettingsArray[index].fileType == FileType.JPG) { 2710 mPreviewEditSettings.clipSettingsArray[index].clipDecodedPath = ((MediaImageItem)m) 2711 .getDecodedImageFileName(); 2712 2713 mPreviewEditSettings.clipSettingsArray[index].clipOriginalPath = 2714 mPreviewEditSettings.clipSettingsArray[index].clipPath; 2715 } 2716 return maxHeight; 2717 } 2718 2719 /** 2720 * Populates the background music track properties 2721 * 2722 * @param mediaBGMList The background music list 2723 * 2724 */ 2725 private void populateBackgroundMusicProperties(List<AudioTrack> mediaBGMList) { 2726 2727 if (mediaBGMList.size() == 1) { 2728 mAudioTrack = mediaBGMList.get(0); 2729 } else 2730 { 2731 mAudioTrack = null; 2732 } 2733 2734 if (mAudioTrack != null) { 2735 mAudioSettings = new AudioSettings(); 2736 Properties mAudioProperties = new Properties(); 2737 mAudioSettings.pFile = null; 2738 mAudioSettings.Id = mAudioTrack.getId(); 2739 try { 2740 mAudioProperties = getMediaProperties(mAudioTrack.getFilename()); 2741 } catch (Exception e) { 2742 throw new IllegalArgumentException("Unsupported file or file not found"); 2743 } 2744 mAudioSettings.bRemoveOriginal = false; 2745 mAudioSettings.channels = mAudioProperties.audioChannels; 2746 mAudioSettings.Fs = mAudioProperties.audioSamplingFrequency; 2747 mAudioSettings.loop = mAudioTrack.isLooping(); 2748 mAudioSettings.ExtendedFs = 0; 2749 mAudioSettings.pFile = mAudioTrack.getFilename(); 2750 mAudioSettings.startMs = mAudioTrack.getStartTime(); 2751 mAudioSettings.beginCutTime = mAudioTrack.getBoundaryBeginTime(); 2752 mAudioSettings.endCutTime = mAudioTrack.getBoundaryEndTime(); 2753 if (mAudioTrack.isMuted()) { 2754 mAudioSettings.volume = 0; 2755 } else { 2756 mAudioSettings.volume = mAudioTrack.getVolume(); 2757 } 2758 mAudioSettings.fileType = mAudioProperties.fileType; 2759 mAudioSettings.ducking_lowVolume = mAudioTrack.getDuckedTrackVolume(); 2760 mAudioSettings.ducking_threshold = mAudioTrack.getDuckingThreshhold(); 2761 mAudioSettings.bInDucking_enable = mAudioTrack.isDuckingEnabled(); 2762 mAudioTrackPCMFilePath = String.format(mProjectPath + "/" + AUDIO_TRACK_PCM_FILE); 2763 //String.format(mProjectPath + "/" + "AudioPcm" + ".pcm"); 2764 mAudioSettings.pcmFilePath = mAudioTrackPCMFilePath; 2765 2766 mPreviewEditSettings.backgroundMusicSettings = 2767 new BackgroundMusicSettings(); 2768 mPreviewEditSettings.backgroundMusicSettings.file = 2769 mAudioTrackPCMFilePath; 2770 mPreviewEditSettings.backgroundMusicSettings.fileType = 2771 mAudioProperties.fileType; 2772 mPreviewEditSettings.backgroundMusicSettings.insertionTime = 2773 mAudioTrack.getStartTime(); 2774 mPreviewEditSettings.backgroundMusicSettings.volumePercent = 2775 mAudioTrack.getVolume(); 2776 mPreviewEditSettings.backgroundMusicSettings.beginLoop = mAudioTrack 2777 .getBoundaryBeginTime(); 2778 mPreviewEditSettings.backgroundMusicSettings.endLoop = 2779 mAudioTrack.getBoundaryEndTime(); 2780 mPreviewEditSettings.backgroundMusicSettings.enableDucking = mAudioTrack 2781 .isDuckingEnabled(); 2782 mPreviewEditSettings.backgroundMusicSettings.duckingThreshold = mAudioTrack 2783 .getDuckingThreshhold(); 2784 mPreviewEditSettings.backgroundMusicSettings.lowVolume = mAudioTrack 2785 .getDuckedTrackVolume(); 2786 mPreviewEditSettings.backgroundMusicSettings.isLooping = 2787 mAudioTrack.isLooping(); 2788 mPreviewEditSettings.primaryTrackVolume = 100; 2789 mProcessingState = PROCESSING_AUDIO_PCM; 2790 mProcessingObject = mAudioTrack; 2791 } else { 2792 if (mAudioSettings != null) { 2793 mAudioSettings = null; 2794 } 2795 if (mPreviewEditSettings.backgroundMusicSettings != null) { 2796 mPreviewEditSettings.backgroundMusicSettings = null; 2797 } 2798 mAudioTrackPCMFilePath = null; 2799 } 2800 } 2801 2802 /** 2803 * Calculates all the effects in all the media items 2804 * in media items list 2805 * 2806 * @param mediaItemsList The media item list 2807 * 2808 * @return The total number of effects 2809 * 2810 */ 2811 private int getTotalEffects(List<MediaItem> mediaItemsList) { 2812 int totalEffects = 0; 2813 final Iterator<MediaItem> it = mediaItemsList.iterator(); 2814 while (it.hasNext()) { 2815 final MediaItem t = it.next(); 2816 totalEffects += t.getAllEffects().size(); 2817 totalEffects += t.getAllOverlays().size(); 2818 final Iterator<Effect> ef = t.getAllEffects().iterator(); 2819 while (ef.hasNext()) { 2820 final Effect e = ef.next(); 2821 if (e instanceof EffectKenBurns) 2822 totalEffects--; 2823 } 2824 } 2825 return totalEffects; 2826 } 2827 2828 /** 2829 * This function is responsible for forming clip settings 2830 * array and clip properties array including transition clips 2831 * and effect settings for preview purpose or export. 2832 * 2833 * 2834 * @param mediaItemsList The media item list 2835 * @param mediaTransitionList The transitions list 2836 * @param mediaBGMList The background music list 2837 * @param listener The MediaProcessingProgressListener 2838 * 2839 */ 2840 public void previewStoryBoard(List<MediaItem> mediaItemsList, 2841 List<Transition> mediaTransitionList, List<AudioTrack> mediaBGMList, 2842 MediaProcessingProgressListener listener) { 2843 if (mInvalidatePreviewArray) { 2844 int previewIndex = 0; 2845 int totalEffects = 0; 2846 int storyBoardTime = 0; 2847 int maxHeight = 0; 2848 int beginCutTime = 0; 2849 int endCutTime = 0; 2850 int effectIndex = 0; 2851 Transition lTransition = null; 2852 MediaItem lMediaItem = null; 2853 mPreviewEditSettings = new EditSettings(); 2854 mClipProperties = new PreviewClipProperties(); 2855 mTotalClips = 0; 2856 2857 mTotalClips = mediaItemsList.size(); 2858 for (Transition transition : mediaTransitionList) { 2859 if (transition.getDuration() > 0) 2860 mTotalClips++; 2861 } 2862 2863 totalEffects = getTotalEffects(mediaItemsList); 2864 2865 mPreviewEditSettings.clipSettingsArray = new ClipSettings[mTotalClips]; 2866 mPreviewEditSettings.effectSettingsArray = new EffectSettings[totalEffects]; 2867 mClipProperties.clipProperties = new Properties[mTotalClips]; 2868 2869 /** record the call back progress listner */ 2870 if (listener != null) 2871 { 2872 mMediaProcessingProgressListener = listener; 2873 mProgressToApp = 0; 2874 } 2875 2876 if (mediaItemsList.size() > 0) { 2877 for (int i = 0; i < mediaItemsList.size(); i++) { 2878 /* Get the Media Item from the list */ 2879 lMediaItem = mediaItemsList.get(i); 2880 if (lMediaItem instanceof MediaVideoItem) { 2881 beginCutTime = (int)((MediaVideoItem)lMediaItem).getBoundaryBeginTime(); 2882 endCutTime = (int)((MediaVideoItem)lMediaItem).getBoundaryEndTime(); 2883 } else if (lMediaItem instanceof MediaImageItem) { 2884 beginCutTime = 0; 2885 endCutTime = (int)((MediaImageItem)lMediaItem).getTimelineDuration(); 2886 } 2887 /* Get the transition associated with Media Item */ 2888 lTransition = lMediaItem.getBeginTransition(); 2889 if (lTransition != null && (lTransition.getDuration() > 0)) { 2890 /* generate transition clip */ 2891 generateTransition(lTransition, mPreviewEditSettings, 2892 mClipProperties, previewIndex); 2893 storyBoardTime += mClipProperties.clipProperties[previewIndex].duration; 2894 previewIndex++; 2895 } 2896 /* Populate media item properties */ 2897 maxHeight = populateMediaItemProperties(lMediaItem, 2898 previewIndex, 2899 maxHeight); 2900 if (lMediaItem instanceof MediaImageItem) 2901 { 2902 int tmpCnt = 0; 2903 boolean bEffectKbPresent = false; 2904 List<Effect> effectList = lMediaItem.getAllEffects(); 2905 /** 2906 * check if Kenburns effect is present 2907 */ 2908 while ( tmpCnt < effectList.size()) { 2909 if (effectList.get(tmpCnt) instanceof EffectKenBurns) { 2910 bEffectKbPresent = true; 2911 break; 2912 } 2913 tmpCnt++; 2914 } 2915 2916 if (bEffectKbPresent) { 2917 try { 2918 mClipProperties.clipProperties[previewIndex] 2919 = getMediaProperties(((MediaImageItem)lMediaItem).getGeneratedImageClip()); 2920 } catch (Exception e) { 2921 throw new IllegalArgumentException("Unsupported file or file not found"); 2922 } 2923 } else { 2924 try { 2925 mClipProperties.clipProperties[previewIndex] 2926 = getMediaProperties(((MediaImageItem)lMediaItem).getScaledImageFileName()); 2927 } catch (Exception e) { 2928 throw new IllegalArgumentException("Unsupported file or file not found"); 2929 } 2930 mClipProperties.clipProperties[previewIndex].width = ((MediaImageItem)lMediaItem).getScaledWidth(); 2931 mClipProperties.clipProperties[previewIndex].height = ((MediaImageItem)lMediaItem).getScaledHeight(); 2932 } 2933 2934 }else 2935 { 2936 try { 2937 mClipProperties.clipProperties[previewIndex] 2938 = getMediaProperties(lMediaItem.getFilename()); 2939 } catch (Exception e) { 2940 throw new IllegalArgumentException("Unsupported file or file not found"); 2941 } 2942 } 2943 mClipProperties.clipProperties[previewIndex].Id = lMediaItem.getId(); 2944 checkOddSizeImage(lMediaItem, mClipProperties, previewIndex); 2945 adjustVolume(lMediaItem, mClipProperties, previewIndex); 2946 2947 /* 2948 * Adjust media item start time and end time w.r.t to begin 2949 * and end transitions associated with media item 2950 */ 2951 2952 adjustMediaItemBoundary(mPreviewEditSettings.clipSettingsArray[previewIndex], 2953 mClipProperties.clipProperties[previewIndex], lMediaItem); 2954 2955 /* 2956 * Get all the effects and overlays for that media item and 2957 * adjust start time and duration of effects 2958 */ 2959 2960 effectIndex = populateEffects(lMediaItem, 2961 mPreviewEditSettings.effectSettingsArray, effectIndex, beginCutTime, 2962 endCutTime, storyBoardTime); 2963 storyBoardTime += mClipProperties.clipProperties[previewIndex].duration; 2964 previewIndex++; 2965 2966 /* Check if there is any end transition at last media item */ 2967 2968 if (i == (mediaItemsList.size() - 1)) { 2969 lTransition = lMediaItem.getEndTransition(); 2970 if (lTransition != null && (lTransition.getDuration() > 0)) { 2971 generateTransition(lTransition, mPreviewEditSettings, mClipProperties, 2972 previewIndex); 2973 break; 2974 } 2975 } 2976 } 2977 } 2978 if (!mErrorFlagSet) { 2979 mPreviewEditSettings.videoFrameSize = findVideoResolution(mVideoEditor 2980 .getAspectRatio(), maxHeight); 2981 /*if (mediaBGMList.size() == 1) //for remove Audio check */ { 2982 populateBackgroundMusicProperties(mediaBGMList); 2983 } 2984 /** call to native populate settings */ 2985 try { 2986 nativePopulateSettings(mPreviewEditSettings, mClipProperties, mAudioSettings); 2987 } catch (IllegalArgumentException ex) { 2988 Log.e("MediaArtistNativeHelper", 2989 "Illegal argument exception in nativePopulateSettings"); 2990 throw ex; 2991 } catch (IllegalStateException ex) { 2992 Log.e("MediaArtistNativeHelper", 2993 "Illegal state exception in nativePopulateSettings"); 2994 throw ex; 2995 } catch (RuntimeException ex) { 2996 Log.e("MediaArtistNativeHelper", "Runtime exception in nativePopulateSettings"); 2997 throw ex; 2998 } 2999 mInvalidatePreviewArray = false; 3000 mProcessingState = PROCESSING_NONE; 3001 } 3002 if (mErrorFlagSet) { 3003 mErrorFlagSet = false; 3004 throw new RuntimeException("preview generation cannot be completed"); 3005 } 3006 } 3007 } /* END of previewStoryBoard */ 3008 3009 /** 3010 * This function is responsible for starting the preview 3011 * 3012 * 3013 * @param surface The surface on which preview has to be displayed 3014 * @param fromMs The time in ms from which preview has to be started 3015 * @param toMs The time in ms till preview has to be played 3016 * @param loop To loop the preview or not 3017 * @param callbackAfterFrameCount INdicated after how many frames 3018 * the callback is needed 3019 * @param listener The PreviewProgressListener 3020 * 3021 */ 3022 public void doPreview(Surface surface, long fromMs, long toMs, boolean loop, 3023 int callbackAfterFrameCount, PreviewProgressListener listener) { 3024 mPreviewProgress = fromMs; 3025 if (listener != null) { 3026 mPreviewProgressListener = listener; 3027 } 3028 if (!mInvalidatePreviewArray) { 3029 try { 3030 /** Modify the image files names to rgb image files. */ 3031 for (int clipCnt = 0; clipCnt < mPreviewEditSettings.clipSettingsArray.length; clipCnt++) { 3032 if (mPreviewEditSettings.clipSettingsArray[clipCnt].fileType == FileType.JPG) { 3033 mPreviewEditSettings.clipSettingsArray[clipCnt].clipPath = mPreviewEditSettings.clipSettingsArray[clipCnt].clipDecodedPath; 3034 } 3035 } 3036 nativePopulateSettings(mPreviewEditSettings, mClipProperties, mAudioSettings); 3037 nativeStartPreview(surface, fromMs, toMs, callbackAfterFrameCount, loop); 3038 } catch (IllegalArgumentException ex) { 3039 Log.e("MediaArtistNativeHelper", 3040 "Illegal argument exception in nativeStartPreview"); 3041 throw ex; 3042 } catch (IllegalStateException ex) { 3043 Log.e("MediaArtistNativeHelper", "Illegal state exception in nativeStartPreview"); 3044 throw ex; 3045 } catch (RuntimeException ex) { 3046 Log.e("MediaArtistNativeHelper", "Runtime exception in nativeStartPreview"); 3047 throw ex; 3048 } 3049 3050 } else { 3051 return; 3052 } 3053 } 3054 3055 /** 3056 * This function is responsible for stopping the preview 3057 */ 3058 public long stopPreview() { 3059 nativeStopPreview(); 3060 return mPreviewProgress; 3061 } 3062 3063 /** 3064 * This function is responsible for rendering a single frame 3065 * from the complete story board on the surface 3066 * 3067 * @param surface The surface on which frame has to be rendered 3068 * @param time The time in ms at which the frame has to be rendered 3069 * @param surfaceWidth The surface width 3070 * @param surfaceHeight The surface height 3071 * 3072 * @return The actual time from the story board at which the frame was extracted 3073 * and rendered 3074 */ 3075 public long renderPreviewFrame(Surface surface, long time, int surfaceWidth, 3076 int surfaceHeight) { 3077 long timeMs = 0; 3078 if (!mInvalidatePreviewArray) { 3079 try { 3080 for (int clipCnt = 0; clipCnt < mPreviewEditSettings.clipSettingsArray.length; clipCnt++) { 3081 if (mPreviewEditSettings.clipSettingsArray[clipCnt].fileType == FileType.JPG) { 3082 mPreviewEditSettings.clipSettingsArray[clipCnt].clipPath = mPreviewEditSettings.clipSettingsArray[clipCnt].clipDecodedPath; 3083 } 3084 } 3085 nativePopulateSettings(mPreviewEditSettings, mClipProperties, mAudioSettings); 3086 timeMs = (long)nativeRenderPreviewFrame(surface, time, surfaceWidth, surfaceHeight); 3087 } catch (IllegalArgumentException ex) { 3088 Log.e("MediaArtistNativeHelper", 3089 "Illegal Argument exception in nativeRenderPreviewFrame"); 3090 throw ex; 3091 } catch (IllegalStateException ex) { 3092 Log.e("MediaArtistNativeHelper", 3093 "Illegal state exception in nativeRenderPreviewFrame"); 3094 throw ex; 3095 } catch (RuntimeException ex) { 3096 Log.e("MediaArtistNativeHelper", "Runtime exception in nativeRenderPreviewFrame"); 3097 throw ex; 3098 } 3099 return timeMs; 3100 } else { 3101 3102 throw new RuntimeException("Call generate preview first"); 3103 } 3104 } 3105 3106 /** 3107 * This function is responsible for rendering a single frame 3108 * from a single media item on the surface 3109 * 3110 * @param surface The surface on which frame has to be rendered 3111 * @param filepath The file path for which the frame needs to be displayed 3112 * @param time The time in ms at which the frame has to be rendered 3113 * @param framewidth The frame width 3114 * @param framewidth The frame height 3115 * 3116 * @return The actual time from media item at which the frame was extracted 3117 * and rendered 3118 */ 3119 public long renderMediaItemPreviewFrame(Surface surface, String filepath, 3120 long time, int framewidth, 3121 int frameheight) { 3122 long timeMs = 0; 3123 try { 3124 3125 timeMs = (long)nativeRenderMediaItemPreviewFrame(surface, filepath, framewidth, 3126 frameheight, 0, 0, time); 3127 } catch (IllegalArgumentException ex) { 3128 Log.e("MediaArtistNativeHelper", 3129 "Illegal Argument exception in renderMediaItemPreviewFrame"); 3130 throw ex; 3131 } catch (IllegalStateException ex) { 3132 Log.e("MediaArtistNativeHelper", 3133 "Illegal state exception in renderMediaItemPreviewFrame"); 3134 throw ex; 3135 } catch (RuntimeException ex) { 3136 Log.e("MediaArtistNativeHelper", "Runtime exception in renderMediaItemPreviewFrame"); 3137 throw ex; 3138 } 3139 3140 return timeMs; 3141 } 3142 3143 /** 3144 * This function sets the flag to invalidate the preview array 3145 * and for generating the preview again 3146 */ 3147 void setGeneratePreview(boolean isRequired) { 3148 mInvalidatePreviewArray = isRequired; 3149 } 3150 3151 /** 3152 * @return Returns the current status of preview invalidation 3153 * flag 3154 */ 3155 boolean getGeneratePreview() { 3156 return mInvalidatePreviewArray; 3157 } 3158 3159 /** 3160 * Calculates the aspect ratio from widht and height 3161 * 3162 * @param w The width of media item 3163 * @param h The height of media item 3164 * 3165 * @return The calculated aspect ratio 3166 */ 3167 public int getAspectRatio(int w, int h) { 3168 double apRatio = (double)(w) / (double)(h); 3169 BigDecimal bd = new BigDecimal(apRatio); 3170 bd = bd.setScale(3, BigDecimal.ROUND_HALF_UP); 3171 apRatio = bd.doubleValue(); 3172 int var = MediaProperties.ASPECT_RATIO_16_9; 3173 if (apRatio >= 1.7) { 3174 var = MediaProperties.ASPECT_RATIO_16_9; 3175 } else if (apRatio >= 1.6) { 3176 var = MediaProperties.ASPECT_RATIO_5_3; 3177 } else if (apRatio >= 1.5) { 3178 var = MediaProperties.ASPECT_RATIO_3_2; 3179 } else if (apRatio > 1.3) { 3180 var = MediaProperties.ASPECT_RATIO_4_3; 3181 } else if (apRatio >= 1.2) { 3182 var = MediaProperties.ASPECT_RATIO_11_9; 3183 } 3184 return var; 3185 } 3186 3187 /** 3188 * Maps the file type used in native layer 3189 * to file type used in JAVA layer 3190 * 3191 * @param fileType The file type in native layer 3192 * 3193 * @return The File type in JAVA layer 3194 */ 3195 public int getFileType(int fileType) { 3196 int retValue = -1; 3197 switch (fileType) { 3198 case FileType.UNSUPPORTED: 3199 retValue = MediaProperties.FILE_UNSUPPORTED; 3200 break; 3201 case FileType.THREE_GPP: 3202 retValue = MediaProperties.FILE_3GP; 3203 break; 3204 case FileType.MP4: 3205 retValue = MediaProperties.FILE_MP4; 3206 break; 3207 case FileType.JPG: 3208 retValue = MediaProperties.FILE_JPEG; 3209 break; 3210 case FileType.PNG: 3211 retValue = MediaProperties.FILE_PNG; 3212 break; 3213 case FileType.MP3: 3214 retValue = MediaProperties.FILE_MP3; 3215 break; 3216 3217 default: 3218 retValue = -1; 3219 } 3220 return retValue; 3221 } 3222 3223 /** 3224 * Maps the video codec type used in native layer 3225 * to video codec type used in JAVA layer 3226 * 3227 * @param codecType The video codec type in native layer 3228 * 3229 * @return The video codec type in JAVA layer 3230 */ 3231 public int getVideoCodecType(int codecType) { 3232 int retValue = -1; 3233 switch (codecType) { 3234 case VideoFormat.H263: 3235 retValue = MediaProperties.VCODEC_H263; 3236 break; 3237 case VideoFormat.H264: 3238 retValue = MediaProperties.VCODEC_H264BP; 3239 break; 3240 case VideoFormat.MPEG4: 3241 retValue = MediaProperties.VCODEC_MPEG4; 3242 break; 3243 case VideoFormat.UNSUPPORTED: 3244 3245 default: 3246 retValue = -1; 3247 } 3248 return retValue; 3249 } 3250 3251 /** 3252 * Maps the audio codec type used in native layer 3253 * to audio codec type used in JAVA layer 3254 * 3255 * @param audioType The audio codec type in native layer 3256 * 3257 * @return The audio codec type in JAVA layer 3258 */ 3259 public int getAudioCodecType(int codecType) { 3260 int retValue = -1; 3261 switch (codecType) { 3262 case AudioFormat.AMR_NB: 3263 retValue = MediaProperties.ACODEC_AMRNB; 3264 break; 3265 case AudioFormat.AAC: 3266 retValue = MediaProperties.ACODEC_AAC_LC; 3267 break; 3268 case AudioFormat.MP3: 3269 retValue = MediaProperties.ACODEC_MP3; 3270 break; 3271 3272 default: 3273 retValue = -1; 3274 } 3275 return retValue; 3276 } 3277 3278 /** 3279 * Returns the frame rate as integer 3280 * 3281 * @param fps The fps as enum 3282 * 3283 * @return The frame rate as integer 3284 */ 3285 public int getFrameRate(int fps) { 3286 int retValue = -1; 3287 switch (fps) { 3288 case VideoFrameRate.FR_5_FPS: 3289 retValue = 5; 3290 break; 3291 case VideoFrameRate.FR_7_5_FPS: 3292 retValue = 8; 3293 break; 3294 case VideoFrameRate.FR_10_FPS: 3295 retValue = 10; 3296 break; 3297 case VideoFrameRate.FR_12_5_FPS: 3298 retValue = 13; 3299 break; 3300 case VideoFrameRate.FR_15_FPS: 3301 retValue = 15; 3302 break; 3303 case VideoFrameRate.FR_20_FPS: 3304 retValue = 20; 3305 break; 3306 case VideoFrameRate.FR_25_FPS: 3307 retValue = 25; 3308 break; 3309 case VideoFrameRate.FR_30_FPS: 3310 retValue = 30; 3311 break; 3312 3313 default: 3314 retValue = -1; 3315 } 3316 return retValue; 3317 } 3318 3319 /** 3320 * Maps the file type used in JAVA layer 3321 * to file type used in native layer 3322 * 3323 * @param fileType The file type in JAVA layer 3324 * 3325 * @return The File type in native layer 3326 */ 3327 int getMediaItemFileType(int fileType) { 3328 int retValue = -1; 3329 3330 switch (fileType) { 3331 case MediaProperties.FILE_UNSUPPORTED: 3332 retValue = FileType.UNSUPPORTED; 3333 break; 3334 case MediaProperties.FILE_3GP: 3335 retValue = FileType.THREE_GPP; 3336 break; 3337 case MediaProperties.FILE_MP4: 3338 retValue = FileType.MP4; 3339 break; 3340 case MediaProperties.FILE_JPEG: 3341 retValue = FileType.JPG; 3342 break; 3343 case MediaProperties.FILE_PNG: 3344 retValue = FileType.PNG; 3345 break; 3346 3347 default: 3348 retValue = -1; 3349 } 3350 return retValue; 3351 3352 } 3353 3354 /** 3355 * Maps the rendering mode used in native layer 3356 * to rendering mode used in JAVA layer 3357 * 3358 * @param renderingMode The rendering mode in JAVA layer 3359 * 3360 * @return The rendering mode in native layer 3361 */ 3362 int getMediaItemRenderingMode(int renderingMode) { 3363 int retValue = -1; 3364 switch (renderingMode) { 3365 case MediaItem.RENDERING_MODE_BLACK_BORDER: 3366 retValue = MediaRendering.BLACK_BORDERS; 3367 break; 3368 case MediaItem.RENDERING_MODE_STRETCH: 3369 retValue = MediaRendering.RESIZING; 3370 break; 3371 case MediaItem.RENDERING_MODE_CROPPING: 3372 retValue = MediaRendering.CROPPING; 3373 break; 3374 3375 default: 3376 retValue = -1; 3377 } 3378 return retValue; 3379 } 3380 3381 /** 3382 * Maps the transition behavior used in JAVA layer 3383 * to transition behavior used in native layer 3384 * 3385 * @param transitionType The transition behavior in JAVA layer 3386 * 3387 * @return The transition behavior in native layer 3388 */ 3389 int getVideoTransitionBehaviour(int transitionType) { 3390 int retValue = -1; 3391 switch (transitionType) { 3392 case Transition.BEHAVIOR_SPEED_UP: 3393 retValue = TransitionBehaviour.SPEED_UP; 3394 break; 3395 case Transition.BEHAVIOR_SPEED_DOWN: 3396 retValue = TransitionBehaviour.SPEED_DOWN; 3397 break; 3398 case Transition.BEHAVIOR_LINEAR: 3399 retValue = TransitionBehaviour.LINEAR; 3400 break; 3401 case Transition.BEHAVIOR_MIDDLE_SLOW: 3402 retValue = TransitionBehaviour.SLOW_MIDDLE; 3403 break; 3404 case Transition.BEHAVIOR_MIDDLE_FAST: 3405 retValue = TransitionBehaviour.FAST_MIDDLE; 3406 break; 3407 3408 default: 3409 retValue = -1; 3410 } 3411 return retValue; 3412 } 3413 3414 /** 3415 * Maps the transition slide direction used in JAVA layer 3416 * to transition slide direction used in native layer 3417 * 3418 * @param slideDirection The transition slide direction 3419 * in JAVA layer 3420 * 3421 * @return The transition slide direction in native layer 3422 */ 3423 int getSlideSettingsDirection(int slideDirection) { 3424 int retValue = -1; 3425 switch (slideDirection) { 3426 case TransitionSliding.DIRECTION_RIGHT_OUT_LEFT_IN: 3427 retValue = SlideDirection.RIGHT_OUT_LEFT_IN; 3428 break; 3429 case TransitionSliding.DIRECTION_LEFT_OUT_RIGHT_IN: 3430 retValue = SlideDirection.LEFT_OUT_RIGTH_IN; 3431 break; 3432 case TransitionSliding.DIRECTION_TOP_OUT_BOTTOM_IN: 3433 retValue = SlideDirection.TOP_OUT_BOTTOM_IN; 3434 break; 3435 case TransitionSliding.DIRECTION_BOTTOM_OUT_TOP_IN: 3436 retValue = SlideDirection.BOTTOM_OUT_TOP_IN; 3437 break; 3438 3439 default: 3440 retValue = -1; 3441 } 3442 return retValue; 3443 } 3444 3445 /** 3446 * Maps the effect color type used in JAVA layer 3447 * to effect color type used in native layer 3448 * 3449 * @param effect The EffectColor reference 3450 * 3451 * @return The color effect value from native layer 3452 */ 3453 private int getEffectColorType(EffectColor effect) { 3454 int retValue = -1; 3455 switch (effect.getType()) { 3456 case EffectColor.TYPE_COLOR: 3457 if (effect.getColor() == EffectColor.GREEN) { 3458 retValue = VideoEffect.GREEN; 3459 } else if (effect.getColor() == EffectColor.PINK) { 3460 retValue = VideoEffect.PINK; 3461 } else if (effect.getColor() == EffectColor.GRAY) { 3462 retValue = VideoEffect.BLACK_AND_WHITE; 3463 } else { 3464 retValue = VideoEffect.COLORRGB16; 3465 } 3466 break; 3467 case EffectColor.TYPE_GRADIENT: 3468 retValue = VideoEffect.GRADIENT; 3469 break; 3470 case EffectColor.TYPE_SEPIA: 3471 retValue = VideoEffect.SEPIA; 3472 break; 3473 case EffectColor.TYPE_NEGATIVE: 3474 retValue = VideoEffect.NEGATIVE; 3475 break; 3476 case EffectColor.TYPE_FIFTIES: 3477 retValue = VideoEffect.FIFTIES; 3478 break; 3479 3480 default: 3481 retValue = -1; 3482 } 3483 return retValue; 3484 } 3485 3486 /** 3487 * Calculates videdo resolution for output clip 3488 * based on clip's height and aspect ratio of storyboard 3489 * 3490 * @param aspectRatio The aspect ratio of story board 3491 * @param height The height of clip 3492 * 3493 * @return The video resolution 3494 */ 3495 private int findVideoResolution(int aspectRatio, int height) { 3496 final Pair<Integer, Integer>[] resolutions; 3497 final Pair<Integer, Integer> maxResolution; 3498 int retValue = VideoFrameSize.SIZE_UNDEFINED; 3499 switch (aspectRatio) { 3500 case MediaProperties.ASPECT_RATIO_3_2: 3501 if (height == MediaProperties.HEIGHT_480) 3502 retValue = VideoFrameSize.NTSC; 3503 else if (height == MediaProperties.HEIGHT_720) 3504 retValue = VideoFrameSize.W720p; 3505 break; 3506 case MediaProperties.ASPECT_RATIO_16_9: 3507 if (height == MediaProperties.HEIGHT_480) 3508 retValue = VideoFrameSize.WVGA16x9; 3509 else if (height == MediaProperties.HEIGHT_720) 3510 retValue = VideoFrameSize.V720p; 3511 break; 3512 case MediaProperties.ASPECT_RATIO_4_3: 3513 if (height == MediaProperties.HEIGHT_480) 3514 retValue = VideoFrameSize.VGA; 3515 if (height == MediaProperties.HEIGHT_720) 3516 retValue = VideoFrameSize.S720p; 3517 break; 3518 case MediaProperties.ASPECT_RATIO_5_3: 3519 if (height == MediaProperties.HEIGHT_480) 3520 retValue = VideoFrameSize.WVGA; 3521 break; 3522 case MediaProperties.ASPECT_RATIO_11_9: 3523 if (height == MediaProperties.HEIGHT_144) 3524 retValue = VideoFrameSize.QCIF; 3525 break; 3526 } 3527 if (retValue == VideoFrameSize.SIZE_UNDEFINED) { 3528 resolutions = MediaProperties.getSupportedResolutions(mVideoEditor.getAspectRatio()); 3529 // Get the highest resolution 3530 maxResolution = resolutions[resolutions.length - 1]; 3531 retValue = findVideoResolution(mVideoEditor.getAspectRatio(), 3532 maxResolution.second); 3533 } 3534 3535 return retValue; 3536 } 3537 3538 /** 3539 * This method is responsible for exporting a movie 3540 * 3541 * @param filePath The output file path 3542 * @param projectDir The output project directory 3543 * @param height The height of clip 3544 * @param bitrate The bitrate at which the movie should be exported 3545 * @param mediaItemsList The media items list 3546 * @param mediaTransitionList The transitons list 3547 * @param mediaBGMList The background track list 3548 * @param listener The ExportProgressListener 3549 * 3550 */ 3551 public void export(String filePath, String projectDir, int height, int bitrate, 3552 List<MediaItem> mediaItemsList, List<Transition> mediaTransitionList, 3553 List<AudioTrack> mediaBGMList, ExportProgressListener listener) { 3554 3555 int outBitrate = 0; 3556 mExportFilename = filePath; 3557 previewStoryBoard(mediaItemsList, mediaTransitionList, mediaBGMList,null); 3558 if (listener != null) { 3559 mExportProgressListener = listener; 3560 } 3561 mProgressToApp = 0; 3562 3563 switch (bitrate) { 3564 case MediaProperties.BITRATE_28K: 3565 outBitrate = Bitrate.BR_32_KBPS; 3566 break; 3567 case MediaProperties.BITRATE_40K: 3568 outBitrate = Bitrate.BR_48_KBPS; 3569 break; 3570 case MediaProperties.BITRATE_64K: 3571 outBitrate = Bitrate.BR_64_KBPS; 3572 break; 3573 case MediaProperties.BITRATE_96K: 3574 outBitrate = Bitrate.BR_96_KBPS; 3575 break; 3576 case MediaProperties.BITRATE_128K: 3577 outBitrate = Bitrate.BR_128_KBPS; 3578 break; 3579 case MediaProperties.BITRATE_192K: 3580 outBitrate = Bitrate.BR_192_KBPS; 3581 break; 3582 case MediaProperties.BITRATE_256K: 3583 outBitrate = Bitrate.BR_256_KBPS; 3584 break; 3585 case MediaProperties.BITRATE_384K: 3586 outBitrate = Bitrate.BR_384_KBPS; 3587 break; 3588 case MediaProperties.BITRATE_512K: 3589 outBitrate = Bitrate.BR_512_KBPS; 3590 break; 3591 case MediaProperties.BITRATE_800K: 3592 outBitrate = Bitrate.BR_800_KBPS; 3593 break; 3594 case MediaProperties.BITRATE_2M: 3595 outBitrate = Bitrate.BR_2_MBPS; 3596 break; 3597 3598 case MediaProperties.BITRATE_5M: 3599 outBitrate = Bitrate.BR_5_MBPS; 3600 break; 3601 case MediaProperties.BITRATE_8M: 3602 outBitrate = Bitrate.BR_8_MBPS; 3603 break; 3604 3605 default: 3606 throw new IllegalArgumentException("Argument Bitrate incorrect"); 3607 } 3608 mPreviewEditSettings.videoFrameRate = VideoFrameRate.FR_30_FPS; 3609 mPreviewEditSettings.outputFile = mOutputFilename = filePath; 3610 3611 int aspectRatio = mVideoEditor.getAspectRatio(); 3612 mPreviewEditSettings.videoFrameSize = findVideoResolution(aspectRatio, height); 3613 mPreviewEditSettings.videoFormat = VideoFormat.H264; 3614 mPreviewEditSettings.audioFormat = AudioFormat.AAC; 3615 mPreviewEditSettings.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 3616 mPreviewEditSettings.maxFileSize = 0; 3617 mPreviewEditSettings.audioChannels = 2; 3618 mPreviewEditSettings.videoBitrate = outBitrate; 3619 mPreviewEditSettings.audioBitrate = Bitrate.BR_96_KBPS; 3620 3621 mPreviewEditSettings.transitionSettingsArray = new TransitionSettings[mTotalClips - 1]; 3622 for (int index = 0; index < mTotalClips - 1; index++) { 3623 mPreviewEditSettings.transitionSettingsArray[index] = new TransitionSettings(); 3624 mPreviewEditSettings.transitionSettingsArray[index].videoTransitionType = VideoTransition.NONE; 3625 mPreviewEditSettings.transitionSettingsArray[index].audioTransitionType = AudioTransition.NONE; 3626 } 3627 for (int clipCnt = 0; clipCnt < mPreviewEditSettings.clipSettingsArray.length; clipCnt++) { 3628 if (mPreviewEditSettings.clipSettingsArray[clipCnt].fileType == FileType.JPG) { 3629 mPreviewEditSettings.clipSettingsArray[clipCnt].clipPath = 3630 mPreviewEditSettings.clipSettingsArray[clipCnt].clipOriginalPath; 3631 } 3632 } 3633 nativePopulateSettings(mPreviewEditSettings, mClipProperties, mAudioSettings); 3634 3635 int err = 0; 3636 try { 3637 mProcessingState = PROCESSING_EXPORT; 3638 mProcessingObject = null; 3639 err = generateClip(mPreviewEditSettings); 3640 mProcessingState = PROCESSING_NONE; 3641 } catch (IllegalArgumentException ex) { 3642 Log.e("MediaArtistNativeHelper", "IllegalArgument for generateClip"); 3643 throw ex; 3644 } catch (IllegalStateException ex) { 3645 Log.e("MediaArtistNativeHelper", "IllegalStateExceptiont for generateClip"); 3646 throw ex; 3647 } catch (RuntimeException ex) { 3648 Log.e("MediaArtistNativeHelper", "RuntimeException for generateClip"); 3649 throw ex; 3650 } 3651 3652 if (err != 0) { 3653 Log.e("MediaArtistNativeHelper", "RuntimeException for generateClip"); 3654 throw new RuntimeException("generateClip failed with error="+err ); 3655 } 3656 3657 mExportDone = true; 3658 setGeneratePreview(true); 3659 mExportProgressListener = null; 3660 } 3661 3662 /** 3663 * This method is responsible for exporting a movie 3664 * 3665 * @param filePath The output file path 3666 * @param projectDir The output project directory 3667 * @param height The height of clip 3668 * @param bitrate The bitrate at which the movie should be exported 3669 * @param audioCodec The audio codec to use 3670 * @param videoCodec The video codec to use 3671 * @param mediaItemsList The media items list 3672 * @param mediaTransitionList The transitons list 3673 * @param mediaBGMList The background track list 3674 * @param listener The ExportProgressListener 3675 * 3676 */ 3677 public void export(String filePath, String projectDir,int height,int bitrate, 3678 int audioCodec,int videoCodec,List<MediaItem> mediaItemsList, 3679 List<Transition> mediaTransitionList,List<AudioTrack> mediaBGMList, 3680 ExportProgressListener listener) { 3681 3682 int outBitrate = 0; 3683 mExportFilename = filePath; 3684 previewStoryBoard(mediaItemsList, mediaTransitionList, mediaBGMList,null); 3685 if (listener != null) { 3686 mExportProgressListener = listener; 3687 } 3688 mProgressToApp = 0; 3689 3690 switch (bitrate) { 3691 case MediaProperties.BITRATE_28K: 3692 outBitrate = Bitrate.BR_32_KBPS; 3693 break; 3694 case MediaProperties.BITRATE_40K: 3695 outBitrate = Bitrate.BR_48_KBPS; 3696 break; 3697 case MediaProperties.BITRATE_64K: 3698 outBitrate = Bitrate.BR_64_KBPS; 3699 break; 3700 case MediaProperties.BITRATE_96K: 3701 outBitrate = Bitrate.BR_96_KBPS; 3702 break; 3703 case MediaProperties.BITRATE_128K: 3704 outBitrate = Bitrate.BR_128_KBPS; 3705 break; 3706 case MediaProperties.BITRATE_192K: 3707 outBitrate = Bitrate.BR_192_KBPS; 3708 break; 3709 case MediaProperties.BITRATE_256K: 3710 outBitrate = Bitrate.BR_256_KBPS; 3711 break; 3712 case MediaProperties.BITRATE_384K: 3713 outBitrate = Bitrate.BR_384_KBPS; 3714 break; 3715 case MediaProperties.BITRATE_512K: 3716 outBitrate = Bitrate.BR_512_KBPS; 3717 break; 3718 case MediaProperties.BITRATE_800K: 3719 outBitrate = Bitrate.BR_800_KBPS; 3720 break; 3721 case MediaProperties.BITRATE_2M: 3722 outBitrate = Bitrate.BR_2_MBPS; 3723 break; 3724 case MediaProperties.BITRATE_5M: 3725 outBitrate = Bitrate.BR_5_MBPS; 3726 break; 3727 case MediaProperties.BITRATE_8M: 3728 outBitrate = Bitrate.BR_8_MBPS; 3729 break; 3730 3731 default: 3732 throw new IllegalArgumentException("Argument Bitrate incorrect"); 3733 } 3734 mPreviewEditSettings.videoFrameRate = VideoFrameRate.FR_30_FPS; 3735 mPreviewEditSettings.outputFile = mOutputFilename = filePath; 3736 3737 int aspectRatio = mVideoEditor.getAspectRatio(); 3738 mPreviewEditSettings.videoFrameSize = findVideoResolution(aspectRatio, height); 3739 switch (audioCodec) { 3740 case MediaProperties.ACODEC_AAC_LC: 3741 mPreviewEditSettings.audioFormat = AudioFormat.AAC; 3742 break; 3743 case MediaProperties.ACODEC_AMRNB: 3744 mPreviewEditSettings.audioFormat = AudioFormat.AMR_NB; 3745 break; 3746 } 3747 3748 switch (videoCodec) { 3749 case MediaProperties.VCODEC_H263: 3750 mPreviewEditSettings.videoFormat = VideoFormat.H263; 3751 break; 3752 case MediaProperties.VCODEC_H264BP: 3753 mPreviewEditSettings.videoFormat = VideoFormat.H264; 3754 break; 3755 case MediaProperties.VCODEC_MPEG4: 3756 mPreviewEditSettings.videoFormat = VideoFormat.MPEG4; 3757 break; 3758 } 3759 3760 mPreviewEditSettings.audioSamplingFreq = AudioSamplingFrequency.FREQ_32000; 3761 mPreviewEditSettings.maxFileSize = 0; 3762 mPreviewEditSettings.audioChannels = 2; 3763 mPreviewEditSettings.videoBitrate = outBitrate; 3764 mPreviewEditSettings.audioBitrate = Bitrate.BR_96_KBPS; 3765 3766 mPreviewEditSettings.transitionSettingsArray = 3767 new TransitionSettings[mTotalClips - 1]; 3768 for (int index = 0; index < mTotalClips - 1; index++) { 3769 mPreviewEditSettings.transitionSettingsArray[index] = 3770 new TransitionSettings(); 3771 mPreviewEditSettings.transitionSettingsArray[index].videoTransitionType = 3772 VideoTransition.NONE; 3773 mPreviewEditSettings.transitionSettingsArray[index].audioTransitionType = 3774 AudioTransition.NONE; 3775 } 3776 for (int clipCnt = 0; clipCnt < mPreviewEditSettings.clipSettingsArray.length; clipCnt++) { 3777 if (mPreviewEditSettings.clipSettingsArray[clipCnt].fileType == FileType.JPG) { 3778 mPreviewEditSettings.clipSettingsArray[clipCnt].clipPath = 3779 mPreviewEditSettings.clipSettingsArray[clipCnt].clipOriginalPath; 3780 } 3781 } 3782 nativePopulateSettings(mPreviewEditSettings, mClipProperties, mAudioSettings); 3783 3784 int err = 0; 3785 try { 3786 mProcessingState = PROCESSING_EXPORT; 3787 mProcessingObject = null; 3788 err = generateClip(mPreviewEditSettings); 3789 mProcessingState = PROCESSING_NONE; 3790 } catch (IllegalArgumentException ex) { 3791 Log.e("MediaArtistNativeHelper", "IllegalArgument for generateClip"); 3792 throw ex; 3793 } catch (IllegalStateException ex) { 3794 Log.e("MediaArtistNativeHelper", "IllegalStateExceptiont for generateClip"); 3795 throw ex; 3796 } catch (RuntimeException ex) { 3797 Log.e("MediaArtistNativeHelper", "RuntimeException for generateClip"); 3798 throw ex; 3799 } 3800 3801 if (err != 0) { 3802 Log.e("MediaArtistNativeHelper", "RuntimeException for generateClip"); 3803 throw new RuntimeException("generateClip failed with error="+err ); 3804 } 3805 3806 mExportDone = true; 3807 setGeneratePreview(true); 3808 mExportProgressListener = null; 3809 } 3810 3811 3812 /** 3813 * This methods takes care of stopping the Export process 3814 * 3815 * @param The input file name for which export has to be stopped 3816 */ 3817 public void stop(String filename) { 3818 if (!mExportDone) { 3819 try { 3820 stopEncoding(); 3821 } catch (IllegalStateException ex) { 3822 Log.e("MediaArtistNativeHelper", "Illegal state exception in unload settings"); 3823 throw ex; 3824 } catch (RuntimeException ex) { 3825 Log.e("MediaArtistNativeHelper", "Runtime exception in unload settings"); 3826 throw ex; 3827 } 3828 3829 new File(mExportFilename).delete(); 3830 } 3831 } 3832 3833 /** 3834 * This method extracts a frame from the input file 3835 * and returns the frame as a bitmap 3836 * 3837 * @param inputFile The inputFile 3838 * @param width The width of the output frame 3839 * @param height The height of the output frame 3840 * @param timeMS The time in ms at which the frame hass to be extracted 3841 */ 3842 public Bitmap getPixels(String inputFile, int width, int height, long timeMS) { 3843 if (inputFile == null) { 3844 throw new IllegalArgumentException(); 3845 } 3846 3847 int newWidth = 0; 3848 int newHeight = 0; 3849 Bitmap tempBitmap = null; 3850 3851 /* Make width and height as even */ 3852 newWidth = (width + 1) & 0xFFFFFFFE; 3853 newHeight = (height + 1) & 0xFFFFFFFE; 3854 3855 /* Create a temp bitmap for resized thumbnails */ 3856 if ((newWidth != width) || (newHeight != height)) { 3857 tempBitmap = Bitmap.createBitmap(newWidth, newHeight, Bitmap.Config.ARGB_8888); 3858 } 3859 3860 IntBuffer rgb888 = IntBuffer.allocate(newWidth * newHeight * 4); 3861 Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888); 3862 nativeGetPixels(inputFile, rgb888.array(), newWidth, newHeight, timeMS); 3863 3864 if ((newWidth == width) && (newHeight == height)) { 3865 bitmap.copyPixelsFromBuffer(rgb888); 3866 } else { 3867 /* Create a temp bitmap to be used for resize */ 3868 tempBitmap.copyPixelsFromBuffer(rgb888); 3869 3870 /* Create a canvas to resize */ 3871 final Canvas canvas = new Canvas(bitmap); 3872 canvas.drawBitmap(tempBitmap, new Rect(0, 0, newWidth, newHeight), 3873 new Rect(0, 0, width, height), 3874 sResizePaint); 3875 } 3876 3877 if (tempBitmap != null) { 3878 tempBitmap.recycle(); 3879 } 3880 return bitmap; 3881 } 3882 3883 /** 3884 * This method extracts a list of frame from the 3885 * input file and returns the frame in bitmap array 3886 * 3887 * @param filename The inputFile 3888 * @param width The width of the output frame 3889 * @param height The height of the output frame 3890 * @param startMs The starting time in ms 3891 * @param endMs The end time in ms 3892 * @param thumbnailCount The number of frames to be extracted 3893 * from startMs to endMs 3894 * 3895 * @return The frames as bitmaps in bitmap array 3896 **/ 3897 public Bitmap[] getPixelsList(String filename, int width, int height, long startMs, long endMs, 3898 int thumbnailCount) { 3899 int[] rgb888 = null; 3900 int thumbnailSize = 0; 3901 int newWidth = 0; 3902 int newHeight = 0; 3903 Bitmap tempBitmap = null; 3904 3905 /* Make width and height as even */ 3906 newWidth = (width + 1) & 0xFFFFFFFE; 3907 newHeight = (height + 1) & 0xFFFFFFFE; 3908 thumbnailSize = newWidth * newHeight * 4; 3909 3910 /* Create a temp bitmap for resized thumbnails */ 3911 if ((newWidth != width) || (newHeight != height)) { 3912 tempBitmap = Bitmap.createBitmap(newWidth, newHeight, Bitmap.Config.ARGB_8888); 3913 } 3914 int i = 0; 3915 int deltaTime = (int)(endMs - startMs) / thumbnailCount; 3916 Bitmap[] bitmap = null; 3917 3918 try { 3919 // This may result in out of Memory Error 3920 rgb888 = new int[thumbnailSize * thumbnailCount]; 3921 bitmap = new Bitmap[thumbnailCount]; 3922 } catch (Throwable e) { 3923 // Allocating to new size with Fixed count 3924 try { 3925 System.gc(); 3926 rgb888 = new int[thumbnailSize * MAX_THUMBNAIL_PERMITTED]; 3927 bitmap = new Bitmap[MAX_THUMBNAIL_PERMITTED]; 3928 thumbnailCount = MAX_THUMBNAIL_PERMITTED; 3929 } catch (Throwable ex) { 3930 throw new RuntimeException("Memory allocation fails, thumbnail count too large: "+thumbnailCount); 3931 } 3932 } 3933 IntBuffer tmpBuffer = IntBuffer.allocate(thumbnailSize); 3934 nativeGetPixelsList(filename, rgb888, newWidth, newHeight, deltaTime, thumbnailCount, startMs, 3935 endMs); 3936 3937 for (; i < thumbnailCount; i++) { 3938 bitmap[i] = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888); 3939 tmpBuffer.put(rgb888, (i * thumbnailSize), thumbnailSize); 3940 tmpBuffer.rewind(); 3941 3942 if ((newWidth == width) && (newHeight == height)) { 3943 bitmap[i].copyPixelsFromBuffer(tmpBuffer); 3944 } else { 3945 /* Copy the out rgb buffer to temp bitmap */ 3946 tempBitmap.copyPixelsFromBuffer(tmpBuffer); 3947 3948 /* Create a canvas to resize */ 3949 final Canvas canvas = new Canvas(bitmap[i]); 3950 canvas.drawBitmap(tempBitmap, new Rect(0, 0, newWidth, newHeight), 3951 new Rect(0, 0, width, height), 3952 sResizePaint); 3953 } 3954 } 3955 3956 if (tempBitmap != null) { 3957 tempBitmap.recycle(); 3958 } 3959 return bitmap; 3960 } 3961 3962 /** 3963 * This method generates the audio graph 3964 * 3965 * @param uniqueId The unique id 3966 * @param inFileName The inputFile 3967 * @param OutAudiGraphFileName output filename 3968 * @param frameDuration The each frame duration 3969 * @param audioChannels The number of audio channels 3970 * @param samplesCount Total number of samples count 3971 * @param listener ExtractAudioWaveformProgressListener reference 3972 * @param isVideo The flag to indicate if the file is video file or not 3973 * 3974 **/ 3975 public void generateAudioGraph(String uniqueId, String inFileName, String OutAudiGraphFileName, 3976 int frameDuration, int audioChannels, int samplesCount, 3977 ExtractAudioWaveformProgressListener listener, boolean isVideo) { 3978 String tempPCMFileName; 3979 3980 if (listener != null) { 3981 mExtractAudioWaveformProgressListener = listener; 3982 } 3983 /** 3984 * in case of Video , first call will generate the PCM file to make the 3985 * audio graph 3986 */ 3987 if (isVideo) { 3988 tempPCMFileName = String.format(mProjectPath + "/" + uniqueId + ".pcm"); 3989 } else { 3990 tempPCMFileName = mAudioTrackPCMFilePath; 3991 } 3992 /** 3993 * For Video item, generate the PCM 3994 */ 3995 if (isVideo) { 3996 nativeGenerateRawAudio(inFileName, tempPCMFileName); 3997 } 3998 3999 nativeGenerateAudioGraph(tempPCMFileName, OutAudiGraphFileName, frameDuration, 4000 audioChannels, samplesCount); 4001 4002 /* once the audio graph file is generated, delete the pcm file */ 4003 if (isVideo) { 4004 new File(tempPCMFileName).delete(); 4005 } 4006 } 4007 4008 public void clearPreviewSurface(Surface surface) { 4009 nativeClearSurface(surface); 4010 } 4011 /** Native Methods */ 4012 native Properties getMediaProperties(String file) throws IllegalArgumentException, 4013 IllegalStateException, RuntimeException, Exception; 4014 4015 /** 4016 * Get the version of ManualEdit. 4017 * 4018 * @return version of ManualEdit 4019 * @throws RuntimeException if an error occurred 4020 * @see Version 4021 */ 4022 private static native Version getVersion() throws RuntimeException; 4023 4024 /** 4025 * Returns the video thumbnail in an array of integers. Output format is 4026 * ARGB8888. 4027 * 4028 * @param pixelArray the array that receives the pixelvalues 4029 * @param width width of the video thumbnail 4030 * @param height height of the video thumbnail 4031 * @param timeMS desired time of the thumbnail in ms 4032 * @return actual time in ms of the thumbnail generated 4033 * @throws IllegalStateException if the class has not been initialized 4034 * @throws IllegalArgumentException if the pixelArray is not available or 4035 * one of the dimensions is negative or zero or the time is 4036 * negative 4037 * @throws RuntimeException on runtime errors in native code 4038 */ 4039 private native int nativeGetPixels(String fileName, int[] pixelArray, int width, int height, 4040 long timeMS); 4041 4042 private native int nativeGetPixelsList(String fileName, int[] pixelArray, int width, int height, 4043 int timeMS, int nosofTN, long startTimeMs, long endTimeMs); 4044 4045 /** 4046 * Releases the JNI and cleans up the core native module.. Should be called 4047 * only after init( ) 4048 * 4049 * @throws IllegalStateException if the method could not be called 4050 */ 4051 private native void release() throws IllegalStateException, RuntimeException; 4052 4053 /* 4054 * Clear the preview surface 4055 */ 4056 private native void nativeClearSurface(Surface surface); 4057 4058 4059 /** 4060 * Stops the encoding. This method should only be called after encoding has 4061 * started using method <code> startEncoding</code> 4062 * 4063 * @throws IllegalStateException if the method could not be called 4064 */ 4065 private native void stopEncoding() throws IllegalStateException, RuntimeException; 4066 4067 4068 4069 private native void _init(String tempPath, String libraryPath) 4070 throws IllegalArgumentException, IllegalStateException, RuntimeException; 4071 4072 private native void nativeStartPreview(Surface mSurface, long fromMs, long toMs, 4073 int callbackAfterFrameCount, boolean loop) throws IllegalArgumentException, 4074 IllegalStateException, RuntimeException; 4075 4076 private native void nativePopulateSettings(EditSettings mEditSettings, 4077 PreviewClipProperties mProperties, AudioSettings mAudioSettings) 4078 throws IllegalArgumentException, IllegalStateException, RuntimeException; 4079 4080 private native int nativeRenderPreviewFrame(Surface mSurface, long timeMs, 4081 int surfaceWidth, int surfaceHeight) 4082 throws IllegalArgumentException, 4083 IllegalStateException, RuntimeException; 4084 4085 private native int nativeRenderMediaItemPreviewFrame(Surface mSurface, String filepath, 4086 int framewidth, int frameheight, int surfacewidth, int surfaceheight, long timeMs) 4087 throws IllegalArgumentException, IllegalStateException, RuntimeException; 4088 4089 private native void nativeStopPreview(); 4090 4091 private native int nativeGenerateAudioGraph(String pcmFilePath, String outGraphPath, 4092 int frameDuration, int channels, int sampleCount); 4093 4094 private native int nativeGenerateRawAudio(String InFileName, String PCMFileName); 4095 4096 private native int nativeGenerateClip(EditSettings editSettings) 4097 throws IllegalArgumentException, IllegalStateException, RuntimeException; 4098 4099} 4100