1 /* Copyright (c) 2012-2014, The Linux Foundataion. All rights reserved.
2 *
3 * Redistribution and use in source and binary forms, with or without
4 * modification, are permitted provided that the following conditions are
5 * met:
6 * * Redistributions of source code must retain the above copyright
7 * notice, this list of conditions and the following disclaimer.
8 * * Redistributions in binary form must reproduce the above
9 * copyright notice, this list of conditions and the following
10 * disclaimer in the documentation and/or other materials provided
11 * with the distribution.
12 * * Neither the name of The Linux Foundation nor the names of its
13 * contributors may be used to endorse or promote products derived
14 * from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
20 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
23 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
24 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
25 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
26 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 */
29
30 #include <stdlib.h>
31 #include <unistd.h>
32 #include <fcntl.h>
33 #include <time.h>
34 #include <semaphore.h>
35 #include <pthread.h>
36
37 #include <sys/types.h>
38 #include <sys/stat.h>
39 #include <sys/wait.h>
40
41 #include <ui/DisplayInfo.h>
42 #include <gui/Surface.h>
43 #include <gui/SurfaceComposerClient.h>
44 #include <gui/ISurfaceComposer.h>
45
46 #include <system/camera.h>
47
48 #include <camera/Camera.h>
49 #include <camera/ICamera.h>
50 #include <camera/CameraParameters.h>
51 #include <media/mediarecorder.h>
52
53 #include <utils/RefBase.h>
54 #include <utils/Mutex.h>
55 #include <utils/Condition.h>
56 #include <binder/IPCThreadState.h>
57 #include <binder/ProcessState.h>
58 #include <binder/IServiceManager.h>
59 #include <cutils/properties.h>
60 #include <cutils/memory.h>
61 #include <SkImageDecoder.h>
62 #include <SkImageEncoder.h>
63 #include <MediaCodec.h>
64 #include <OMX_IVCommon.h>
65 #include <foundation/AMessage.h>
66 #include <media/ICrypto.h>
67 #include <MediaMuxer.h>
68 #include <foundation/ABuffer.h>
69 #include <MediaErrors.h>
70 #include <gralloc_priv.h>
71 #include <math.h>
72
73 #include "qcamera_test.h"
74
75 #define ERROR(format, ...) printf( \
76 "%s[%d] : ERROR: "format"\n", __func__, __LINE__, ##__VA_ARGS__)
77 #define VIDEO_BUF_ALLIGN(size, allign) (((size) + (allign-1)) & (~(allign-1)))
78
79 namespace qcamera {
80
81 using namespace android;
82
83 int CameraContext::JpegIdx = 0;
84 int CameraContext::mPiPIdx = 0;
85 SkBitmap *CameraContext::skBMtmp[2];
86 sp<IMemory> CameraContext::PiPPtrTmp[2];
87
88 /*===========================================================================
89 * FUNCTION : previewCallback
90 *
91 * DESCRIPTION: preview callback preview mesages are enabled
92 *
93 * PARAMETERS :
94 * @mem : preview buffer
95 *
96 * RETURN : None
97 *==========================================================================*/
previewCallback(const sp<IMemory> & mem)98 void CameraContext::previewCallback(const sp<IMemory>& mem)
99 {
100 printf("PREVIEW Callback 0x%x", ( unsigned int ) mem->pointer());
101 uint8_t *ptr = (uint8_t*) mem->pointer();
102 printf("PRV_CB: 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x",
103 ptr[0],
104 ptr[1],
105 ptr[2],
106 ptr[3],
107 ptr[4],
108 ptr[5],
109 ptr[6],
110 ptr[7],
111 ptr[8],
112 ptr[9]);
113 }
114
115 /*===========================================================================
116 * FUNCTION : useLock
117 *
118 * DESCRIPTION: Mutex lock for CameraContext
119 *
120 * PARAMETERS : none
121 *
122 * RETURN : none
123 *==========================================================================*/
useLock()124 void CameraContext::useLock()
125 {
126 Mutex::Autolock l(mLock);
127 if ( mInUse ) {
128 mCond.wait(mLock);
129 } else {
130 mInUse = true;
131 }
132 }
133
134 /*===========================================================================
135 * FUNCTION : signalFinished
136 *
137 * DESCRIPTION: Mutex unlock CameraContext
138 *
139 * PARAMETERS : none
140 *
141 * RETURN : none
142 *==========================================================================*/
signalFinished()143 void CameraContext::signalFinished()
144 {
145 Mutex::Autolock l(mLock);
146 mInUse = false;
147 mCond.signal();
148 }
149
150 /*===========================================================================
151 * FUNCTION : mutexLock
152 *
153 * DESCRIPTION: Mutex lock for ViV Video
154 *
155 * PARAMETERS : none
156 *
157 * RETURN : none
158 *==========================================================================*/
mutexLock()159 void CameraContext::mutexLock()
160 {
161 Mutex::Autolock l(mViVLock);
162 if (mViVinUse ) {
163 mViVCond.wait(mViVLock);
164 } else {
165 mViVinUse = true;
166 }
167 }
168
169 /*===========================================================================
170 * FUNCTION : mutexUnLock
171 *
172 * DESCRIPTION: Mutex unlock for ViV Video
173 *
174 * PARAMETERS : none
175 *
176 * RETURN : none
177 *==========================================================================*/
mutexUnlock()178 void CameraContext::mutexUnlock()
179 {
180 Mutex::Autolock l(mViVLock);
181 mViVinUse = false;
182 mViVCond.signal();
183 }
184
185
186
187 /*===========================================================================
188 * FUNCTION : saveFile
189 *
190 * DESCRIPTION: helper function for saving buffers on filesystem
191 *
192 * PARAMETERS :
193 * @mem : buffer to save to filesystem
194 * @path: File path
195 *
196 * RETURN : status_t type of status
197 * NO_ERROR -- success
198 * none-zero failure code
199 *==========================================================================*/
saveFile(const sp<IMemory> & mem,String8 path)200 status_t CameraContext::saveFile(const sp<IMemory>& mem, String8 path)
201 {
202 unsigned char *buff = NULL;
203 int size;
204 int fd = -1;
205
206 if (mem == NULL) {
207 return BAD_VALUE;
208 }
209
210 fd = open(path, O_CREAT | O_WRONLY | O_TRUNC, 0655);
211 if(fd < 0) {
212 printf("Unable to open file %s %s\n", path.string(), strerror(fd));
213 return -errno;
214 }
215
216 size = mem->size();
217 if (size <= 0) {
218 printf("IMemory object is of zero size\n");
219 close(fd);
220 return BAD_VALUE;
221 }
222
223 buff = (unsigned char *)mem->pointer();
224 if (!buff) {
225 printf("Buffer pointer is invalid\n");
226 close(fd);
227 return BAD_VALUE;
228 }
229
230 if ( size != write(fd, buff, size) ) {
231 printf("Bad Write error (%d)%s\n",
232 errno,
233 strerror(errno));
234 close(fd);
235 return INVALID_OPERATION;
236 }
237
238 printf("%s: buffer=%08X, size=%d stored at %s\n",
239 __FUNCTION__, (int)buff, size, path.string());
240
241 if (fd >= 0)
242 close(fd);
243
244 return NO_ERROR;
245 }
246
247 /*===========================================================================
248 * FUNCTION : PiPCopyToOneFile
249 *
250 * DESCRIPTION: Copy the smaller picture to the bigger one
251 *
252 * PARAMETERS :
253 * @bitmap0 : Decoded image buffer 0
254 * @bitmap1 : Decoded image buffer 1
255 *
256 * RETURN : decoded picture in picture in SkBitmap
257 *==========================================================================*/
PiPCopyToOneFile(SkBitmap * bitmap0,SkBitmap * bitmap1)258 SkBitmap * CameraContext::PiPCopyToOneFile(
259 SkBitmap *bitmap0, SkBitmap *bitmap1)
260 {
261 int size0;
262 int size1;
263 SkBitmap *src;
264 SkBitmap *dst;
265 unsigned int dstOffset;
266 unsigned int srcOffset;
267
268 if (bitmap0 == NULL && bitmap1 == NULL) {
269 return NULL;
270 }
271
272 size0 = bitmap0->getSize();
273 if (size0 <= 0) {
274 printf("Decoded image 0 is of zero size\n");
275 return NULL;
276 }
277
278 size1 = bitmap1->getSize();
279 if (size1 <= 0) {
280 printf("Decoded image 1 is of zero size\n");
281 return NULL;
282 }
283
284 if (size0 > size1) {
285 dst = bitmap0;
286 src = bitmap1;
287 } else if (size1 > size0){
288 dst = bitmap1;
289 src = bitmap0;
290 } else {
291 printf("Picture size should be with different size!\n");
292 return NULL;
293 }
294
295 for(int i=0; i<src->height(); i++) {
296 dstOffset = i*(dst->width())*mfmtMultiplier;
297 srcOffset = i*(src->width())*mfmtMultiplier;
298 memcpy(((unsigned char *) dst->getPixels())+dstOffset,
299 ((unsigned char *) src->getPixels())+srcOffset,
300 src->width()*mfmtMultiplier);
301 }
302
303 return dst;
304 }
305
306 /*===========================================================================
307 * FUNCTION : decodeJPEG
308 *
309 * DESCRIPTION: decode jpeg input buffer.
310 *
311 * PARAMETERS :
312 * @mem : buffer to decode
313 *
314 * RETURN : decoded picture in SkBitmap
315
316 *==========================================================================*/
decodeJPEG(const sp<IMemory> & mem)317 SkBitmap *CameraContext::decodeJPEG(const sp<IMemory>& mem)
318 {
319 SkBitmap *skBM;
320 skBM = new SkBitmap; //Deleted in encodeJPEG (skBMtmp[0] and skBMtmp[1])
321 SkBitmap::Config prefConfig = SkBitmap::kARGB_8888_Config;
322 const void *buff = NULL;
323 int size;
324
325 buff = (const void *)mem->pointer();
326 size= mem->size();
327
328 switch(prefConfig) {
329 case SkBitmap::kARGB_8888_Config:
330 {
331 mfmtMultiplier = 4;
332 }
333 break;
334
335 case SkBitmap::kARGB_4444_Config:
336 {
337 mfmtMultiplier = 2;
338 }
339 break;
340
341 case SkBitmap::kRGB_565_Config:
342 {
343 mfmtMultiplier = 2;
344 }
345 break;
346
347 case SkBitmap::kIndex8_Config:
348 {
349 mfmtMultiplier = 4;
350 }
351 break;
352
353 case SkBitmap::kA8_Config:
354 {
355 mfmtMultiplier = 4;
356 }
357 break;
358
359 default:
360 {
361 mfmtMultiplier = 0;
362 printf("Decode format is not correct!\n");
363 }
364 break;
365 }
366
367 if (SkImageDecoder::DecodeMemory(buff, size, skBM, prefConfig,
368 SkImageDecoder::kDecodePixels_Mode) == false) {
369 printf("%s():%d:: Failed during jpeg decode\n",__FUNCTION__,__LINE__);
370 return NULL;
371 }
372
373 return skBM;
374 }
375
376 /*===========================================================================
377 * FUNCTION : encodeJPEG
378 *
379 * DESCRIPTION: encode the decoded input buffer.
380 *
381 * PARAMETERS :
382 * @stream : SkWStream
383 * @bitmap : SkBitmap decoded image to encode
384 * @path : File path
385 *
386 * RETURN : status_t type of status
387 * NO_ERROR -- success
388 * none-zero failure code
389
390 *==========================================================================*/
encodeJPEG(SkWStream * stream,const SkBitmap * bitmap,String8 path)391 status_t CameraContext::encodeJPEG(SkWStream * stream,
392 const SkBitmap *bitmap, String8 path)
393 {
394 int qFactor = 100;
395 long len;
396 status_t ret;
397 unsigned char *buff;
398 unsigned char temp;
399
400 skJpegEnc = SkImageEncoder::Create(SkImageEncoder::kJPEG_Type);
401
402 if (skJpegEnc->encodeStream(stream, *bitmap, qFactor) == false) {
403 return BAD_VALUE;
404 }
405 printf("%s: buffer=%08X, size=%d stored at %s\n",
406 __FUNCTION__, (int)bitmap->getPixels(),
407 bitmap->getSize(), path.string());
408 delete skBMtmp[0];
409 delete skBMtmp[1];
410
411 FILE *fh = fopen(path.string(), "r+");
412 if ( !fh ) {
413 printf("Could not open file %s\n", path.string());
414 return BAD_VALUE;
415 }
416
417 fseek(fh, 0, SEEK_END);
418 len = ftell(fh);
419 rewind(fh);
420
421 if( !len ) {
422 printf("File %s is empty !\n", path.string());
423 fclose(fh);
424 return BAD_VALUE;
425 }
426
427 buff = (unsigned char*)malloc(len);
428 if (!buff) {
429 printf("Cannot allocate memory for buffer reading!\n");
430 return BAD_VALUE;
431 }
432
433 ret = fread(buff, 1, len, fh);
434 if (ret != len) {
435 printf("Reading error\n");
436 return BAD_VALUE;
437 }
438
439 ret = ReadSectionsFromBuffer(buff, len, READ_ALL);
440 if (ret != NO_ERROR) {
441 printf("Cannot read sections from buffer\n");
442 DiscardData();
443 DiscardSections();
444 return BAD_VALUE;
445 }
446 free(buff);
447 rewind(fh);
448
449 temp = 0xff;
450 ret = fwrite(&temp, sizeof(unsigned char), 1, fh);
451 if (ret != 1) {
452 printf("Writing error\n");
453 }
454 temp = 0xd8;
455 fwrite(&temp, sizeof(unsigned char), 1, fh);
456
457 for (int i=0; i<mSectionsRead; i++) {
458 switch((mSections[i].Type)) {
459
460 case 0x123:
461 fwrite(mSections[i].Data, sizeof(unsigned char),
462 mSections[i].Size, fh);
463 break;
464
465 case 0xe0:
466 temp = 0xff;
467 fwrite(&temp, sizeof(unsigned char), 1, fh);
468 temp = 0xe1;
469 fwrite(&temp, sizeof(unsigned char), 1, fh);
470 fwrite(mJEXIFSection.Data, sizeof(unsigned char),
471 mJEXIFSection.Size, fh);
472 break;
473
474 default:
475 temp = 0xff;
476 fwrite(&temp, sizeof(unsigned char), 1, fh);
477 fwrite(&mSections[i].Type, sizeof(unsigned char), 1, fh);
478 fwrite(mSections[i].Data, sizeof(unsigned char),
479 mSections[i].Size, fh);
480 break;
481 }
482 }
483 free(mJEXIFSection.Data);
484 DiscardData();
485 DiscardSections();
486 fclose(fh);
487
488 ret = NO_ERROR;
489
490 return ret;
491 }
492
493 /*===========================================================================
494 * FUNCTION : readSectionsFromBuffer
495 *
496 * DESCRIPTION: read all jpeg sections of input buffer.
497 *
498 * PARAMETERS :
499 * @mem : buffer to read from Metadata Sections
500 * @buffer_size: buffer size
501 * @ReadMode: Read mode - all, jpeg or exif
502 *
503 * RETURN : status_t type of status
504 * NO_ERROR -- success
505 * none-zero failure code
506 *==========================================================================*/
ReadSectionsFromBuffer(unsigned char * buffer,unsigned int buffer_size,ReadMode_t ReadMode)507 status_t CameraContext::ReadSectionsFromBuffer (unsigned char *buffer,
508 unsigned int buffer_size, ReadMode_t ReadMode)
509 {
510 int a;
511 unsigned int pos = 0;
512 int HaveCom = 0;
513 mSectionsAllocated = 10;
514
515 mSections = (Sections_t *)malloc(sizeof(Sections_t) * mSectionsAllocated);
516
517 if (!buffer) {
518 printf("Input buffer is null\n");
519 return BAD_VALUE;
520 }
521
522 if (buffer_size < 1) {
523 printf("Input size is 0\n");
524 return BAD_VALUE;
525 }
526
527 a = (int) buffer[pos++];
528
529 if (a != 0xff || buffer[pos++] != M_SOI){
530 printf("No valid image\n");
531 return BAD_VALUE;
532 }
533
534 for(;;){
535 int itemlen;
536 int marker = 0;
537 int ll,lh;
538 unsigned char * Data;
539
540 CheckSectionsAllocated();
541
542 for (a = 0; a <= 16; a++){
543 marker = buffer[pos++];
544 if (marker != 0xff) break;
545
546 if (a >= 16){
547 fprintf(stderr,"too many padding bytes\n");
548 return BAD_VALUE;
549 }
550 }
551
552 mSections[mSectionsRead].Type = marker;
553
554 // Read the length of the section.
555 lh = buffer[pos++];
556 ll = buffer[pos++];
557
558 itemlen = (lh << 8) | ll;
559
560 if (itemlen < 2) {
561 ALOGE("invalid marker");
562 return BAD_VALUE;
563 }
564
565 mSections[mSectionsRead].Size = itemlen;
566
567 Data = (unsigned char *)malloc(itemlen);
568 if (Data == NULL) {
569 ALOGE("Could not allocate memory");
570 return NO_MEMORY;
571 }
572 mSections[mSectionsRead].Data = Data;
573
574 // Store first two pre-read bytes.
575 Data[0] = (unsigned char)lh;
576 Data[1] = (unsigned char)ll;
577
578 if (pos+itemlen-2 > buffer_size) {
579 ALOGE("Premature end of file?");
580 return BAD_VALUE;
581 }
582
583 memcpy(Data+2, buffer+pos, itemlen-2); // Read the whole section.
584 pos += itemlen-2;
585
586 mSectionsRead += 1;
587
588 switch(marker){
589
590 case M_SOS: // stop before hitting compressed data
591 // If reading entire image is requested, read the rest of the
592 // data.
593 if (ReadMode & READ_IMAGE){
594 int size;
595 // Determine how much file is left.
596 size = buffer_size - pos;
597
598 if (size < 1) {
599 ALOGE("could not read the rest of the image");
600 return BAD_VALUE;
601 }
602 Data = (unsigned char *)malloc(size);
603 if (Data == NULL) {
604 ALOGE("%d: could not allocate data for entire "
605 "image size: %d", __LINE__, size);
606 return BAD_VALUE;
607 }
608
609 memcpy(Data, buffer+pos, size);
610
611 CheckSectionsAllocated();
612 mSections[mSectionsRead].Data = Data;
613 mSections[mSectionsRead].Size = size;
614 mSections[mSectionsRead].Type = PSEUDO_IMAGE_MARKER;
615 mSectionsRead ++;
616 mHaveAll = 1;
617 }
618 return NO_ERROR;
619
620 case M_EOI: // in case it's a tables-only JPEG stream
621 ALOGE("No image in jpeg!\n");
622 return BAD_VALUE;
623
624 case M_COM: // Comment section
625 if (HaveCom || ((ReadMode & READ_METADATA) == 0)){
626 // Discard this section.
627 free(mSections[--mSectionsRead].Data);
628 }
629 break;
630
631 case M_JFIF:
632 // Regular jpegs always have this tag, exif images have the
633 // exif marker instead, althogh ACDsee will write images
634 // with both markers.
635 // this program will re-create this marker on absence of exif
636 // marker.
637 // hence no need to keep the copy from the file.
638 if (ReadMode & READ_METADATA){
639 if (memcmp(Data+2, "JFIF", 4) == 0) {
640 break;
641 }
642 free(mSections[--mSectionsRead].Data);
643 }
644 break;
645
646 case M_EXIF:
647 // There can be different section using the same marker.
648 if (ReadMode & READ_METADATA){
649 if (memcmp(Data+2, "Exif", 4) == 0){
650 break;
651 }else if (memcmp(Data+2, "http:", 5) == 0){
652 // Change tag for internal purposes.
653 mSections[mSectionsRead-1].Type = M_XMP;
654 break;
655 }
656 }
657 // Oterwise, discard this section.
658 free(mSections[--mSectionsRead].Data);
659 break;
660
661 case M_IPTC:
662 if (ReadMode & READ_METADATA){
663 // Note: We just store the IPTC section.
664 // Its relatively straightforward
665 // and we don't act on any part of it,
666 // so just display it at parse time.
667 }else{
668 free(mSections[--mSectionsRead].Data);
669 }
670 break;
671
672 case M_SOF0:
673 case M_SOF1:
674 case M_SOF2:
675 case M_SOF3:
676 case M_SOF5:
677 case M_SOF6:
678 case M_SOF7:
679 case M_SOF9:
680 case M_SOF10:
681 case M_SOF11:
682 case M_SOF13:
683 case M_SOF14:
684 case M_SOF15:
685 break;
686 default:
687 // Skip any other sections.
688 break;
689 }
690 }
691 return NO_ERROR;
692 }
693
694 /*===========================================================================
695 * FUNCTION : CheckSectionsAllocated
696 *
697 * DESCRIPTION: Check allocated jpeg sections.
698 *
699 * PARAMETERS : none
700 *
701 * RETURN : none
702
703 *==========================================================================*/
CheckSectionsAllocated(void)704 void CameraContext::CheckSectionsAllocated(void)
705 {
706 if (mSectionsRead > mSectionsAllocated){
707 ALOGE("allocation screw up");
708 }
709 if (mSectionsRead >= mSectionsAllocated){
710 mSectionsAllocated += mSectionsAllocated +1;
711 mSections = (Sections_t *)realloc(mSections,
712 sizeof(Sections_t) * mSectionsAllocated);
713 if (mSections == NULL){
714 ALOGE("could not allocate data for entire image");
715 }
716 }
717 }
718
719 /*===========================================================================
720 * FUNCTION : findSection
721 *
722 * DESCRIPTION: find the desired Section of the JPEG buffer.
723 *
724 * PARAMETERS :
725 * @SectionType: Section type
726 *
727 * RETURN : return the found section
728
729 *==========================================================================*/
FindSection(int SectionType)730 CameraContext::Sections_t *CameraContext::FindSection(int SectionType)
731 {
732 int a;
733
734 for (a = 0; a < mSectionsRead; a++){
735 if (mSections[a].Type == SectionType){
736 return &mSections[a];
737 }
738 }
739 // Could not be found.
740 return NULL;
741 }
742
743
744 /*===========================================================================
745 * FUNCTION : DiscardData
746 *
747 * DESCRIPTION: DiscardData
748 *
749 * PARAMETERS : none
750 *
751 * RETURN : none
752
753 *==========================================================================*/
DiscardData()754 void CameraContext::DiscardData()
755 {
756 int a;
757
758 for (a = 0; a < mSectionsRead; a++){
759 free(mSections[a].Data);
760 }
761
762 mSectionsRead = 0;
763 mHaveAll = 0;
764 }
765
766 /*===========================================================================
767 * FUNCTION : DiscardSections
768 *
769 * DESCRIPTION: Discard allocated sections
770 *
771 * PARAMETERS : none
772 *
773 * RETURN : none
774
775 *==========================================================================*/
DiscardSections()776 void CameraContext::DiscardSections()
777 {
778 free(mSections);
779 mSectionsAllocated = 0;
780 mHaveAll = 0;
781 }
782
783 /*===========================================================================
784 * FUNCTION : notify
785 *
786 * DESCRIPTION: notify callback
787 *
788 * PARAMETERS :
789 * @msgType : type of callback
790 * @ext1: extended parameters
791 * @ext2: extended parameters
792 *
793 * RETURN : None
794 *==========================================================================*/
notify(int32_t msgType,int32_t ext1,int32_t ext2)795 void CameraContext::notify(int32_t msgType, int32_t ext1, int32_t ext2)
796 {
797 printf("Notify cb: %d %d %d\n", msgType, ext1, ext2);
798
799 if (( msgType & CAMERA_MSG_PREVIEW_FRAME) && (ext1 == CAMERA_FRAME_DATA_FD)) {
800 int fd = dup(ext2);
801 printf("notify Preview Frame fd: %d dup fd: %d\n", ext2, fd);
802 close(fd);
803 }
804
805 if ( msgType & CAMERA_MSG_FOCUS ) {
806 printf("AutoFocus %s \n",
807 (ext1) ? "OK" : "FAIL");
808 }
809
810 if ( msgType & CAMERA_MSG_SHUTTER ) {
811 printf("Shutter done \n");
812 }
813
814 if ( msgType & CAMERA_MSG_ERROR) {
815 printf("Camera Test CAMERA_MSG_ERROR\n");
816 stopPreview();
817 closeCamera();
818 }
819 }
820
821 /*===========================================================================
822 * FUNCTION : postData
823 *
824 * DESCRIPTION: handles data callbacks
825 *
826 * PARAMETERS :
827 * @msgType : type of callback
828 * @dataPtr: buffer data
829 * @metadata: additional metadata where available
830 *
831 * RETURN : None
832 *==========================================================================*/
postData(int32_t msgType,const sp<IMemory> & dataPtr,camera_frame_metadata_t * metadata)833 void CameraContext::postData(int32_t msgType,
834 const sp<IMemory>& dataPtr,
835 camera_frame_metadata_t *metadata)
836 {
837 Size currentPictureSize = mSupportedPictureSizes.itemAt(
838 mCurrentPictureSizeIdx);
839 unsigned char *buff = NULL;
840 int size;
841 status_t ret = 0;
842
843 memset(&mJEXIFSection, 0, sizeof(mJEXIFSection)),
844
845 printf("Data cb: %d\n", msgType);
846
847 if ( msgType & CAMERA_MSG_PREVIEW_FRAME ) {
848 previewCallback(dataPtr);
849 }
850
851 if ( msgType & CAMERA_MSG_RAW_IMAGE ) {
852 printf("RAW done \n");
853 }
854
855 if (msgType & CAMERA_MSG_POSTVIEW_FRAME) {
856 printf("Postview frame \n");
857 }
858
859 if (msgType & CAMERA_MSG_COMPRESSED_IMAGE ) {
860 String8 jpegPath;
861 jpegPath = jpegPath.format("/sdcard/img_%d.jpg", JpegIdx);
862 if (!mPiPCapture) {
863 // Normal capture case
864 printf("JPEG done\n");
865 saveFile(dataPtr, jpegPath);
866 JpegIdx++;
867 } else {
868 // PiP capture case
869 SkFILEWStream *wStream;
870 skBMtmp[mPiPIdx] = decodeJPEG(dataPtr);
871
872 mWidthTmp[mPiPIdx] = currentPictureSize.width;
873 mHeightTmp[mPiPIdx] = currentPictureSize.height;
874 PiPPtrTmp[mPiPIdx] = dataPtr;
875 // If there are two jpeg buffers
876 if (mPiPIdx == 1) {
877 printf("PiP done\n");
878
879 // Find the the capture with higher width and height and read
880 // its jpeg sections
881 if ((mWidthTmp[0]*mHeightTmp[0]) >
882 (mWidthTmp[1]*mHeightTmp[1])) {
883 buff = (unsigned char *)PiPPtrTmp[0]->pointer();
884 size = PiPPtrTmp[0]->size();
885 } else if ((mWidthTmp[0]*mHeightTmp[0]) <
886 (mWidthTmp[1]*mHeightTmp[1])) {
887 buff = (unsigned char *)PiPPtrTmp[1]->pointer();
888 size = PiPPtrTmp[1]->size();
889 } else {
890 printf("Cannot take PiP. Images are with the same width"
891 " and height size!!!\n");
892 return;
893 }
894
895 if (buff != NULL && size != 0) {
896 ret = ReadSectionsFromBuffer(buff, size, READ_ALL);
897 if (ret != NO_ERROR) {
898 printf("Cannot read sections from buffer\n");
899 DiscardData();
900 DiscardSections();
901 return;
902 }
903
904 mJEXIFTmp = FindSection(M_EXIF);
905 mJEXIFSection = *mJEXIFTmp;
906 mJEXIFSection.Data =
907 (unsigned char*)malloc(mJEXIFTmp->Size);
908 memcpy(mJEXIFSection.Data,
909 mJEXIFTmp->Data, mJEXIFTmp->Size);
910 DiscardData();
911 DiscardSections();
912
913 wStream = new SkFILEWStream(jpegPath.string());
914 skBMDec = PiPCopyToOneFile(skBMtmp[0], skBMtmp[1]);
915 if (encodeJPEG(wStream, skBMDec, jpegPath) != false) {
916 printf("%s():%d:: Failed during jpeg encode\n",
917 __FUNCTION__,__LINE__);
918 return;
919 }
920 mPiPIdx = 0;
921 JpegIdx++;
922 delete wStream;
923 }
924 } else {
925 mPiPIdx++;
926 }
927 disablePiPCapture();
928 }
929 }
930
931 if ( ( msgType & CAMERA_MSG_PREVIEW_METADATA ) &&
932 ( NULL != metadata ) ) {
933 printf("Face detected %d \n", metadata->number_of_faces);
934 }
935
936 signalFinished();
937 }
938
939 /*===========================================================================
940 * FUNCTION : postDataTimestamp
941 *
942 * DESCRIPTION: handles recording callbacks
943 *
944 * PARAMETERS :
945 * @timestamp : timestamp of buffer
946 * @msgType : type of buffer
947 * @dataPtr : buffer data
948 *
949 * RETURN : None
950 *==========================================================================*/
postDataTimestamp(nsecs_t timestamp,int32_t msgType,const sp<IMemory> & dataPtr)951 void CameraContext::postDataTimestamp(nsecs_t timestamp,
952 int32_t msgType,
953 const sp<IMemory>& dataPtr)
954 {
955 printf("Recording cb: %d %lld %p\n", msgType, timestamp, dataPtr.get());
956 }
957
958 /*===========================================================================
959 * FUNCTION : dataCallbackTimestamp
960 *
961 * DESCRIPTION: handles recording callbacks. Used for ViV recording
962 *
963 * PARAMETERS :
964 * @timestamp : timestamp of buffer
965 * @msgType : type of buffer
966 * @dataPtr : buffer data
967 *
968 * RETURN : None
969 *==========================================================================*/
dataCallbackTimestamp(nsecs_t timestamp,int32_t msgType,const sp<IMemory> & dataPtr)970 void CameraContext::dataCallbackTimestamp(nsecs_t timestamp,
971 int32_t msgType,
972 const sp<IMemory>& dataPtr)
973 {
974 mutexLock();
975 // Not needed check. Just avoiding warnings of not used variables.
976 if (timestamp > 0)
977 timestamp = 0;
978 // Not needed check. Just avoiding warnings of not used variables.
979 if (msgType > 0)
980 msgType = 0;
981 int i = 0;
982 void * srcBuff = NULL;
983 void * dstBuff = NULL;
984
985 size_t srcYStride = 0, dstYStride = 0;
986 size_t srcUVStride = 0, dstUVStride = 0;
987 size_t srcYScanLines = 0, dstYScanLines = 0;
988 size_t srcUVScanLines = 0, dstUVScanLines = 0;
989 size_t srcOffset = 0, dstOffset = 0;
990 size_t srcBaseOffset = 0;
991 size_t dstBaseOffset = 0;
992 Size currentVideoSize = mSupportedVideoSizes.itemAt(mCurrentVideoSizeIdx);
993 status_t err = NO_ERROR;
994 ANativeWindowBuffer* anb = NULL;
995
996 dstBuff = (void *) dataPtr->pointer();
997
998 if (mCameraIndex == mInterpr->mViVVid.sourceCameraID) {
999 srcYStride = calcStride(currentVideoSize.width);
1000 srcUVStride = calcStride(currentVideoSize.width);
1001 srcYScanLines = calcYScanLines(currentVideoSize.height);
1002 srcUVScanLines = calcUVScanLines(currentVideoSize.height);
1003 mInterpr->mViVBuff.srcWidth = currentVideoSize.width;
1004 mInterpr->mViVBuff.srcHeight = currentVideoSize.height;
1005
1006
1007 mInterpr->mViVBuff.YStride = srcYStride;
1008 mInterpr->mViVBuff.UVStride = srcUVStride;
1009 mInterpr->mViVBuff.YScanLines = srcYScanLines;
1010 mInterpr->mViVBuff.UVScanLines = srcUVScanLines;
1011
1012 memcpy( mInterpr->mViVBuff.buff, (void *) dataPtr->pointer(),
1013 mInterpr->mViVBuff.buffSize);
1014
1015 mInterpr->mViVVid.isBuffValid = true;
1016 } else if (mCameraIndex == mInterpr->mViVVid.destinationCameraID) {
1017 if(mInterpr->mViVVid.isBuffValid == true) {
1018 dstYStride = calcStride(currentVideoSize.width);
1019 dstUVStride = calcStride(currentVideoSize.width);
1020 dstYScanLines = calcYScanLines(currentVideoSize.height);
1021 dstUVScanLines = calcUVScanLines(currentVideoSize.height);
1022
1023 srcYStride = mInterpr->mViVBuff.YStride;
1024 srcUVStride = mInterpr->mViVBuff.UVStride;
1025 srcYScanLines = mInterpr->mViVBuff.YScanLines;
1026 srcUVScanLines = mInterpr->mViVBuff.UVScanLines;
1027
1028
1029 for (i=0; i<(int) mInterpr->mViVBuff.srcHeight; i++) {
1030 srcOffset = i*srcYStride;
1031 dstOffset = i*dstYStride;
1032 memcpy((unsigned char *) dstBuff + dstOffset,
1033 (unsigned char *) mInterpr->mViVBuff.buff +
1034 srcOffset, mInterpr->mViVBuff.srcWidth);
1035 }
1036 srcBaseOffset = srcYStride * srcYScanLines;
1037 dstBaseOffset = dstYStride * dstYScanLines;
1038 for (i=0;i<(int) mInterpr->mViVBuff.srcHeight/2;i++) {
1039 srcOffset = i*srcUVStride + srcBaseOffset;
1040 dstOffset = i*dstUVStride + dstBaseOffset;
1041 memcpy((unsigned char *) dstBuff + dstOffset,
1042 (unsigned char *) mInterpr->mViVBuff.buff +
1043 srcOffset, mInterpr->mViVBuff.srcWidth);
1044 }
1045
1046 err = native_window_dequeue_buffer_and_wait(
1047 mInterpr->mViVVid.ANW.get(),&anb);
1048 if (err != NO_ERROR) {
1049 printf("Cannot dequeue anb for sensor %d!!!\n", mCameraIndex);
1050 return;
1051 }
1052 mInterpr->mViVVid.graphBuf = new GraphicBuffer(anb, false);
1053 if(NULL == mInterpr->mViVVid.graphBuf.get()) {
1054 printf("Invalid Graphic buffer\n");
1055 return;
1056 }
1057 err = mInterpr->mViVVid.graphBuf->lock(
1058 GRALLOC_USAGE_SW_WRITE_OFTEN,
1059 (void**)(&mInterpr->mViVVid.mappedBuff));
1060 if (err != NO_ERROR) {
1061 printf("Graphic buffer could not be locked %d!!!\n", err);
1062 return;
1063 }
1064
1065 srcYStride = dstYStride;
1066 srcUVStride = dstUVStride;
1067 srcYScanLines = dstYScanLines;
1068 srcUVScanLines = dstUVScanLines;
1069 srcBuff = dstBuff;
1070
1071 for (i=0; i<(int) currentVideoSize.height; i++) {
1072 srcOffset = i*srcYStride;
1073 dstOffset = i*dstYStride;
1074 memcpy((unsigned char *) mInterpr->mViVVid.mappedBuff +
1075 dstOffset, (unsigned char *) srcBuff +
1076 srcOffset, currentVideoSize.width);
1077 }
1078
1079 srcBaseOffset = srcYStride * srcYScanLines;
1080 dstBaseOffset = dstUVStride * currentVideoSize.height;
1081
1082 for (i=0;i<(int) currentVideoSize.height/2;i++) {
1083 srcOffset = i*srcUVStride + srcBaseOffset;
1084 dstOffset = i*dstUVStride + dstBaseOffset;
1085 memcpy((unsigned char *) mInterpr->mViVVid.mappedBuff +
1086 dstOffset, (unsigned char *) srcBuff +
1087 srcOffset, currentVideoSize.width);
1088 }
1089
1090
1091 mInterpr->mViVVid.graphBuf->unlock();
1092
1093 err = mInterpr->mViVVid.ANW->queueBuffer(
1094 mInterpr->mViVVid.ANW.get(), anb, -1);
1095 if(err)
1096 printf("Failed to enqueue buffer to recorder!!!\n");
1097 }
1098 }
1099 mCamera->releaseRecordingFrame(dataPtr);
1100
1101 mutexUnlock();
1102 }
1103
1104 /*===========================================================================
1105 * FUNCTION : ViVEncoderThread
1106 *
1107 * DESCRIPTION: Creates a separate thread for ViV recording
1108 *
1109 * PARAMETERS : None
1110 *
1111 * RETURN : None
1112 *==========================================================================*/
ViVEncoderThread()1113 status_t Interpreter::ViVEncoderThread()
1114 {
1115 int ret = NO_ERROR;
1116 pthread_attr_t attr;
1117 pthread_attr_init(&attr);
1118
1119 ret = pthread_create(&mViVEncThread, &attr, ThreadWrapper, this);
1120 ret = pthread_attr_destroy(&attr);
1121
1122 return ret;
1123 }
1124
1125 /*===========================================================================
1126 * FUNCTION : ThreadWrapper
1127 *
1128 * DESCRIPTION: Helper function for for ViV recording thread
1129 *
1130 * PARAMETERS : Interpreter context
1131 *
1132 * RETURN : None
1133 *==========================================================================*/
ThreadWrapper(void * context)1134 void *Interpreter::ThreadWrapper(void *context) {
1135 Interpreter *writer = static_cast<Interpreter *>(context);
1136 writer->ViVEncode();
1137 return NULL;
1138 }
1139
1140 /*===========================================================================
1141 * FUNCTION : ViVEncode
1142 *
1143 * DESCRIPTION: Thread for ViV encode. Buffers from video codec are sent to
1144 * muxer and saved in a file.
1145 *
1146 * PARAMETERS : Interpreter context
1147 *
1148 * RETURN : None
1149 *==========================================================================*/
ViVEncode()1150 void Interpreter::ViVEncode()
1151 {
1152 status_t err = NO_ERROR;
1153 ssize_t trackIdx = -1;
1154 uint32_t debugNumFrames = 0;
1155
1156 size_t bufIndex, offset, size;
1157 int64_t ptsUsec;
1158 uint32_t flags;
1159 bool DoRecording = true;
1160
1161
1162 err = mTestContext->mViVVid.codec->getOutputBuffers(
1163 &mTestContext->mViVVid.buffers);
1164 if (err != NO_ERROR) {
1165 printf("Unable to get output buffers (err=%d)\n", err);
1166 }
1167
1168 while (DoRecording) {
1169 err = mTestContext->mViVVid.codec->dequeueOutputBuffer(
1170 &bufIndex,
1171 &offset,
1172 &size,
1173 &ptsUsec,
1174 &flags, -1);
1175
1176 switch (err) {
1177
1178 case NO_ERROR:
1179 // got a buffer
1180 if ((flags & MediaCodec::BUFFER_FLAG_CODECCONFIG) != 0) {
1181 // ignore this -- we passed the CSD into MediaMuxer when
1182 // we got the format change notification
1183 size = 0;
1184 }
1185 if (size != 0) {
1186 // If the virtual display isn't providing us with timestamps,
1187 // use the current time.
1188 if (ptsUsec == 0) {
1189 ptsUsec = systemTime(SYSTEM_TIME_MONOTONIC) / 1000;
1190 }
1191
1192 // The MediaMuxer docs are unclear, but it appears that we
1193 // need to pass either the full set of BufferInfo flags, or
1194 // (flags & BUFFER_FLAG_SYNCFRAME).
1195 err = mTestContext->mViVVid.muxer->writeSampleData(
1196 mTestContext->mViVVid.buffers[bufIndex],
1197 trackIdx,
1198 ptsUsec,
1199 flags);
1200 if (err != NO_ERROR) {
1201 fprintf(stderr, "Failed writing data to muxer (err=%d)\n",
1202 err);
1203 }
1204 debugNumFrames++;
1205 }
1206 err = mTestContext->mViVVid.codec->releaseOutputBuffer(bufIndex);
1207 if (err != NO_ERROR) {
1208 fprintf(stderr, "Unable to release output buffer (err=%d)\n",
1209 err);
1210 }
1211 if ((flags & MediaCodec::BUFFER_FLAG_EOS) != 0) {
1212 // Not expecting EOS from SurfaceFlinger. Go with it.
1213 printf("Received end-of-stream\n");
1214 //DoRecording = false;
1215 }
1216 break;
1217 case -EAGAIN: // INFO_TRY_AGAIN_LATER
1218 ALOGV("Got -EAGAIN, looping");
1219 break;
1220 case INFO_FORMAT_CHANGED: // INFO_OUTPUT_FORMAT_CHANGED
1221 {
1222 // format includes CSD, which we must provide to muxer
1223 sp<AMessage> newFormat;
1224 mTestContext->mViVVid.codec->getOutputFormat(&newFormat);
1225 trackIdx = mTestContext->mViVVid.muxer->addTrack(newFormat);
1226 err = mTestContext->mViVVid.muxer->start();
1227 if (err != NO_ERROR) {
1228 printf("Unable to start muxer (err=%d)\n", err);
1229 }
1230 }
1231 break;
1232 case INFO_OUTPUT_BUFFERS_CHANGED: // INFO_OUTPUT_BUFFERS_CHANGED
1233 // not expected for an encoder; handle it anyway
1234 ALOGV("Encoder buffers changed");
1235 err = mTestContext->mViVVid.codec->getOutputBuffers(
1236 &mTestContext->mViVVid.buffers);
1237 if (err != NO_ERROR) {
1238 printf("Unable to get new output buffers (err=%d)\n", err);
1239 }
1240 break;
1241 case INVALID_OPERATION:
1242 DoRecording = false;
1243 break;
1244 default:
1245 printf("Got weird result %d from dequeueOutputBuffer\n", err);
1246 break;
1247 }
1248 }
1249
1250 return;
1251 }
1252
1253
1254 /*===========================================================================
1255 * FUNCTION : calcBufferSize
1256 *
1257 * DESCRIPTION: Temp buffer size calculation. Temp buffer is used to store
1258 * the buffer from the camera with smaller resolution. It is
1259 * copied to the buffer from camera with higher resolution.
1260 *
1261 * PARAMETERS :
1262 * @width : video size width
1263 * @height : video size height
1264 *
1265 * RETURN : size_t
1266 *==========================================================================*/
calcBufferSize(int width,int height)1267 size_t CameraContext::calcBufferSize(int width, int height)
1268 {
1269 size_t size = 0;
1270 size_t UVAlignment;
1271 size_t YPlane, UVPlane, YStride, UVStride, YScanlines, UVScanlines;
1272 if (!width || !height) {
1273 return size;
1274 }
1275 UVAlignment = 4096;
1276 YStride = calcStride(width);
1277 UVStride = calcStride(width);
1278 YScanlines = calcYScanLines(height);
1279 UVScanlines = calcUVScanLines(height);
1280 YPlane = YStride * YScanlines;
1281 UVPlane = UVStride * UVScanlines + UVAlignment;
1282 size = YPlane + UVPlane;
1283 size = VIDEO_BUF_ALLIGN(size, 4096);
1284
1285 return size;
1286 }
1287
1288 /*===========================================================================
1289 * FUNCTION : calcStride
1290 *
1291 * DESCRIPTION: Temp buffer stride calculation.
1292 *
1293 * PARAMETERS :
1294 * @width : video size width
1295 *
1296 * RETURN : size_t
1297 *==========================================================================*/
calcStride(int width)1298 size_t CameraContext::calcStride(int width)
1299 {
1300 size_t alignment, stride = 0;
1301 if (!width) {
1302 return stride;
1303 }
1304 alignment = 128;
1305 stride = VIDEO_BUF_ALLIGN(width, alignment);
1306
1307 return stride;
1308 }
1309
1310 /*===========================================================================
1311 * FUNCTION : calcYScanLines
1312 *
1313 * DESCRIPTION: Temp buffer scanlines calculation for Y plane.
1314 *
1315 * PARAMETERS :
1316 * @width : video size height
1317 *
1318 * RETURN : size_t
1319 *==========================================================================*/
calcYScanLines(int height)1320 size_t CameraContext::calcYScanLines(int height)
1321 {
1322 size_t alignment, scanlines = 0;
1323 if (!height) {
1324 return scanlines;
1325 }
1326 alignment = 32;
1327 scanlines = VIDEO_BUF_ALLIGN(height, alignment);
1328
1329 return scanlines;
1330 }
1331
1332 /*===========================================================================
1333 * FUNCTION : calcUVScanLines
1334 *
1335 * DESCRIPTION: Temp buffer scanlines calculation for UV plane.
1336 *
1337 * PARAMETERS :
1338 * @width : video size height
1339 *
1340 * RETURN : size_t
1341 *==========================================================================*/
calcUVScanLines(int height)1342 size_t CameraContext::calcUVScanLines(int height)
1343 {
1344 size_t alignment, scanlines = 0;
1345 if (!height) {
1346 return scanlines;
1347 }
1348 alignment = 16;
1349 scanlines = VIDEO_BUF_ALLIGN(((height + 1) >> 1), alignment);
1350
1351 return scanlines;
1352 }
1353
1354 /*===========================================================================
1355 * FUNCTION : printSupportedParams
1356 *
1357 * DESCRIPTION: dump common supported parameters
1358 *
1359 * PARAMETERS : None
1360 *
1361 * RETURN : None
1362 *==========================================================================*/
printSupportedParams()1363 void CameraContext::printSupportedParams()
1364 {
1365 printf("\n\r\tSupported Cameras: %s",
1366 mParams.get("camera-indexes")?
1367 mParams.get("camera-indexes") : "NULL");
1368 printf("\n\r\tSupported Picture Sizes: %s",
1369 mParams.get(CameraParameters::KEY_SUPPORTED_PICTURE_SIZES)?
1370 mParams.get(
1371 CameraParameters::KEY_SUPPORTED_PICTURE_SIZES) : "NULL");
1372 printf("\n\r\tSupported Picture Formats: %s",
1373 mParams.get(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS)?
1374 mParams.get(
1375 CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS) : "NULL");
1376 printf("\n\r\tSupported Preview Sizes: %s",
1377 mParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_SIZES)?
1378 mParams.get(
1379 CameraParameters::KEY_SUPPORTED_PREVIEW_SIZES) : "NULL");
1380 printf("\n\r\tSupported Video Sizes: %s",
1381 mParams.get(CameraParameters::KEY_SUPPORTED_VIDEO_SIZES)?
1382 mParams.get(
1383 CameraParameters::KEY_SUPPORTED_VIDEO_SIZES) : "NULL");
1384 printf("\n\r\tSupported Preview Formats: %s",
1385 mParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS)?
1386 mParams.get(
1387 CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS) : "NULL");
1388 printf("\n\r\tSupported Preview Frame Rates: %s",
1389 mParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES)?
1390 mParams.get(
1391 CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES) : "NULL");
1392 printf("\n\r\tSupported Thumbnail Sizes: %s",
1393 mParams.get(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES)?
1394 mParams.get(
1395 CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES) : "NULL");
1396 printf("\n\r\tSupported Whitebalance Modes: %s",
1397 mParams.get(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE)?
1398 mParams.get(
1399 CameraParameters::KEY_SUPPORTED_WHITE_BALANCE) : "NULL");
1400 printf("\n\r\tSupported Effects: %s",
1401 mParams.get(CameraParameters::KEY_SUPPORTED_EFFECTS)?
1402 mParams.get(CameraParameters::KEY_SUPPORTED_EFFECTS) : "NULL");
1403 printf("\n\r\tSupported Scene Modes: %s",
1404 mParams.get(CameraParameters::KEY_SUPPORTED_SCENE_MODES)?
1405 mParams.get(CameraParameters::KEY_SUPPORTED_SCENE_MODES) : "NULL");
1406 printf("\n\r\tSupported Focus Modes: %s",
1407 mParams.get(CameraParameters::KEY_SUPPORTED_FOCUS_MODES)?
1408 mParams.get(CameraParameters::KEY_SUPPORTED_FOCUS_MODES) : "NULL");
1409 printf("\n\r\tSupported Antibanding Options: %s",
1410 mParams.get(CameraParameters::KEY_SUPPORTED_ANTIBANDING)?
1411 mParams.get(CameraParameters::KEY_SUPPORTED_ANTIBANDING) : "NULL");
1412 printf("\n\r\tSupported Flash Modes: %s",
1413 mParams.get(CameraParameters::KEY_SUPPORTED_FLASH_MODES)?
1414 mParams.get(CameraParameters::KEY_SUPPORTED_FLASH_MODES) : "NULL");
1415 printf("\n\r\tSupported Focus Areas: %d",
1416 mParams.getInt(CameraParameters::KEY_MAX_NUM_FOCUS_AREAS));
1417 printf("\n\r\tSupported FPS ranges : %s",
1418 mParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE)?
1419 mParams.get(
1420 CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE) : "NULL");
1421 printf("\n\r\tFocus Distances: %s \n",
1422 mParams.get(CameraParameters::KEY_FOCUS_DISTANCES)?
1423 mParams.get(CameraParameters::KEY_FOCUS_DISTANCES) : "NULL");
1424 }
1425
1426 /*===========================================================================
1427 * FUNCTION : createPreviewSurface
1428 *
1429 * DESCRIPTION: helper function for creating preview surfaces
1430 *
1431 * PARAMETERS :
1432 * @width : preview width
1433 * @height: preview height
1434 * @pixFormat : surface pixelformat
1435 *
1436 * RETURN : status_t type of status
1437 * NO_ERROR -- success
1438 * none-zero failure code
1439 *==========================================================================*/
createPreviewSurface(unsigned int width,unsigned int height,int32_t pixFormat)1440 status_t CameraContext::createPreviewSurface(unsigned int width,
1441 unsigned int height,
1442 int32_t pixFormat)
1443 {
1444 int ret = NO_ERROR;
1445 DisplayInfo dinfo;
1446 sp<IBinder> display(SurfaceComposerClient::getBuiltInDisplay(
1447 ISurfaceComposer::eDisplayIdMain));
1448 SurfaceComposerClient::getDisplayInfo(display, &dinfo);
1449 unsigned int previewWidth, previewHeight;
1450
1451 if ( dinfo.w < width ) {
1452 previewWidth = dinfo.w;
1453 } else {
1454 previewWidth = width;
1455 }
1456
1457 if ( dinfo.h < height ) {
1458 previewHeight = dinfo.h;
1459 } else {
1460 previewHeight = height;
1461 }
1462
1463 mClient = new SurfaceComposerClient();
1464
1465 if ( NULL == mClient.get() ) {
1466 printf("Unable to establish connection to Surface Composer \n");
1467 return NO_INIT;
1468 }
1469
1470 mSurfaceControl = mClient->createSurface(String8("QCamera_Test"),
1471 previewWidth,
1472 previewHeight,
1473 pixFormat,
1474 0);
1475 if ( NULL == mSurfaceControl.get() ) {
1476 printf("Unable to create preview surface \n");
1477 return NO_INIT;
1478 }
1479
1480 mPreviewSurface = mSurfaceControl->getSurface();
1481 if ( NULL != mPreviewSurface.get() ) {
1482 mClient->openGlobalTransaction();
1483 ret |= mSurfaceControl->setLayer(0x7fffffff);
1484 if ( mCameraIndex == 0 )
1485 ret |= mSurfaceControl->setPosition(0, 0);
1486 else
1487 ret |= mSurfaceControl->setPosition(
1488 dinfo.w - previewWidth, dinfo.h - previewHeight);
1489
1490 ret |= mSurfaceControl->setSize(previewWidth, previewHeight);
1491 ret |= mSurfaceControl->show();
1492 mClient->closeGlobalTransaction();
1493
1494 if ( NO_ERROR != ret ) {
1495 printf("Preview surface configuration failed! \n");
1496 }
1497 } else {
1498 ret = NO_INIT;
1499 }
1500
1501 return ret;
1502 }
1503
1504 /*===========================================================================
1505 * FUNCTION : destroyPreviewSurface
1506 *
1507 * DESCRIPTION: closes previously open preview surface
1508 *
1509 * PARAMETERS : None
1510 *
1511 * RETURN : status_t type of status
1512 * NO_ERROR -- success
1513 * none-zero failure code
1514 *==========================================================================*/
destroyPreviewSurface()1515 status_t CameraContext::destroyPreviewSurface()
1516 {
1517 if ( NULL != mPreviewSurface.get() ) {
1518 mPreviewSurface.clear();
1519 }
1520
1521 if ( NULL != mSurfaceControl.get() ) {
1522 mSurfaceControl->clear();
1523 mSurfaceControl.clear();
1524 }
1525
1526 if ( NULL != mClient.get() ) {
1527 mClient->dispose();
1528 mClient.clear();
1529 }
1530
1531 return NO_ERROR;
1532 }
1533
1534 /*===========================================================================
1535 * FUNCTION : CameraContext
1536 *
1537 * DESCRIPTION: camera context constructor
1538 *
1539 * PARAMETERS : None
1540 *
1541 * RETURN : None
1542 *==========================================================================*/
CameraContext(int cameraIndex)1543 CameraContext::CameraContext(int cameraIndex) :
1544 mCameraIndex(cameraIndex),
1545 mResizePreview(true),
1546 mHardwareActive(false),
1547 mPreviewRunning(false),
1548 mRecordRunning(false),
1549 mVideoFd(-1),
1550 mVideoIdx(0),
1551 mRecordingHint(false),
1552 mDoPrintMenu(true),
1553 mPiPCapture(false),
1554 mfmtMultiplier(1),
1555 mSectionsRead(false),
1556 mSectionsAllocated(false),
1557 mSections(NULL),
1558 mJEXIFTmp(NULL),
1559 mHaveAll(false),
1560 mViVinUse(false),
1561 mCamera(NULL),
1562 mClient(NULL),
1563 mSurfaceControl(NULL),
1564 mPreviewSurface(NULL),
1565 mInUse(false)
1566 {
1567 mRecorder = new MediaRecorder();
1568 }
1569
1570 /*===========================================================================
1571 * FUNCTION : setTestCtxInstance
1572 *
1573 * DESCRIPTION : Sends TestContext instance to CameraContext
1574 *
1575 * PARAMETERS :
1576 * @instance : TestContext instance
1577 *
1578 * RETURN : None
1579 *==========================================================================*/
setTestCtxInstance(TestContext * instance)1580 void CameraContext::setTestCtxInstance(TestContext *instance)
1581 {
1582 mInterpr = instance;
1583 }
1584
1585 /*===========================================================================
1586 * FUNCTION : setTestCtxInst
1587 *
1588 * DESCRIPTION : Sends TestContext instance to Interpreter
1589 *
1590 * PARAMETERS :
1591 * @instance : TestContext instance
1592 *
1593 * RETURN : None
1594 *==========================================================================*/
setTestCtxInst(TestContext * instance)1595 void Interpreter::setTestCtxInst(TestContext *instance)
1596 {
1597 mTestContext = instance;
1598 }
1599
1600 /*===========================================================================
1601 * FUNCTION : ~CameraContext
1602 *
1603 * DESCRIPTION: camera context destructor
1604 *
1605 * PARAMETERS : None
1606 *
1607 * RETURN : None
1608 *==========================================================================*/
~CameraContext()1609 CameraContext::~CameraContext()
1610 {
1611 stopPreview();
1612 closeCamera();
1613 }
1614
1615 /*===========================================================================
1616 * FUNCTION : openCamera
1617 *
1618 * DESCRIPTION: connects to and initializes camera
1619 *
1620 * PARAMETERS : None
1621 *
1622 * RETURN : status_t type of status
1623 * NO_ERROR -- success
1624 * none-zero failure code
1625 *==========================================================================*/
openCamera()1626 status_t CameraContext::openCamera()
1627 {
1628 useLock();
1629
1630 if ( NULL != mCamera.get() ) {
1631 printf("Camera already open! \n");
1632 return NO_ERROR;
1633 }
1634
1635 printf("openCamera(camera_index=%d)\n", mCameraIndex);
1636
1637 #ifndef USE_JB_MR1
1638
1639 String16 packageName("CameraTest");
1640
1641 mCamera = Camera::connect(mCameraIndex,
1642 packageName,
1643 Camera::USE_CALLING_UID);
1644
1645 #else
1646
1647 mCamera = Camera::connect(mCameraIndex);
1648
1649 #endif
1650
1651 if ( NULL == mCamera.get() ) {
1652 printf("Unable to connect to CameraService\n");
1653 return NO_INIT;
1654 }
1655
1656 mParams = mCamera->getParameters();
1657 mParams.getSupportedPreviewSizes(mSupportedPreviewSizes);
1658 mParams.getSupportedPictureSizes(mSupportedPictureSizes);
1659 mParams.getSupportedVideoSizes(mSupportedVideoSizes);
1660
1661 mCurrentPictureSizeIdx = mSupportedPictureSizes.size() / 2;
1662 mCurrentPreviewSizeIdx = mSupportedPreviewSizes.size() / 2;
1663 mCurrentVideoSizeIdx = mSupportedVideoSizes.size() / 2;
1664
1665 mCamera->setListener(this);
1666 mHardwareActive = true;
1667
1668 mInterpr->setViVSize((Size) mSupportedVideoSizes.itemAt(
1669 mCurrentVideoSizeIdx),
1670 mCameraIndex);
1671
1672 signalFinished();
1673
1674 return NO_ERROR;
1675 }
1676
1677 /*===========================================================================
1678 * FUNCTION : onAsBinder
1679 *
1680 * DESCRIPTION: onAsBinder
1681 *
1682 * PARAMETERS : None
1683 *
1684 * RETURN : Pointer to IBinder
1685 *==========================================================================*/
onAsBinder()1686 IBinder* CameraContext::onAsBinder() {
1687 return NULL;
1688 }
1689
1690 /*===========================================================================
1691 * FUNCTION : getNumberOfCameras
1692 *
1693 * DESCRIPTION: returns the number of supported camera by the system
1694 *
1695 * PARAMETERS : None
1696 *
1697 * RETURN : supported camera count
1698 *==========================================================================*/
getNumberOfCameras()1699 int CameraContext::getNumberOfCameras()
1700 {
1701 int ret = -1;
1702
1703 if ( NULL != mCamera.get() ) {
1704 ret = mCamera->getNumberOfCameras();
1705 }
1706
1707 return ret;
1708 }
1709
1710 /*===========================================================================
1711 * FUNCTION : closeCamera
1712 *
1713 * DESCRIPTION: closes a previously the initialized camera reference
1714 *
1715 * PARAMETERS : None
1716 *
1717 * RETURN : status_t type of status
1718 * NO_ERROR -- success
1719 * none-zero failure code
1720 *==========================================================================*/
closeCamera()1721 status_t CameraContext::closeCamera()
1722 {
1723 useLock();
1724 if ( NULL == mCamera.get() ) {
1725 return NO_INIT;
1726 }
1727
1728 mCamera->disconnect();
1729 mCamera.clear();
1730
1731 mRecorder->init();
1732 mRecorder->close();
1733 mRecorder->release();
1734 mRecorder.clear();
1735
1736 mHardwareActive = false;
1737 mPreviewRunning = false;
1738 mRecordRunning = false;
1739
1740 signalFinished();
1741 return NO_ERROR;
1742 }
1743
1744 /*===========================================================================
1745 * FUNCTION : startPreview
1746 *
1747 * DESCRIPTION: starts camera preview
1748 *
1749 * PARAMETERS : None
1750 *
1751 * RETURN : status_t type of status
1752 * NO_ERROR -- success
1753 * none-zero failure code
1754 *==========================================================================*/
startPreview()1755 status_t CameraContext::startPreview()
1756 {
1757 useLock();
1758
1759 int ret = NO_ERROR;
1760 int previewWidth, previewHeight;
1761 Size calculatedPreviewSize;
1762 Size currentPreviewSize = mSupportedPreviewSizes.itemAt(
1763 mCurrentPreviewSizeIdx);
1764 Size currentPictureSize = mSupportedPictureSizes.itemAt(
1765 mCurrentPictureSizeIdx);
1766 Size currentVideoSize = mSupportedVideoSizes.itemAt(
1767 mCurrentVideoSizeIdx);
1768
1769 #ifndef USE_JB_MR1
1770
1771 sp<IGraphicBufferProducer> gbp;
1772
1773 #endif
1774
1775 if (!mHardwareActive ) {
1776 printf("Camera not active! \n");
1777 return NO_INIT;
1778 }
1779
1780 if (mPreviewRunning) {
1781 printf("Preview is already running! \n");
1782 signalFinished();
1783 return NO_ERROR;
1784 }
1785
1786 if (mResizePreview) {
1787 mPreviewRunning = false;
1788
1789 if ( mRecordingHint ) {
1790 calculatedPreviewSize =
1791 getPreviewSizeFromVideoSizes(currentVideoSize);
1792 previewWidth = calculatedPreviewSize.width;
1793 previewHeight = calculatedPreviewSize.height;
1794 } else {
1795 previewWidth = currentPreviewSize.width;
1796 previewHeight = currentPreviewSize.height;
1797 }
1798
1799 ret = createPreviewSurface(previewWidth,
1800 previewHeight,
1801 HAL_PIXEL_FORMAT_YCrCb_420_SP);
1802 if ( NO_ERROR != ret ) {
1803 printf("Error while creating preview surface\n");
1804 return ret;
1805 }
1806
1807 // set rdi mode if system prop is set for front camera
1808 if (mCameraIndex == 1) {
1809 char value[32];
1810 property_get("persist.camera.rdimode", value, "0");
1811 int rdimode = atoi(value);
1812 printf("rdi mode = %d\n", rdimode);
1813 if (rdimode == 1) {
1814 mParams.set("rdi-mode", "enable");
1815 } else {
1816 mParams.set("rdi-mode", "disable");
1817 }
1818 } else {
1819 mParams.set("rdi-mode", "disable");
1820 }
1821
1822 //mParams.set("rdi-mode", "enable");
1823 mParams.set("recording-hint", "true");
1824 mParams.setPreviewSize(previewWidth, previewHeight);
1825 mParams.setPictureSize(currentPictureSize.width,
1826 currentPictureSize.height);
1827 mParams.setVideoSize(
1828 currentVideoSize.width, currentVideoSize.height);
1829
1830 ret |= mCamera->setParameters(mParams.flatten());
1831
1832 #ifndef USE_JB_MR1
1833
1834 gbp = mPreviewSurface->getIGraphicBufferProducer();
1835 ret |= mCamera->setPreviewTarget(gbp);
1836
1837 #else
1838
1839 ret |= mCamera->setPreviewDisplay(mPreviewSurface);
1840
1841 #endif
1842 mResizePreview = false;
1843 }
1844
1845 if ( !mPreviewRunning ) {
1846 ret |= mCamera->startPreview();
1847 if ( NO_ERROR != ret ) {
1848 printf("Preview start failed! \n");
1849 return ret;
1850 }
1851
1852 mPreviewRunning = true;
1853 }
1854
1855 signalFinished();
1856
1857 return ret;
1858 }
1859
1860 /*===========================================================================
1861 * FUNCTION : getPreviewSizeFromVideoSizes
1862 *
1863 * DESCRIPTION: Get the preview size from video size. Find all resolutions with
1864 * the same aspect ratio and choose the same or the closest
1865 * from them.
1866 *
1867 * PARAMETERS :
1868 * @currentVideoSize: current video size
1869
1870 *
1871 * RETURN : PreviewSize
1872 *==========================================================================*/
getPreviewSizeFromVideoSizes(Size currentVideoSize)1873 Size CameraContext::getPreviewSizeFromVideoSizes(Size currentVideoSize)
1874 {
1875
1876 Size tmpPreviewSize;
1877 Size PreviewSize;
1878 Size PreviewSizes[mSupportedPreviewSizes.size()];
1879 float tolerance = 0.00001;
1880 float videoRatio;
1881 float previewRatio;
1882 size_t i = 0;
1883 size_t j = 0;
1884 int delta;
1885
1886 // Find all the resolutions with the same aspect ratio and choose the
1887 // same or the closest resolution from them. Choose the closest resolution
1888 // in case same aspect ratio is not found
1889 if (currentVideoSize.width * currentVideoSize.height > 0 &&
1890 mSupportedPreviewSizes.size() > 0) {
1891 videoRatio = (float)currentVideoSize.width /
1892 (float)currentVideoSize.height;
1893 for (i=0; i<mSupportedPreviewSizes.size(); i++) {
1894 tmpPreviewSize = mSupportedPreviewSizes.itemAt(i);
1895 previewRatio = (float)tmpPreviewSize.width /
1896 (float)tmpPreviewSize.height;
1897 if (fabs(videoRatio - previewRatio) < tolerance) {
1898 PreviewSizes[j] = tmpPreviewSize;
1899 j++;
1900 }
1901 }
1902
1903 if ( j > 0 ) {
1904 delta = abs((currentVideoSize.width *currentVideoSize.height)-
1905 (PreviewSizes[0].width * PreviewSizes[0].height));
1906 PreviewSize = PreviewSizes[0];
1907 for (i=0; i<j; i++) {
1908 if(abs(currentVideoSize.width * currentVideoSize.height) -
1909 (PreviewSizes[i].width * PreviewSizes[i].height) <
1910 delta) {
1911 PreviewSize = PreviewSizes[i];
1912 delta = abs((currentVideoSize.width *
1913 currentVideoSize.height) -
1914 (PreviewSizes[i].width * PreviewSizes[i].height));
1915 }
1916 }
1917 } else {
1918 // Choose the closest resolution in case same aspect ratio is
1919 // not found
1920 tmpPreviewSize = mSupportedPreviewSizes.itemAt(j);
1921 PreviewSize = tmpPreviewSize;
1922 delta = abs(
1923 (currentVideoSize.width * currentVideoSize.height)-
1924 (tmpPreviewSize.width * tmpPreviewSize.height));
1925 for (i=0; i<mSupportedPreviewSizes.size(); i++) {
1926 tmpPreviewSize = mSupportedPreviewSizes.itemAt(i);
1927 if(abs(
1928 (currentVideoSize.width * currentVideoSize.height)-
1929 (tmpPreviewSize.width * tmpPreviewSize.height)) <
1930 delta) {
1931 PreviewSize = tmpPreviewSize;
1932 delta = abs(
1933 (currentVideoSize.width * currentVideoSize.height)-
1934 (tmpPreviewSize.width * tmpPreviewSize.height));
1935 }
1936 }
1937 }
1938 } else {
1939 memset(&PreviewSize, 0, sizeof(PreviewSize));
1940 }
1941 return PreviewSize;
1942 }
1943
1944 /*===========================================================================
1945 * FUNCTION : autoFocus
1946 *
1947 * DESCRIPTION: Triggers autofocus
1948 *
1949 * PARAMETERS : None
1950 *
1951 * RETURN : status_t type of status
1952 * NO_ERROR -- success
1953 * none-zero failure code
1954 *==========================================================================*/
autoFocus()1955 status_t CameraContext::autoFocus()
1956 {
1957 useLock();
1958 status_t ret = NO_ERROR;
1959
1960 if ( mPreviewRunning ) {
1961 ret = mCamera->autoFocus();
1962 }
1963
1964 signalFinished();
1965 return ret;
1966 }
1967
1968 /*===========================================================================
1969 * FUNCTION : enablePreviewCallbacks
1970 *
1971 * DESCRIPTION: Enables preview callback messages
1972 *
1973 * PARAMETERS : None
1974 *
1975 * RETURN : status_t type of status
1976 * NO_ERROR -- success
1977 * none-zero failure code
1978 *==========================================================================*/
enablePreviewCallbacks()1979 status_t CameraContext::enablePreviewCallbacks()
1980 {
1981 useLock();
1982 if ( mHardwareActive ) {
1983 mCamera->setPreviewCallbackFlags(
1984 CAMERA_FRAME_CALLBACK_FLAG_ENABLE_MASK);
1985 }
1986
1987 signalFinished();
1988 return NO_ERROR;
1989 }
1990
1991 /*===========================================================================
1992 * FUNCTION : takePicture
1993 *
1994 * DESCRIPTION: triggers image capture
1995 *
1996 * PARAMETERS : None
1997 *
1998 * RETURN : status_t type of status
1999 * NO_ERROR -- success
2000 * none-zero failure code
2001 *==========================================================================*/
takePicture()2002 status_t CameraContext::takePicture()
2003 {
2004 status_t ret = NO_ERROR;
2005
2006 useLock(); // Unlocked in jpeg callback
2007
2008 if ( mPreviewRunning ) {
2009 ret = mCamera->takePicture(
2010 CAMERA_MSG_COMPRESSED_IMAGE|
2011 CAMERA_MSG_RAW_IMAGE);
2012 if (!mRecordingHint) {
2013 mPreviewRunning = false;
2014 }
2015 } else {
2016 printf("Please resume/start the preview before taking a picture!\n");
2017 signalFinished(); //Unlock in case preview is not running
2018 }
2019 return ret;
2020 }
2021
2022 /*===========================================================================
2023 * FUNCTION : configureRecorder
2024 *
2025 * DESCRIPTION: Configure video recorder
2026 *
2027 * PARAMETERS : None
2028 *
2029 * RETURN : status_t type of status
2030 * NO_ERROR -- success
2031 * none-zero failure code
2032 *==========================================================================*/
configureRecorder()2033 status_t CameraContext::configureRecorder()
2034 {
2035 useLock();
2036 status_t ret = NO_ERROR;
2037
2038 mResizePreview = true;
2039 mParams.set("recording-hint", "true");
2040 mRecordingHint = true;
2041 mCamera->setParameters(mParams.flatten());
2042
2043 Size videoSize = mSupportedVideoSizes.itemAt(mCurrentVideoSizeIdx);
2044 ret = mRecorder->setParameters(
2045 String8("video-param-encoding-bitrate=64000"));
2046 if ( ret != NO_ERROR ) {
2047 ERROR("Could not configure recorder (%d)", ret);
2048 return ret;
2049 }
2050
2051 ret = mRecorder->setCamera(
2052 mCamera->remote(), mCamera->getRecordingProxy());
2053 if ( ret != NO_ERROR ) {
2054 ERROR("Could not set camera (%d)", ret);
2055 return ret;
2056 }
2057 ret = mRecorder->setVideoSource(VIDEO_SOURCE_CAMERA);
2058 if ( ret != NO_ERROR ) {
2059 ERROR("Could not set video soruce (%d)", ret);
2060 return ret;
2061 }
2062 ret = mRecorder->setAudioSource(AUDIO_SOURCE_DEFAULT);
2063 if ( ret != NO_ERROR ) {
2064 ERROR("Could not set audio source (%d)", ret);
2065 return ret;
2066 }
2067 ret = mRecorder->setOutputFormat(OUTPUT_FORMAT_DEFAULT);
2068 if ( ret != NO_ERROR ) {
2069 ERROR("Could not set output format (%d)", ret);
2070 return ret;
2071 }
2072
2073 ret = mRecorder->setVideoEncoder(VIDEO_ENCODER_DEFAULT);
2074 if ( ret != NO_ERROR ) {
2075 ERROR("Could not set video encoder (%d)", ret);
2076 return ret;
2077 }
2078
2079 char fileName[100];
2080
2081 sprintf(fileName, "/sdcard/vid_cam%d_%dx%d_%d.mpeg", mCameraIndex,
2082 videoSize.width, videoSize.height, mVideoIdx++);
2083
2084 if ( mVideoFd < 0 ) {
2085 mVideoFd = open(fileName, O_CREAT | O_RDWR );
2086 }
2087
2088 if ( mVideoFd < 0 ) {
2089 ERROR("Could not open video file for writing %s!", fileName);
2090 return UNKNOWN_ERROR;
2091 }
2092
2093 ret = mRecorder->setOutputFile(mVideoFd, 0, 0);
2094 if ( ret != NO_ERROR ) {
2095 ERROR("Could not set output file (%d)", ret);
2096 return ret;
2097 }
2098
2099 ret = mRecorder->setVideoSize(videoSize.width, videoSize.height);
2100 if ( ret != NO_ERROR ) {
2101 ERROR("Could not set video size %dx%d", videoSize.width,
2102 videoSize.height);
2103 return ret;
2104 }
2105
2106 ret = mRecorder->setVideoFrameRate(30);
2107 if ( ret != NO_ERROR ) {
2108 ERROR("Could not set video frame rate (%d)", ret);
2109 return ret;
2110 }
2111
2112 ret = mRecorder->setAudioEncoder(AUDIO_ENCODER_DEFAULT);
2113 if ( ret != NO_ERROR ) {
2114 ERROR("Could not set audio encoder (%d)", ret);
2115 return ret;
2116 }
2117
2118 signalFinished();
2119 return ret;
2120 }
2121
2122 /*===========================================================================
2123 * FUNCTION : unconfigureViVRecording
2124 *
2125 * DESCRIPTION: Unconfigures video in video recording
2126 *
2127 * PARAMETERS : None
2128 *
2129 * RETURN : status_t type of status
2130 * NO_ERROR -- success
2131 * none-zero failure code
2132 *==========================================================================*/
unconfigureRecorder()2133 status_t CameraContext::unconfigureRecorder()
2134 {
2135 useLock();
2136
2137 if ( !mRecordRunning ) {
2138 mResizePreview = true;
2139 mParams.set("recording-hint", "false");
2140 mRecordingHint = false;
2141 mCamera->setParameters(mParams.flatten());
2142 }
2143
2144 signalFinished();
2145 return NO_ERROR;
2146 }
2147
2148 /*===========================================================================
2149 * FUNCTION : configureViVRecording
2150 *
2151 * DESCRIPTION: Configures video in video recording
2152 *
2153 * PARAMETERS : None
2154 *
2155 * RETURN : status_t type of status
2156 * NO_ERROR -- success
2157 * none-zero failure code
2158 *==========================================================================*/
configureViVRecording()2159 status_t CameraContext::configureViVRecording()
2160 {
2161 status_t ret = NO_ERROR;
2162
2163 mResizePreview = true;
2164 mParams.set("recording-hint", "true");
2165 mRecordingHint = true;
2166 mCamera->setParameters(mParams.flatten());
2167 mCamera->setRecordingProxyListener(this);
2168
2169 signalFinished();
2170 return ret;
2171 }
2172
2173 /*===========================================================================
2174 * FUNCTION : startRecording
2175 *
2176 * DESCRIPTION: triggers start recording
2177 *
2178 * PARAMETERS : None
2179 *
2180 * RETURN : status_t type of status
2181 * NO_ERROR -- success
2182 * none-zero failure code
2183 *==========================================================================*/
startRecording()2184 status_t CameraContext::startRecording()
2185 {
2186 useLock();
2187 status_t ret = NO_ERROR;
2188
2189
2190 if ( mPreviewRunning ) {
2191
2192 mCamera->unlock();
2193
2194 ret = mRecorder->prepare();
2195 if ( ret != NO_ERROR ) {
2196 ERROR("Could not prepare recorder");
2197 return ret;
2198 }
2199
2200 ret = mRecorder->start();
2201 if ( ret != NO_ERROR ) {
2202 ERROR("Could not start recorder");
2203 return ret;
2204 }
2205
2206 mRecordRunning = true;
2207 }
2208 signalFinished();
2209 return ret;
2210 }
2211
2212 /*===========================================================================
2213 * FUNCTION : stopRecording
2214 *
2215 * DESCRIPTION: triggers start recording
2216 *
2217 * PARAMETERS : None
2218 *
2219 * RETURN : status_t type of status
2220 * NO_ERROR -- success
2221 * none-zero failure code
2222 *==========================================================================*/
stopRecording()2223 status_t CameraContext::stopRecording()
2224 {
2225 useLock();
2226 status_t ret = NO_ERROR;
2227
2228 if ( mRecordRunning ) {
2229 mRecorder->stop();
2230 close(mVideoFd);
2231 mVideoFd = -1;
2232
2233 mRecordRunning = false;
2234 }
2235
2236 signalFinished();
2237
2238 return ret;
2239 }
2240
2241 /*===========================================================================
2242 * FUNCTION : startViVRecording
2243 *
2244 * DESCRIPTION: Starts video in video recording
2245 *
2246 * PARAMETERS : None
2247 *
2248 * RETURN : status_t type of status
2249 * NO_ERROR -- success
2250 * none-zero failure code
2251 *==========================================================================*/
startViVRecording()2252 status_t CameraContext::startViVRecording()
2253 {
2254 useLock();
2255 status_t ret;
2256
2257 if (mInterpr->mViVVid.VideoSizes[0].width *
2258 mInterpr->mViVVid.VideoSizes[0].height >=
2259 mInterpr->mViVVid.VideoSizes[1].width *
2260 mInterpr->mViVVid.VideoSizes[1].height) {
2261 mInterpr->mViVBuff.buffSize = calcBufferSize(
2262 mInterpr->mViVVid.VideoSizes[1].width,
2263 mInterpr->mViVVid.VideoSizes[1].height);
2264 if (mInterpr->mViVBuff.buff == NULL) {
2265 mInterpr->mViVBuff.buff =
2266 (void *)malloc(mInterpr->mViVBuff.buffSize);
2267 }
2268 mInterpr->mViVVid.sourceCameraID = 1;
2269 mInterpr->mViVVid.destinationCameraID = 0;
2270
2271 } else {
2272 mInterpr->mViVBuff.buffSize = calcBufferSize(
2273 mInterpr->mViVVid.VideoSizes[0].width,
2274 mInterpr->mViVVid.VideoSizes[0].height);
2275 if (mInterpr->mViVBuff.buff == NULL) {
2276 mInterpr->mViVBuff.buff =
2277 (void *)malloc(mInterpr->mViVBuff.buffSize);
2278 }
2279 mInterpr->mViVVid.sourceCameraID = 0;
2280 mInterpr->mViVVid.destinationCameraID = 1;
2281 }
2282
2283 ret = mCamera->startRecording();
2284
2285 signalFinished();
2286 return ret;
2287 }
2288
2289 /*===========================================================================
2290 * FUNCTION : stopViVRecording
2291 *
2292 * DESCRIPTION: Stops video in video recording
2293 *
2294 * PARAMETERS : None
2295 *
2296 * RETURN : status_t type of status
2297 * NO_ERROR -- success
2298 * none-zero failure code
2299 *==========================================================================*/
stopViVRecording()2300 status_t CameraContext::stopViVRecording()
2301 {
2302 useLock();
2303 status_t ret = NO_ERROR;
2304
2305 mCamera->stopRecording();
2306
2307 signalFinished();
2308 return ret;
2309 }
2310
2311 /*===========================================================================
2312 * FUNCTION : stopPreview
2313 *
2314 * DESCRIPTION: stops camera preview
2315 *
2316 * PARAMETERS : None
2317 *
2318 * RETURN : status_t type of status
2319 * NO_ERROR -- success
2320 * none-zero failure code
2321 *==========================================================================*/
stopPreview()2322 status_t CameraContext::stopPreview()
2323 {
2324 useLock();
2325 status_t ret = NO_ERROR;
2326
2327 if ( mHardwareActive ) {
2328 mCamera->stopPreview();
2329 ret = destroyPreviewSurface();
2330 }
2331
2332 mPreviewRunning = false;
2333 mResizePreview = true;
2334
2335 signalFinished();
2336
2337 return ret;
2338 }
2339
2340 /*===========================================================================
2341 * FUNCTION : resumePreview
2342 *
2343 * DESCRIPTION: resumes camera preview after image capture
2344 *
2345 * PARAMETERS : None
2346 *
2347 * RETURN : status_t type of status
2348 * NO_ERROR -- success
2349 * none-zero failure code
2350 *==========================================================================*/
resumePreview()2351 status_t CameraContext::resumePreview()
2352 {
2353 useLock();
2354 status_t ret = NO_ERROR;
2355
2356 if ( mHardwareActive ) {
2357 ret = mCamera->startPreview();
2358 mPreviewRunning = true;
2359 } else {
2360 ret = NO_INIT;
2361 }
2362
2363 signalFinished();
2364 return ret;
2365 }
2366
2367 /*===========================================================================
2368 * FUNCTION : nextPreviewSize
2369 *
2370 * DESCRIPTION: Iterates through all supported preview sizes.
2371 *
2372 * PARAMETERS : None
2373 *
2374 * RETURN : status_t type of status
2375 * NO_ERROR -- success
2376 * none-zero failure code
2377 *==========================================================================*/
nextPreviewSize()2378 status_t CameraContext::nextPreviewSize()
2379 {
2380 useLock();
2381 if ( mHardwareActive ) {
2382 mCurrentPreviewSizeIdx += 1;
2383 mCurrentPreviewSizeIdx %= mSupportedPreviewSizes.size();
2384 Size previewSize = mSupportedPreviewSizes.itemAt(
2385 mCurrentPreviewSizeIdx);
2386 mParams.setPreviewSize(previewSize.width,
2387 previewSize.height);
2388 mResizePreview = true;
2389
2390 if ( mPreviewRunning ) {
2391 mCamera->stopPreview();
2392 mCamera->setParameters(mParams.flatten());
2393 mCamera->startPreview();
2394 } else {
2395 mCamera->setParameters(mParams.flatten());
2396 }
2397 }
2398
2399 signalFinished();
2400 return NO_ERROR;
2401 }
2402
2403
2404 /*===========================================================================
2405 * FUNCTION : setPreviewSize
2406 *
2407 * DESCRIPTION: Sets exact preview size if supported
2408 *
2409 * PARAMETERS : format size in the form of WIDTHxHEIGHT
2410 *
2411 * RETURN : status_t type of status
2412 * NO_ERROR -- success
2413 * none-zero failure code
2414 *==========================================================================*/
setPreviewSize(const char * format)2415 status_t CameraContext::setPreviewSize(const char *format)
2416 {
2417 useLock();
2418 if ( mHardwareActive ) {
2419 int newHeight;
2420 int newWidth;
2421 sscanf(format, "%dx%d", &newWidth, &newHeight);
2422
2423 unsigned int i;
2424 for (i = 0; i < mSupportedPreviewSizes.size(); ++i) {
2425 Size previewSize = mSupportedPreviewSizes.itemAt(i);
2426 if ( newWidth == previewSize.width &&
2427 newHeight == previewSize.height )
2428 {
2429 break;
2430 }
2431
2432 }
2433 if ( i == mSupportedPreviewSizes.size())
2434 {
2435 printf("Preview size %dx%d not supported !\n",
2436 newWidth, newHeight);
2437 return INVALID_OPERATION;
2438 }
2439
2440 mParams.setPreviewSize(newWidth,
2441 newHeight);
2442 mResizePreview = true;
2443
2444 if ( mPreviewRunning ) {
2445 mCamera->stopPreview();
2446 mCamera->setParameters(mParams.flatten());
2447 mCamera->startPreview();
2448 } else {
2449 mCamera->setParameters(mParams.flatten());
2450 }
2451 }
2452
2453 signalFinished();
2454 return NO_ERROR;
2455 }
2456
2457 /*===========================================================================
2458 * FUNCTION : getCurrentPreviewSize
2459 *
2460 * DESCRIPTION: queries the currently configured preview size
2461 *
2462 * PARAMETERS :
2463 * @previewSize : preview size currently configured
2464 *
2465 * RETURN : status_t type of status
2466 * NO_ERROR -- success
2467 * none-zero failure code
2468 *==========================================================================*/
getCurrentPreviewSize(Size & previewSize)2469 status_t CameraContext::getCurrentPreviewSize(Size &previewSize)
2470 {
2471 useLock();
2472 if ( mHardwareActive ) {
2473 previewSize = mSupportedPreviewSizes.itemAt(mCurrentPreviewSizeIdx);
2474 }
2475 signalFinished();
2476 return NO_ERROR;
2477 }
2478
2479 /*===========================================================================
2480 * FUNCTION : nextPictureSize
2481 *
2482 * DESCRIPTION: Iterates through all supported picture sizes.
2483 *
2484 * PARAMETERS : None
2485 *
2486 * RETURN : status_t type of status
2487 * NO_ERROR -- success
2488 * none-zero failure code
2489 *==========================================================================*/
nextPictureSize()2490 status_t CameraContext::nextPictureSize()
2491 {
2492 useLock();
2493 if ( mHardwareActive ) {
2494 mCurrentPictureSizeIdx += 1;
2495 mCurrentPictureSizeIdx %= mSupportedPictureSizes.size();
2496 Size pictureSize = mSupportedPictureSizes.itemAt(
2497 mCurrentPictureSizeIdx);
2498 mParams.setPictureSize(pictureSize.width,
2499 pictureSize.height);
2500 mCamera->setParameters(mParams.flatten());
2501 }
2502 signalFinished();
2503 return NO_ERROR;
2504 }
2505
2506 /*===========================================================================
2507 * FUNCTION : setPictureSize
2508 *
2509 * DESCRIPTION: Sets exact preview size if supported
2510 *
2511 * PARAMETERS : format size in the form of WIDTHxHEIGHT
2512 *
2513 * RETURN : status_t type of status
2514 * NO_ERROR -- success
2515 * none-zero failure code
2516 *==========================================================================*/
setPictureSize(const char * format)2517 status_t CameraContext::setPictureSize(const char *format)
2518 {
2519 useLock();
2520 if ( mHardwareActive ) {
2521 int newHeight;
2522 int newWidth;
2523 sscanf(format, "%dx%d", &newWidth, &newHeight);
2524
2525 unsigned int i;
2526 for (i = 0; i < mSupportedPictureSizes.size(); ++i) {
2527 Size PictureSize = mSupportedPictureSizes.itemAt(i);
2528 if ( newWidth == PictureSize.width &&
2529 newHeight == PictureSize.height )
2530 {
2531 break;
2532 }
2533
2534 }
2535 if ( i == mSupportedPictureSizes.size())
2536 {
2537 printf("Preview size %dx%d not supported !\n",
2538 newWidth, newHeight);
2539 return INVALID_OPERATION;
2540 }
2541
2542 mParams.setPictureSize(newWidth,
2543 newHeight);
2544 mCamera->setParameters(mParams.flatten());
2545 }
2546
2547 signalFinished();
2548 return NO_ERROR;
2549 }
2550
2551 /*===========================================================================
2552 * FUNCTION : nextVideoSize
2553 *
2554 * DESCRIPTION: Select the next available video size
2555 *
2556 * PARAMETERS : none
2557 *
2558 * RETURN : status_t type of status
2559 * NO_ERROR -- success
2560 * none-zero failure code
2561 *==========================================================================*/
nextVideoSize()2562 status_t CameraContext::nextVideoSize()
2563 {
2564 useLock();
2565 if ( mHardwareActive ) {
2566 mCurrentVideoSizeIdx += 1;
2567 mCurrentVideoSizeIdx %= mSupportedVideoSizes.size();
2568 Size videoSize = mSupportedVideoSizes.itemAt(mCurrentVideoSizeIdx);
2569 mParams.setVideoSize(videoSize.width,
2570 videoSize.height);
2571 mCamera->setParameters(mParams.flatten());
2572 mInterpr->setViVSize((Size) mSupportedVideoSizes.itemAt(
2573 mCurrentVideoSizeIdx), mCameraIndex);
2574 }
2575 signalFinished();
2576 return NO_ERROR;
2577 }
2578
2579 /*===========================================================================
2580 * FUNCTION : setVideoSize
2581 *
2582 * DESCRIPTION: Set video size
2583 *
2584 * PARAMETERS :
2585 * @format : format
2586 *
2587 * RETURN : status_t type of status
2588 * NO_ERROR -- success
2589 * none-zero failure code
2590 *==========================================================================*/
setVideoSize(const char * format)2591 status_t CameraContext::setVideoSize(const char *format)
2592 {
2593 useLock();
2594 if ( mHardwareActive ) {
2595 int newHeight;
2596 int newWidth;
2597 sscanf(format, "%dx%d", &newWidth, &newHeight);
2598
2599 unsigned int i;
2600 for (i = 0; i < mSupportedVideoSizes.size(); ++i) {
2601 Size PictureSize = mSupportedVideoSizes.itemAt(i);
2602 if ( newWidth == PictureSize.width &&
2603 newHeight == PictureSize.height )
2604 {
2605 break;
2606 }
2607
2608 }
2609 if ( i == mSupportedVideoSizes.size())
2610 {
2611 printf("Preview size %dx%d not supported !\n",
2612 newWidth, newHeight);
2613 return INVALID_OPERATION;
2614 }
2615
2616 mParams.setVideoSize(newWidth,
2617 newHeight);
2618 mCamera->setParameters(mParams.flatten());
2619 }
2620
2621 signalFinished();
2622 return NO_ERROR;
2623 }
2624
2625 /*===========================================================================
2626 * FUNCTION : getCurrentVideoSize
2627 *
2628 * DESCRIPTION : Get current video size
2629 *
2630 * PARAMETERS :
2631 * @videoSize: video Size
2632 *
2633 * RETURN : status_t type of status
2634 * NO_ERROR -- success
2635 * none-zero failure code
2636 *==========================================================================*/
getCurrentVideoSize(Size & videoSize)2637 status_t CameraContext::getCurrentVideoSize(Size &videoSize)
2638 {
2639 useLock();
2640 if ( mHardwareActive ) {
2641 videoSize = mSupportedVideoSizes.itemAt(mCurrentVideoSizeIdx);
2642 }
2643 signalFinished();
2644 return NO_ERROR;
2645 }
2646
2647 /*===========================================================================
2648 * FUNCTION : getCurrentPictureSize
2649 *
2650 * DESCRIPTION: queries the currently configured picture size
2651 *
2652 * PARAMETERS :
2653 * @pictureSize : picture size currently configured
2654 *
2655 * RETURN : status_t type of status
2656 * NO_ERROR -- success
2657 * none-zero failure code
2658 *==========================================================================*/
getCurrentPictureSize(Size & pictureSize)2659 status_t CameraContext::getCurrentPictureSize(Size &pictureSize)
2660 {
2661 useLock();
2662 if ( mHardwareActive ) {
2663 pictureSize = mSupportedPictureSizes.itemAt(mCurrentPictureSizeIdx);
2664 }
2665 signalFinished();
2666 return NO_ERROR;
2667 }
2668
2669 }; //namespace qcamera ends here
2670
2671 using namespace qcamera;
2672
2673 /*===========================================================================
2674 * FUNCTION : printMenu
2675 *
2676 * DESCRIPTION: prints the available camera options
2677 *
2678 * PARAMETERS :
2679 * @currentCamera : camera context currently being used
2680 *
2681 * RETURN : None
2682 *==========================================================================*/
printMenu(sp<CameraContext> currentCamera)2683 void CameraContext::printMenu(sp<CameraContext> currentCamera)
2684 {
2685 if ( !mDoPrintMenu ) return;
2686 Size currentPictureSize, currentPreviewSize, currentVideoSize;
2687
2688 assert(currentCamera.get());
2689
2690 currentCamera->getCurrentPictureSize(currentPictureSize);
2691 currentCamera->getCurrentPreviewSize(currentPreviewSize);
2692 currentCamera->getCurrentVideoSize(currentVideoSize);
2693
2694 printf("\n\n=========== FUNCTIONAL TEST MENU ===================\n\n");
2695
2696 printf(" \n\nSTART / STOP / GENERAL SERVICES \n");
2697 printf(" -----------------------------\n");
2698 printf(" %c. Switch camera - Current Index: %d\n",
2699 Interpreter::SWITCH_CAMERA_CMD,
2700 currentCamera->getCameraIndex());
2701 printf(" %c. Resume Preview after capture \n",
2702 Interpreter::RESUME_PREVIEW_CMD);
2703 printf(" %c. Quit \n",
2704 Interpreter::EXIT_CMD);
2705 printf(" %c. Camera Capability Dump",
2706 Interpreter::DUMP_CAPS_CMD);
2707
2708 printf(" \n\n PREVIEW SUB MENU \n");
2709 printf(" -----------------------------\n");
2710 printf(" %c. Start Preview\n",
2711 Interpreter::START_PREVIEW_CMD);
2712 printf(" %c. Stop Preview\n",
2713 Interpreter::STOP_PREVIEW_CMD);
2714 printf(" %c. Preview size: %dx%d\n",
2715 Interpreter::CHANGE_PREVIEW_SIZE_CMD,
2716 currentPreviewSize.width,
2717 currentPreviewSize.height);
2718 printf(" %c. Video size: %dx%d\n",
2719 Interpreter::CHANGE_VIDEO_SIZE_CMD,
2720 currentVideoSize.width,
2721 currentVideoSize.height);
2722 printf(" %c. Start Recording\n",
2723 Interpreter::START_RECORD_CMD);
2724 printf(" %c. Stop Recording\n",
2725 Interpreter::STOP_RECORD_CMD);
2726 printf(" %c. Start ViV Recording\n",
2727 Interpreter::START_VIV_RECORD_CMD);
2728 printf(" %c. Stop ViV Recording\n",
2729 Interpreter::STOP_VIV_RECORD_CMD);
2730 printf(" %c. Enable preview frames\n",
2731 Interpreter::ENABLE_PRV_CALLBACKS_CMD);
2732 printf(" %c. Trigger autofocus \n",
2733 Interpreter::AUTOFOCUS_CMD);
2734
2735 printf(" \n\n IMAGE CAPTURE SUB MENU \n");
2736 printf(" -----------------------------\n");
2737 printf(" %c. Take picture/Full Press\n",
2738 Interpreter::TAKEPICTURE_CMD);
2739 printf(" %c. Take picture in picture\n",
2740 Interpreter::TAKEPICTURE_IN_PICTURE_CMD);
2741 printf(" %c. Picture size: %dx%d\n",
2742 Interpreter::CHANGE_PICTURE_SIZE_CMD,
2743 currentPictureSize.width,
2744 currentPictureSize.height);
2745
2746 printf("\n");
2747 printf(" Choice: ");
2748 }
2749
2750 /*===========================================================================
2751 * FUNCTION : enablePrintPreview
2752 *
2753 * DESCRIPTION: Enables printing the preview
2754 *
2755 * PARAMETERS : None
2756 *
2757 * RETURN : None
2758 *==========================================================================*/
enablePrintPreview()2759 void CameraContext::enablePrintPreview()
2760 {
2761 mDoPrintMenu = true;
2762 }
2763
2764 /*===========================================================================
2765 * FUNCTION : disablePrintPreview
2766 *
2767 * DESCRIPTION: Disables printing the preview
2768 *
2769 * PARAMETERS : None
2770 *
2771 * RETURN : None
2772 *==========================================================================*/
disablePrintPreview()2773 void CameraContext::disablePrintPreview()
2774 {
2775 mDoPrintMenu = false;
2776 }
2777
2778 /*===========================================================================
2779 * FUNCTION : enablePiPCapture
2780 *
2781 * DESCRIPTION: Enables picture in picture capture
2782 *
2783 * PARAMETERS : None
2784 *
2785 * RETURN : None
2786 *==========================================================================*/
enablePiPCapture()2787 void CameraContext::enablePiPCapture()
2788 {
2789 mPiPCapture = true;
2790 }
2791
2792 /*===========================================================================
2793 * FUNCTION : disablePiPCapture
2794 *
2795 * DESCRIPTION: Disables picture in picture capture
2796 *
2797 * PARAMETERS : None
2798 *
2799 * RETURN : None
2800 *==========================================================================*/
disablePiPCapture()2801 void CameraContext::disablePiPCapture()
2802 {
2803 mPiPCapture = false;
2804 }
2805
2806 /*===========================================================================
2807 * FUNCTION : configureViVCodec
2808 *
2809 * DESCRIPTION: Configures video in video codec
2810 *
2811 * PARAMETERS : none
2812 *
2813 * RETURN : status_t type of status
2814 * NO_ERROR -- success
2815 * none-zero failure code
2816 *==========================================================================*/
configureViVCodec()2817 status_t Interpreter::configureViVCodec()
2818 {
2819 status_t ret = NO_ERROR;
2820 char fileName[100];
2821 sp<AMessage> format = new AMessage;
2822 sp<ALooper> looper = new ALooper;
2823
2824 if (mTestContext->mViVVid.VideoSizes[0].width *
2825 mTestContext->mViVVid.VideoSizes[0].height >=
2826 mTestContext->mViVVid.VideoSizes[1].width *
2827 mTestContext->mViVVid.VideoSizes[1].height) {
2828 sprintf(fileName, "/sdcard/ViV_vid_%dx%d_%d.mp4",
2829 mTestContext->mViVVid.VideoSizes[0].width,
2830 mTestContext->mViVVid.VideoSizes[0].height,
2831 mTestContext->mViVVid.ViVIdx++);
2832 format->setInt32("width", mTestContext->mViVVid.VideoSizes[0].width);
2833 format->setInt32("height", mTestContext->mViVVid.VideoSizes[0].height);
2834 } else {
2835 sprintf(fileName, "/sdcard/ViV_vid_%dx%d_%d.mp4",
2836 mTestContext->mViVVid.VideoSizes[1].width,
2837 mTestContext->mViVVid.VideoSizes[1].height,
2838 mTestContext->mViVVid.ViVIdx++);
2839 format->setInt32("width", mTestContext->mViVVid.VideoSizes[1].width);
2840 format->setInt32("height", mTestContext->mViVVid.VideoSizes[1].height);
2841 }
2842 mTestContext->mViVVid.muxer = new MediaMuxer(
2843 fileName, MediaMuxer::OUTPUT_FORMAT_MPEG_4);
2844
2845 format->setString("mime", "video/avc");
2846 format->setInt32("color-format", OMX_COLOR_FormatAndroidOpaque);
2847
2848 format->setInt32("bitrate", 1000000);
2849 format->setFloat("frame-rate", 30);
2850 format->setInt32("i-frame-interval", 10);
2851
2852 looper->setName("ViV_recording_looper");
2853 looper->start();
2854 ALOGV("Creating codec");
2855 mTestContext->mViVVid.codec = MediaCodec::CreateByType(
2856 looper, "video/avc", true);
2857 if (mTestContext->mViVVid.codec == NULL) {
2858 fprintf(stderr, "ERROR: unable to create video/avc codec instance\n");
2859 return UNKNOWN_ERROR;
2860 }
2861 ret = mTestContext->mViVVid.codec->configure(format, NULL, NULL,
2862 MediaCodec::CONFIGURE_FLAG_ENCODE);
2863 if (ret != NO_ERROR) {
2864 mTestContext->mViVVid.codec->release();
2865 mTestContext->mViVVid.codec.clear();
2866
2867 fprintf(stderr, "ERROR: unable to configure codec (err=%d)\n", ret);
2868 return ret;
2869 }
2870
2871 ALOGV("Creating buffer producer");
2872 ret = mTestContext->mViVVid.codec->createInputSurface(
2873 &mTestContext->mViVVid.bufferProducer);
2874 if (ret != NO_ERROR) {
2875 mTestContext->mViVVid.codec->release();
2876 mTestContext->mViVVid.codec.clear();
2877
2878 fprintf(stderr,
2879 "ERROR: unable to create encoder input surface (err=%d)\n", ret);
2880 return ret;
2881 }
2882
2883 ret = mTestContext->mViVVid.codec->start();
2884 if (ret != NO_ERROR) {
2885 mTestContext->mViVVid.codec->release();
2886 mTestContext->mViVVid.codec.clear();
2887
2888 fprintf(stderr, "ERROR: unable to start codec (err=%d)\n", ret);
2889 return ret;
2890 }
2891 ALOGV("Codec prepared");
2892
2893 mTestContext->mViVVid.surface = new Surface(
2894 mTestContext->mViVVid.bufferProducer);
2895 mTestContext->mViVVid.ANW = mTestContext->mViVVid.surface;
2896 ret = native_window_api_connect(mTestContext->mViVVid.ANW.get(),
2897 NATIVE_WINDOW_API_CPU);
2898 if (mTestContext->mViVVid.VideoSizes[0].width *
2899 mTestContext->mViVVid.VideoSizes[0].height >=
2900 mTestContext->mViVVid.VideoSizes[1].width *
2901 mTestContext->mViVVid.VideoSizes[1].height) {
2902 native_window_set_buffers_geometry(mTestContext->mViVVid.ANW.get(),
2903 mTestContext->mViVVid.VideoSizes[0].width,
2904 mTestContext->mViVVid.VideoSizes[0].height,
2905 HAL_PIXEL_FORMAT_NV12_ENCODEABLE);
2906 } else {
2907 native_window_set_buffers_geometry(mTestContext->mViVVid.ANW.get(),
2908 mTestContext->mViVVid.VideoSizes[1].width,
2909 mTestContext->mViVVid.VideoSizes[1].height,
2910 HAL_PIXEL_FORMAT_NV12_ENCODEABLE);
2911 }
2912 native_window_set_usage(mTestContext->mViVVid.ANW.get(),
2913 GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN);
2914 native_window_set_buffer_count(mTestContext->mViVVid.ANW.get(),
2915 mTestContext->mViVVid.buff_cnt);
2916
2917 ViVEncoderThread();
2918
2919 return ret;
2920 }
2921
2922 /*===========================================================================
2923 * FUNCTION : unconfigureViVCodec
2924 *
2925 * DESCRIPTION: Unconfigures video in video codec
2926 *
2927 * PARAMETERS : none
2928 *
2929 * RETURN : status_t type of status
2930 * NO_ERROR -- success
2931 * none-zero failure code
2932 *==========================================================================*/
unconfigureViVCodec()2933 status_t Interpreter::unconfigureViVCodec()
2934 {
2935 status_t ret = NO_ERROR;
2936
2937 ret = native_window_api_disconnect(mTestContext->mViVVid.ANW.get(),
2938 NATIVE_WINDOW_API_CPU);
2939 mTestContext->mViVVid.bufferProducer = NULL;
2940 mTestContext->mViVVid.codec->stop();
2941 pthread_join(mViVEncThread, NULL);
2942 mTestContext->mViVVid.muxer->stop();
2943 mTestContext->mViVVid.codec->release();
2944 mTestContext->mViVVid.codec.clear();
2945 mTestContext->mViVVid.muxer.clear();
2946 mTestContext->mViVVid.surface.clear();
2947 return ret;
2948 }
2949
2950 /*===========================================================================
2951 * FUNCTION : Interpreter
2952 *
2953 * DESCRIPTION: Interpreter constructor
2954 *
2955 * PARAMETERS : none
2956 *
2957 * RETURN : none
2958 *==========================================================================*/
Interpreter(const char * file)2959 Interpreter::Interpreter(const char *file)
2960 : mCmdIndex(0)
2961 , mScript(NULL)
2962 {
2963 if (!file){
2964 printf("no File Given\n");
2965 mUseScript = false;
2966 return;
2967 }
2968
2969 FILE *fh = fopen(file, "r");
2970 if ( !fh ) {
2971 printf("Could not open file %s\n", file);
2972 mUseScript = false;
2973 return;
2974 }
2975
2976 fseek(fh, 0, SEEK_END);
2977 int len = ftell(fh);
2978 rewind(fh);
2979
2980 if( !len ) {
2981 printf("Script file %s is empty !\n", file);
2982 fclose(fh);
2983 return;
2984 }
2985
2986 mScript = new char[len + 1];
2987 if ( !mScript ) {
2988 fclose(fh);
2989 return;
2990 }
2991
2992 fread(mScript, sizeof(char), len, fh);
2993 mScript[len] = '\0'; // ensure null terminated;
2994 fclose(fh);
2995
2996
2997 char *p1;
2998 char *p2;
2999 p1 = p2 = mScript;
3000
3001 do {
3002 switch (*p1) {
3003 case '\0':
3004 case '|':
3005 p1++;
3006 break;
3007 case SWITCH_CAMERA_CMD:
3008 case RESUME_PREVIEW_CMD:
3009 case START_PREVIEW_CMD:
3010 case STOP_PREVIEW_CMD:
3011 case CHANGE_PREVIEW_SIZE_CMD:
3012 case CHANGE_PICTURE_SIZE_CMD:
3013 case START_RECORD_CMD:
3014 case STOP_RECORD_CMD:
3015 case START_VIV_RECORD_CMD:
3016 case STOP_VIV_RECORD_CMD:
3017 case DUMP_CAPS_CMD:
3018 case AUTOFOCUS_CMD:
3019 case TAKEPICTURE_CMD:
3020 case TAKEPICTURE_IN_PICTURE_CMD:
3021 case ENABLE_PRV_CALLBACKS_CMD:
3022 case EXIT_CMD:
3023 case DELAY:
3024 p2 = p1;
3025 while( (p2 != (mScript + len)) && (*p2 != '|')) {
3026 p2++;
3027 }
3028 *p2 = '\0';
3029 if (p2 == (p1 + 1))
3030 mCommands.push_back(Command(
3031 static_cast<Interpreter::Commands_e>(*p1)));
3032 else
3033 mCommands.push_back(Command(
3034 static_cast<Interpreter::Commands_e>(*p1), (p1 + 1)));
3035 p1 = p2;
3036 break;
3037 default:
3038 printf("Invalid cmd %c \n", *p1);
3039 do {
3040 p1++;
3041
3042 } while(*p1 != '|' && p1 != (mScript + len));
3043
3044 }
3045 } while(p1 != (mScript + len));
3046 mUseScript = true;
3047 }
3048
3049 /*===========================================================================
3050 * FUNCTION : ~Interpreter
3051 *
3052 * DESCRIPTION: Interpreter destructor
3053 *
3054 * PARAMETERS : none
3055 *
3056 * RETURN : none
3057 *==========================================================================*/
~Interpreter()3058 Interpreter::~Interpreter()
3059 {
3060 if ( mScript )
3061 delete[] mScript;
3062
3063 mCommands.clear();
3064 }
3065
3066 /*===========================================================================
3067 * FUNCTION : getCommand
3068 *
3069 * DESCRIPTION : Get a command from interpreter
3070 *
3071 * PARAMETERS :
3072 * @currentCamera: Current camera context
3073 *
3074 * RETURN : command
3075 *==========================================================================*/
getCommand(sp<CameraContext> currentCamera)3076 Interpreter::Command Interpreter::getCommand(
3077 sp<CameraContext> currentCamera)
3078 {
3079 if( mUseScript ) {
3080 return mCommands[mCmdIndex++];
3081 } else {
3082 currentCamera->printMenu(currentCamera);
3083 return Interpreter::Command(
3084 static_cast<Interpreter::Commands_e>(getchar()));
3085 }
3086 }
3087
3088 /*===========================================================================
3089 * FUNCTION : TestContext
3090 *
3091 * DESCRIPTION : TestContext constructor
3092 *
3093 * PARAMETERS : None
3094 *
3095 * RETURN : None
3096 *==========================================================================*/
TestContext()3097 TestContext::TestContext()
3098 {
3099 sp<CameraContext> camera;
3100 int i = 0;
3101 mTestRunning = false;
3102 mInterpreter = NULL;
3103 mViVVid.ViVIdx = 0;
3104 mViVVid.buff_cnt = 9;
3105 mViVVid.graphBuf = 0;
3106 mViVVid.mappedBuff = NULL;
3107 mViVVid.isBuffValid = false;
3108 mViVVid.sourceCameraID = -1;
3109 mViVVid.destinationCameraID = -1;
3110 memset(&mViVBuff, 0, sizeof(ViVBuff_t));
3111
3112 ProcessState::self()->startThreadPool();
3113
3114 do {
3115 camera = new CameraContext(i);
3116 if ( NULL == camera.get() ) {
3117 break;
3118 }
3119 camera->setTestCtxInstance(this);
3120
3121 status_t stat = camera->openCamera();
3122 if ( NO_ERROR != stat ) {
3123 printf("Error encountered Openging camera id : %d\n", i);
3124 break;
3125 }
3126
3127 mAvailableCameras.add(camera);
3128 i++;
3129 } while ( i < camera->getNumberOfCameras() ) ;
3130
3131 if (i < camera->getNumberOfCameras() ) {
3132 for (size_t j = 0; j < mAvailableCameras.size(); j++) {
3133 camera = mAvailableCameras.itemAt(j);
3134 camera->closeCamera();
3135 camera.clear();
3136 }
3137
3138 mAvailableCameras.clear();
3139 }
3140 }
3141
3142 /*===========================================================================
3143 * FUNCTION : ~TestContext
3144 *
3145 * DESCRIPTION : TestContext destructor
3146 *
3147 * PARAMETERS : None
3148 *
3149 * RETURN : None
3150 *==========================================================================*/
~TestContext()3151 TestContext::~TestContext()
3152 {
3153 delete mInterpreter;
3154
3155 for (size_t j = 0; j < mAvailableCameras.size(); j++) {
3156 sp<CameraContext> camera = mAvailableCameras.itemAt(j);
3157 camera->closeCamera();
3158 camera.clear();
3159 }
3160
3161 mAvailableCameras.clear();
3162 }
3163
3164 /*===========================================================================
3165 * FUNCTION : GetCamerasNum
3166 *
3167 * DESCRIPTION : Get the number of available cameras
3168 *
3169 * PARAMETERS : None
3170 *
3171 * RETURN : Number of cameras
3172 *==========================================================================*/
GetCamerasNum()3173 int32_t TestContext::GetCamerasNum()
3174 {
3175 return mAvailableCameras.size();
3176 }
3177
3178 /*===========================================================================
3179 * FUNCTION : AddScriptFromFile
3180 *
3181 * DESCRIPTION : Add script from file
3182 *
3183 * PARAMETERS :
3184 * @scriptFile : Script file
3185 *
3186 * RETURN : status_t type of status
3187 * NO_ERROR -- success
3188 * none-zero failure code
3189 *==========================================================================*/
AddScriptFromFile(const char * scriptFile)3190 status_t TestContext::AddScriptFromFile(const char *scriptFile)
3191 {
3192 mInterpreter = new Interpreter(scriptFile);
3193 mInterpreter->setTestCtxInst(this);
3194
3195 return NO_ERROR;
3196 }
3197
3198 /*===========================================================================
3199 * FUNCTION : releasePiPBuff
3200 *
3201 * DESCRIPTION : Release video in video temp buffer
3202 *
3203 * PARAMETERS : None
3204 *
3205 * RETURN : None
3206 *==========================================================================*/
releasePiPBuff()3207 void Interpreter::releasePiPBuff() {
3208 free(mTestContext->mViVBuff.buff);
3209 mTestContext->mViVBuff.buff = NULL;
3210 }
3211
3212 /*===========================================================================
3213 * FUNCTION : functionalTest
3214 *
3215 * DESCRIPTION: queries and executes client supplied commands for testing a
3216 * particular camera.
3217 *
3218 * PARAMETERS :
3219 * @availableCameras : List with all cameras supported
3220 *
3221 * RETURN : status_t type of status
3222 * NO_ERROR -- continue testing
3223 * none-zero -- quit test
3224 *==========================================================================*/
FunctionalTest()3225 status_t TestContext::FunctionalTest()
3226 {
3227 status_t stat = NO_ERROR;
3228
3229 assert(mAvailableCameras.size());
3230
3231 if ( !mInterpreter ) {
3232 mInterpreter = new Interpreter();
3233 mInterpreter->setTestCtxInst(this);
3234 }
3235
3236
3237 mTestRunning = true;
3238
3239 while (mTestRunning) {
3240 sp<CameraContext> currentCamera =
3241 mAvailableCameras.itemAt(mCurrentCameraIndex);
3242 Interpreter::Command command =
3243 mInterpreter->getCommand(currentCamera);
3244 currentCamera->enablePrintPreview();
3245
3246 switch (command.cmd) {
3247 case Interpreter::SWITCH_CAMERA_CMD:
3248 {
3249 mCurrentCameraIndex++;
3250 mCurrentCameraIndex %= mAvailableCameras.size();
3251 currentCamera = mAvailableCameras.itemAt(mCurrentCameraIndex);
3252 }
3253 break;
3254
3255 case Interpreter::RESUME_PREVIEW_CMD:
3256 {
3257 stat = currentCamera->resumePreview();
3258 }
3259 break;
3260
3261 case Interpreter::START_PREVIEW_CMD:
3262 {
3263 stat = currentCamera->startPreview();
3264 }
3265 break;
3266
3267 case Interpreter::STOP_PREVIEW_CMD:
3268 {
3269 stat = currentCamera->stopPreview();
3270 }
3271 break;
3272
3273 case Interpreter::CHANGE_VIDEO_SIZE_CMD:
3274 {
3275 if ( command.arg )
3276 stat = currentCamera->setVideoSize(command.arg);
3277 else
3278 stat = currentCamera->nextVideoSize();
3279 }
3280 break;
3281
3282 case Interpreter::CHANGE_PREVIEW_SIZE_CMD:
3283 {
3284 if ( command.arg )
3285 stat = currentCamera->setPreviewSize(command.arg);
3286 else
3287 stat = currentCamera->nextPreviewSize();
3288 }
3289 break;
3290
3291 case Interpreter::CHANGE_PICTURE_SIZE_CMD:
3292 {
3293 if ( command.arg )
3294 stat = currentCamera->setPictureSize(command.arg);
3295 else
3296 stat = currentCamera->nextPictureSize();
3297 }
3298 break;
3299
3300 case Interpreter::DUMP_CAPS_CMD:
3301 {
3302 currentCamera->printSupportedParams();
3303 }
3304 break;
3305
3306 case Interpreter::AUTOFOCUS_CMD:
3307 {
3308 stat = currentCamera->autoFocus();
3309 }
3310 break;
3311
3312 case Interpreter::TAKEPICTURE_CMD:
3313 {
3314 stat = currentCamera->takePicture();
3315 }
3316 break;
3317
3318 case Interpreter::TAKEPICTURE_IN_PICTURE_CMD:
3319 {
3320 if (mAvailableCameras.size() == 2) {
3321 mSaveCurrentCameraIndex = mCurrentCameraIndex;
3322 for (size_t i = 0; i < mAvailableCameras.size(); i++) {
3323 mCurrentCameraIndex = i;
3324 currentCamera = mAvailableCameras.itemAt(
3325 mCurrentCameraIndex);
3326 currentCamera->enablePiPCapture();
3327 stat = currentCamera->takePicture();
3328 }
3329 mCurrentCameraIndex = mSaveCurrentCameraIndex;
3330 } else {
3331 printf("Number of available sensors should be 2\n");
3332 }
3333 }
3334 break;
3335
3336 case Interpreter::ENABLE_PRV_CALLBACKS_CMD:
3337 {
3338 stat = currentCamera->enablePreviewCallbacks();
3339 }
3340 break;
3341
3342 case Interpreter::START_RECORD_CMD:
3343 {
3344 stat = currentCamera->stopPreview();
3345 stat = currentCamera->configureRecorder();
3346 stat = currentCamera->startPreview();
3347 stat = currentCamera->startRecording();
3348 }
3349 break;
3350
3351 case Interpreter::STOP_RECORD_CMD:
3352 {
3353 stat = currentCamera->stopRecording();
3354
3355 stat = currentCamera->stopPreview();
3356 stat = currentCamera->unconfigureRecorder();
3357 stat = currentCamera->startPreview();
3358 }
3359 break;
3360
3361 case Interpreter::START_VIV_RECORD_CMD:
3362 {
3363
3364 if (mAvailableCameras.size() == 2) {
3365 mSaveCurrentCameraIndex = mCurrentCameraIndex;
3366 stat = mInterpreter->configureViVCodec();
3367 for ( size_t i = 0; i < mAvailableCameras.size(); i++ ) {
3368 mCurrentCameraIndex = i;
3369 currentCamera = mAvailableCameras.itemAt(
3370 mCurrentCameraIndex);
3371 stat = currentCamera->stopPreview();
3372 stat = currentCamera->configureViVRecording();
3373 stat = currentCamera->startPreview();
3374 stat = currentCamera->startViVRecording();
3375 }
3376 mCurrentCameraIndex = mSaveCurrentCameraIndex;
3377 } else {
3378 printf("Number of available sensors should be 2\n");
3379 }
3380
3381 }
3382 break;
3383
3384 case Interpreter::STOP_VIV_RECORD_CMD:
3385 {
3386 if (mAvailableCameras.size() == 2) {
3387 mSaveCurrentCameraIndex = mCurrentCameraIndex;
3388 for ( size_t i = 0; i < mAvailableCameras.size(); i++ ) {
3389 mCurrentCameraIndex = i;
3390 currentCamera = mAvailableCameras.itemAt(
3391 mCurrentCameraIndex);
3392 stat = currentCamera->stopViVRecording();
3393 stat = currentCamera->stopPreview();
3394 stat = currentCamera->unconfigureRecorder();
3395 stat = currentCamera->startPreview();
3396 }
3397 stat = mInterpreter->unconfigureViVCodec();
3398 mCurrentCameraIndex = mSaveCurrentCameraIndex;
3399
3400 mInterpreter->releasePiPBuff();
3401 } else {
3402 printf("Number of available sensors should be 2\n");
3403 }
3404 }
3405 break;
3406
3407 case Interpreter::EXIT_CMD:
3408 {
3409 currentCamera->stopPreview();
3410 mTestRunning = false;
3411 }
3412 break;
3413 case Interpreter::DELAY:
3414 {
3415 if ( command.arg )
3416 usleep(1000 * atoi(command.arg));
3417 }
3418 break;
3419 default:
3420 {
3421 currentCamera->disablePrintPreview();
3422 }
3423 break;
3424 }
3425 printf("Command status 0x%x \n", stat);
3426 }
3427
3428 return NO_ERROR;
3429 }
3430
3431 /*===========================================================================
3432 * FUNCTION : setViVSize
3433 *
3434 * DESCRIPTION : Set video in video size
3435 *
3436 * PARAMETERS :
3437 * @VideoSize : video size
3438 * @camIndex : camera index
3439 *
3440 * RETURN : none
3441 *==========================================================================*/
setViVSize(Size VideoSize,int camIndex)3442 void TestContext::setViVSize(Size VideoSize, int camIndex)
3443 {
3444 mViVVid.VideoSizes[camIndex] = VideoSize;
3445 }
3446
3447 /*===========================================================================
3448 * FUNCTION : main
3449 *
3450 * DESCRIPTION : main function
3451 *
3452 * PARAMETERS :
3453 * @argc : argc
3454 * @argv : argv
3455 *
3456 * RETURN : int status
3457 *==========================================================================*/
main(int argc,char * argv[])3458 int main(int argc, char *argv[])
3459 {
3460 TestContext ctx;
3461
3462 if (argc > 1) {
3463 if ( ctx.AddScriptFromFile((const char *)argv[1]) ) {
3464 printf("Could not add script file... "
3465 "continuing in normal menu mode! \n");
3466 }
3467 }
3468
3469 ctx.FunctionalTest();
3470
3471 return 0;
3472 }
3473