| diff --git a/jni/Android.mk b/jni/Android.mk |
| index 8b816270..d48e0d8e 100755 |
| --- a/jni/Android.mk |
| +++ b/jni/Android.mk |
| @@ -1,50 +1,53 @@ |
| +local_target_dir := $(TARGET_OUT_DATA)/local/tmp |
| + |
| LOCAL_PATH:= $(call my-dir) |
| |
| include $(CLEAR_VARS) |
| |
| LOCAL_C_INCLUDES := \ |
| - $(LOCAL_PATH)/feature_stab/db_vlvm \ |
| - $(LOCAL_PATH)/feature_stab/src \ |
| - $(LOCAL_PATH)/feature_stab/src/dbreg \ |
| - $(LOCAL_PATH)/feature_mos/src \ |
| - $(LOCAL_PATH)/feature_mos/src/mosaic |
| - |
| -LOCAL_CFLAGS := -O3 -DNDEBUG |
| -LOCAL_CPPFLAGS := -std=gnu++98 |
| - |
| -LOCAL_SRC_FILES := \ |
| - feature_mos_jni.cpp \ |
| - mosaic_renderer_jni.cpp \ |
| - feature_mos/src/mosaic/trsMatrix.cpp \ |
| - feature_mos/src/mosaic/AlignFeatures.cpp \ |
| - feature_mos/src/mosaic/Blend.cpp \ |
| - feature_mos/src/mosaic/Delaunay.cpp \ |
| - feature_mos/src/mosaic/ImageUtils.cpp \ |
| - feature_mos/src/mosaic/Mosaic.cpp \ |
| - feature_mos/src/mosaic/Pyramid.cpp \ |
| - feature_mos/src/mosaic_renderer/Renderer.cpp \ |
| - feature_mos/src/mosaic_renderer/WarpRenderer.cpp \ |
| - feature_mos/src/mosaic_renderer/SurfaceTextureRenderer.cpp \ |
| - feature_mos/src/mosaic_renderer/YVURenderer.cpp \ |
| - feature_mos/src/mosaic_renderer/FrameBuffer.cpp \ |
| - feature_stab/db_vlvm/db_feature_detection.cpp \ |
| - feature_stab/db_vlvm/db_feature_matching.cpp \ |
| - feature_stab/db_vlvm/db_framestitching.cpp \ |
| - feature_stab/db_vlvm/db_image_homography.cpp \ |
| - feature_stab/db_vlvm/db_rob_image_homography.cpp \ |
| - feature_stab/db_vlvm/db_utilities.cpp \ |
| - feature_stab/db_vlvm/db_utilities_camera.cpp \ |
| - feature_stab/db_vlvm/db_utilities_indexing.cpp \ |
| - feature_stab/db_vlvm/db_utilities_linalg.cpp \ |
| - feature_stab/db_vlvm/db_utilities_poly.cpp \ |
| - feature_stab/src/dbreg/dbreg.cpp \ |
| - feature_stab/src/dbreg/dbstabsmooth.cpp \ |
| - feature_stab/src/dbreg/vp_motionmodel.c |
| + $(LOCAL_PATH)/feature_mos/src \ |
| + $(LOCAL_PATH)/feature_stab/src \ |
| + $(LOCAL_PATH)/feature_stab/db_vlvm |
| |
| -LOCAL_SHARED_LIBRARIES := liblog libnativehelper libGLESv2 |
| -#LOCAL_LDLIBS := -L$(SYSROOT)/usr/lib -ldl -llog -lGLESv2 -L$(TARGET_OUT) |
| +LOCAL_SRC_FILES := benchmark.cpp \ |
| + feature_mos/src/mosaic/ImageUtils.cpp \ |
| + feature_mos/src/mosaic/Mosaic.cpp \ |
| + feature_mos/src/mosaic/AlignFeatures.cpp \ |
| + feature_mos/src/mosaic/Blend.cpp \ |
| + feature_mos/src/mosaic/Pyramid.cpp \ |
| + feature_mos/src/mosaic/trsMatrix.cpp \ |
| + feature_mos/src/mosaic/Delaunay.cpp \ |
| + feature_mos/src/mosaic_renderer/Renderer.cpp \ |
| + feature_mos/src/mosaic_renderer/WarpRenderer.cpp \ |
| + feature_mos/src/mosaic_renderer/SurfaceTextureRenderer.cpp \ |
| + feature_mos/src/mosaic_renderer/YVURenderer.cpp \ |
| + feature_mos/src/mosaic_renderer/FrameBuffer.cpp \ |
| + feature_stab/db_vlvm/db_rob_image_homography.cpp \ |
| + feature_stab/db_vlvm/db_feature_detection.cpp \ |
| + feature_stab/db_vlvm/db_image_homography.cpp \ |
| + feature_stab/db_vlvm/db_framestitching.cpp \ |
| + feature_stab/db_vlvm/db_feature_matching.cpp \ |
| + feature_stab/db_vlvm/db_utilities.cpp \ |
| + feature_stab/db_vlvm/db_utilities_camera.cpp \ |
| + feature_stab/db_vlvm/db_utilities_indexing.cpp \ |
| + feature_stab/db_vlvm/db_utilities_linalg.cpp \ |
| + feature_stab/db_vlvm/db_utilities_poly.cpp \ |
| + feature_stab/src/dbreg/dbstabsmooth.cpp \ |
| + feature_stab/src/dbreg/dbreg.cpp \ |
| + feature_stab/src/dbreg/vp_motionmodel.c |
| |
| -LOCAL_MODULE_TAGS := optional |
| +LOCAL_CFLAGS := -O3 -DNDEBUG -Wno-unused-parameter -Wno-maybe-uninitialized |
| +LOCAL_CFLAGS += $(CFLAGS_FOR_BENCH_SUITE) |
| +LOCAL_LDFLAGS := $(LDFLAGS_FOR_BENCH_SUITE) |
| +LOCAL_CPPFLAGS := -std=c++98 |
| +LOCAL_MODULE_TAGS := tests |
| +LOCAL_MODULE := panorama_bench |
| +LOCAL_MODULE_STEM_32 := panorama_bench |
| +LOCAL_MODULE_STEM_64 := panorama_bench64 |
| +LOCAL_MULTILIB := both |
| +LOCAL_MODULE_PATH := $(local_target_dir) |
| +LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk |
| +LOCAL_FORCE_STATIC_EXECUTABLE := true |
| +LOCAL_STATIC_LIBRARIES := libc libm |
| |
| -LOCAL_MODULE := libjni_legacymosaic |
| -include $(BUILD_SHARED_LIBRARY) |
| +include $(BUILD_EXECUTABLE) |
| diff --git a/jni/benchmark.cpp b/jni/benchmark.cpp |
| new file mode 100755 |
| index 00000000..2a6440f4 |
| --- /dev/null |
| +++ b/jni/benchmark.cpp |
| @@ -0,0 +1,131 @@ |
| +/* |
| + * Copyright (C) 2012 The Android Open Source Project |
| + * |
| + * Licensed under the Apache License, Version 2.0 (the "License"); |
| + * you may not use this file except in compliance with the License. |
| + * You may obtain a copy of the License at |
| + * |
| + * http://www.apache.org/licenses/LICENSE-2.0 |
| + * |
| + * Unless required by applicable law or agreed to in writing, software |
| + * distributed under the License is distributed on an "AS IS" BASIS, |
| + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| + * See the License for the specific language governing permissions and |
| + * limitations under the License. |
| + */ |
| + |
| +#include <time.h> |
| +#include <sys/types.h> |
| +#include <sys/stat.h> |
| +#include <unistd.h> |
| + |
| +#include "mosaic/Mosaic.h" |
| +#include "mosaic/ImageUtils.h" |
| + |
| +#define MAX_FRAMES 200 |
| +#define KERNEL_ITERATIONS 10 |
| + |
| +const int blendingType = Blend::BLEND_TYPE_HORZ; |
| +const int stripType = Blend::STRIP_TYPE_WIDE; |
| + |
| +ImageType yvuFrames[MAX_FRAMES]; |
| + |
| +int loadImages(const char* basename, int &width, int &height) |
| +{ |
| + char filename[512]; |
| + struct stat filestat; |
| + int i; |
| + |
| + for (i = 0; i < MAX_FRAMES; i++) { |
| + sprintf(filename, "%s_%03d.ppm", basename, i + 1); |
| + if (stat(filename, &filestat) != 0) break; |
| + ImageType rgbFrame = ImageUtils::readBinaryPPM(filename, width, height); |
| + yvuFrames[i] = ImageUtils::allocateImage(width, height, |
| + ImageUtils::IMAGE_TYPE_NUM_CHANNELS); |
| + ImageUtils::rgb2yvu(yvuFrames[i], rgbFrame, width, height); |
| + ImageUtils::freeImage(rgbFrame); |
| + } |
| + return i; |
| +} |
| + |
| +int main(int argc, char **argv) |
| +{ |
| + struct timespec t1, t2, t3; |
| + |
| + int width, height; |
| + float totalElapsedTime = 0; |
| + |
| + const char *basename; |
| + const char *filename; |
| + |
| + if (argc != 3) { |
| + printf("Usage: %s input_dir output_filename\n", argv[0]); |
| + return 0; |
| + } else { |
| + basename = argv[1]; |
| + filename = argv[2]; |
| + } |
| + |
| + // Load the images outside the computational kernel |
| + int totalFrames = loadImages(basename, width, height); |
| + |
| + if (totalFrames == 0) { |
| + printf("Image files not found. Make sure %s exists.\n", |
| + basename); |
| + return 1; |
| + } |
| + |
| + printf("%d frames loaded\n", totalFrames); |
| + |
| + |
| + // Interesting stuff is here |
| + for (int iteration = 0; iteration < KERNEL_ITERATIONS; iteration++) { |
| + Mosaic mosaic; |
| + |
| + mosaic.initialize(blendingType, stripType, width, height, -1, false, 0); |
| + |
| + clock_gettime(CLOCK_MONOTONIC, &t1); |
| + for (int i = 0; i < totalFrames; i++) { |
| + mosaic.addFrame(yvuFrames[i]); |
| + } |
| + clock_gettime(CLOCK_MONOTONIC, &t2); |
| + |
| + float progress = 0.0; |
| + bool cancelComputation = false; |
| + |
| + mosaic.createMosaic(progress, cancelComputation); |
| + |
| + int mosaicWidth, mosaicHeight; |
| + ImageType resultYVU = mosaic.getMosaic(mosaicWidth, mosaicHeight); |
| + |
| + ImageType imageRGB = ImageUtils::allocateImage( |
| + mosaicWidth, mosaicHeight, ImageUtils::IMAGE_TYPE_NUM_CHANNELS); |
| + |
| + clock_gettime(CLOCK_MONOTONIC, &t3); |
| + |
| + float elapsedTime = |
| + (t3.tv_sec - t1.tv_sec) + (t3.tv_nsec - t1.tv_nsec)/1e9; |
| + float addImageTime = |
| + (t2.tv_sec - t1.tv_sec) + (t2.tv_nsec - t1.tv_nsec)/1e9; |
| + float stitchImageTime = |
| + (t3.tv_sec - t2.tv_sec) + (t3.tv_nsec - t2.tv_nsec)/1e9; |
| + |
| + totalElapsedTime += elapsedTime; |
| + |
| + printf("Iteration %d: %dx%d moasic created: " |
| + "%.2f seconds (%.2f + %.2f)\n", |
| + iteration, mosaicWidth, mosaicHeight, |
| + elapsedTime, addImageTime, stitchImageTime); |
| + |
| + // Write the output only once for correctness check |
| + if (iteration == 0) { |
| + ImageUtils::yvu2rgb(imageRGB, resultYVU, mosaicWidth, |
| + mosaicHeight); |
| + ImageUtils::writeBinaryPPM(imageRGB, filename, mosaicWidth, |
| + mosaicHeight); |
| + } |
| + } |
| + printf("Total elapsed time: %.2f seconds\n", totalElapsedTime); |
| + |
| + return 0; |
| +} |
| diff --git a/jni/feature_mos/src/mosaic/AlignFeatures.cpp b/jni/feature_mos/src/mosaic/AlignFeatures.cpp |
| index aeabf8f9..703a5ea5 100644 |
| --- a/jni/feature_mos/src/mosaic/AlignFeatures.cpp |
| +++ b/jni/feature_mos/src/mosaic/AlignFeatures.cpp |
| @@ -30,6 +30,8 @@ |
| |
| #define LOG_TAG "AlignFeatures" |
| |
| +const double Align::DEFAULT_MAX_DISPARITY = 0.1; |
| + |
| Align::Align() |
| { |
| width = height = 0; |
| diff --git a/jni/feature_mos/src/mosaic/AlignFeatures.h b/jni/feature_mos/src/mosaic/AlignFeatures.h |
| index 19f39051..9999f575 100644 |
| --- a/jni/feature_mos/src/mosaic/AlignFeatures.h |
| +++ b/jni/feature_mos/src/mosaic/AlignFeatures.h |
| @@ -44,7 +44,7 @@ public: |
| ///// Settings for feature-based alignment |
| // Number of features to use from corner detection |
| static const int DEFAULT_NR_CORNERS=750; |
| - static const double DEFAULT_MAX_DISPARITY=0.1;//0.4; |
| + static const double DEFAULT_MAX_DISPARITY;//0.4; |
| // Type of homography to model |
| static const int DEFAULT_MOTION_MODEL=DB_HOMOGRAPHY_TYPE_R_T; |
| // static const int DEFAULT_MOTION_MODEL=DB_HOMOGRAPHY_TYPE_PROJECTIVE; |
| diff --git a/jni/feature_mos/src/mosaic/Blend.cpp b/jni/feature_mos/src/mosaic/Blend.cpp |
| index e37755de..b6a843a2 100644 |
| --- a/jni/feature_mos/src/mosaic/Blend.cpp |
| +++ b/jni/feature_mos/src/mosaic/Blend.cpp |
| @@ -26,8 +26,8 @@ |
| #include "Geometry.h" |
| #include "trsMatrix.h" |
| |
| -#include "Log.h" |
| -#define LOG_TAG "BLEND" |
| +const float Blend::LIMIT_SIZE_MULTIPLIER = 50.f * 2.0f; |
| +const float Blend::LIMIT_HEIGHT_MULTIPLIER = 2.5f; |
| |
| Blend::Blend() |
| { |
| @@ -67,7 +67,6 @@ int Blend::initialize(int blendingType, int stripType, int frame_width, int fram |
| |
| if (!m_pFrameYPyr || !m_pFrameUPyr || !m_pFrameVPyr) |
| { |
| - LOGE("Error: Could not allocate pyramids for blending"); |
| return BLEND_RET_ERROR_MEMORY; |
| } |
| |
| @@ -122,7 +121,6 @@ int Blend::runBlend(MosaicFrame **oframes, MosaicFrame **rframes, |
| |
| if (numCenters == 0) |
| { |
| - LOGE("Error: No frames to blend"); |
| return BLEND_RET_ERROR; |
| } |
| |
| @@ -228,9 +226,6 @@ int Blend::runBlend(MosaicFrame **oframes, MosaicFrame **rframes, |
| |
| if (xRightMost <= xLeftMost || yBottomMost <= yTopMost) |
| { |
| - LOGE("RunBlend: aborting -consistency check failed," |
| - "(xLeftMost, xRightMost, yTopMost, yBottomMost): (%d, %d, %d, %d)", |
| - xLeftMost, xRightMost, yTopMost, yBottomMost); |
| return BLEND_RET_ERROR; |
| } |
| |
| @@ -241,17 +236,12 @@ int Blend::runBlend(MosaicFrame **oframes, MosaicFrame **rframes, |
| ret = MosaicSizeCheck(LIMIT_SIZE_MULTIPLIER, LIMIT_HEIGHT_MULTIPLIER); |
| if (ret != BLEND_RET_OK) |
| { |
| - LOGE("RunBlend: aborting - mosaic size check failed, " |
| - "(frame_width, frame_height) vs (mosaic_width, mosaic_height): " |
| - "(%d, %d) vs (%d, %d)", width, height, Mwidth, Mheight); |
| return ret; |
| } |
| |
| - LOGI("Allocate mosaic image for blending - size: %d x %d", Mwidth, Mheight); |
| YUVinfo *imgMos = YUVinfo::allocateImage(Mwidth, Mheight); |
| if (imgMos == NULL) |
| { |
| - LOGE("RunBlend: aborting - couldn't alloc %d x %d mosaic image", Mwidth, Mheight); |
| return BLEND_RET_ERROR_MEMORY; |
| } |
| |
| @@ -362,7 +352,6 @@ int Blend::FillFramePyramid(MosaicFrame *mb) |
| !PyramidShort::BorderReduce(m_pFrameUPyr, m_wb.nlevsC) || !PyramidShort::BorderExpand(m_pFrameUPyr, m_wb.nlevsC, -1) || |
| !PyramidShort::BorderReduce(m_pFrameVPyr, m_wb.nlevsC) || !PyramidShort::BorderExpand(m_pFrameVPyr, m_wb.nlevsC, -1)) |
| { |
| - LOGE("Error: Could not generate Laplacian pyramids"); |
| return BLEND_RET_ERROR; |
| } |
| else |
| @@ -384,7 +373,6 @@ int Blend::DoMergeAndBlend(MosaicFrame **frames, int nsite, |
| m_pMosaicVPyr = PyramidShort::allocatePyramidPacked(m_wb.nlevsC,(unsigned short)rect.Width(),(unsigned short)rect.Height(),BORDER); |
| if (!m_pMosaicYPyr || !m_pMosaicUPyr || !m_pMosaicVPyr) |
| { |
| - LOGE("Error: Could not allocate pyramids for blending"); |
| return BLEND_RET_ERROR_MEMORY; |
| } |
| |
| @@ -579,6 +567,11 @@ int Blend::DoMergeAndBlend(MosaicFrame **frames, int nsite, |
| // Blend |
| PerformFinalBlending(imgMos, cropping_rect); |
| |
| + if (cropping_rect.Width() <= 0 || cropping_rect.Height() <= 0) |
| + { |
| + return BLEND_RET_ERROR; |
| + } |
| + |
| if (m_pMosaicVPyr) free(m_pMosaicVPyr); |
| if (m_pMosaicUPyr) free(m_pMosaicUPyr); |
| if (m_pMosaicYPyr) free(m_pMosaicYPyr); |
| @@ -632,7 +625,6 @@ int Blend::PerformFinalBlending(YUVinfo &imgMos, MosaicRect &cropping_rect) |
| if (!PyramidShort::BorderExpand(m_pMosaicYPyr, m_wb.nlevs, 1) || !PyramidShort::BorderExpand(m_pMosaicUPyr, m_wb.nlevsC, 1) || |
| !PyramidShort::BorderExpand(m_pMosaicVPyr, m_wb.nlevsC, 1)) |
| { |
| - LOGE("Error: Could not BorderExpand!"); |
| return BLEND_RET_ERROR; |
| } |
| |
| @@ -785,18 +777,31 @@ int Blend::PerformFinalBlending(YUVinfo &imgMos, MosaicRect &cropping_rect) |
| break; |
| } |
| } |
| + |
| } |
| |
| + RoundingCroppingSizeToMultipleOf8(cropping_rect); |
| + |
| for(int j=0; j<imgMos.Y.height; j++) |
| { |
| delete b[j]; |
| } |
| |
| - delete b; |
| + delete[] b; |
| |
| return BLEND_RET_OK; |
| } |
| |
| +void Blend::RoundingCroppingSizeToMultipleOf8(MosaicRect &rect) { |
| + int height = rect.bottom - rect.top + 1; |
| + int residue = height & 7; |
| + rect.bottom -= residue; |
| + |
| + int width = rect.right - rect.left + 1; |
| + residue = width & 7; |
| + rect.right -= residue; |
| +} |
| + |
| void Blend::ComputeMask(CSite *csite, BlendRect &vcrect, BlendRect &brect, MosaicRect &rect, YUVinfo &imgMos, int site_idx) |
| { |
| PyramidShort *dptr = m_pMosaicYPyr; |
| diff --git a/jni/feature_mos/src/mosaic/Blend.h b/jni/feature_mos/src/mosaic/Blend.h |
| index 6371fdeb..175eacd4 100644 |
| --- a/jni/feature_mos/src/mosaic/Blend.h |
| +++ b/jni/feature_mos/src/mosaic/Blend.h |
| @@ -119,9 +119,10 @@ protected: |
| void CropFinalMosaic(YUVinfo &imgMos, MosaicRect &cropping_rect); |
| |
| private: |
| - static const float LIMIT_SIZE_MULTIPLIER = 5.0f * 2.0f; |
| - static const float LIMIT_HEIGHT_MULTIPLIER = 2.5f; |
| + static const float LIMIT_SIZE_MULTIPLIER; |
| + static const float LIMIT_HEIGHT_MULTIPLIER; |
| int MosaicSizeCheck(float sizeMultiplier, float heightMultiplier); |
| + void RoundingCroppingSizeToMultipleOf8(MosaicRect& rect); |
| }; |
| |
| #endif |
| diff --git a/jni/feature_mos/src/mosaic/Delaunay.cpp b/jni/feature_mos/src/mosaic/Delaunay.cpp |
| index 82f5d203..0ce09fc5 100644 |
| --- a/jni/feature_mos/src/mosaic/Delaunay.cpp |
| +++ b/jni/feature_mos/src/mosaic/Delaunay.cpp |
| @@ -24,7 +24,7 @@ |
| |
| #define QQ 9 // Optimal value as determined by testing |
| #define DM 38 // 2^(1+DM/2) element sort capability. DM=38 for >10^6 elements |
| -#define NYL (-1) |
| +#define NYL -1 |
| #define valid(l) ccw(orig(basel), dest(l), dest(basel)) |
| |
| |
| diff --git a/jni/feature_mos/src/mosaic/ImageUtils.cpp b/jni/feature_mos/src/mosaic/ImageUtils.cpp |
| index 6d0aac0c..daa86060 100644 |
| --- a/jni/feature_mos/src/mosaic/ImageUtils.cpp |
| +++ b/jni/feature_mos/src/mosaic/ImageUtils.cpp |
| @@ -283,7 +283,7 @@ ImageType ImageUtils::readBinaryPPM(const char *filename, int &width, int &heigh |
| |
| FILE *imgin = NULL; |
| int mval=0, format=0, eret; |
| - ImageType ret = IMAGE_TYPE_NOIMAGE; |
| + ImageType ret = NULL;//IMAGE_TYPE_NOIMAGE; |
| |
| imgin = fopen(filename, "r"); |
| if (imgin == NULL) { |
| diff --git a/jni/feature_mos/src/mosaic/ImageUtils.h b/jni/feature_mos/src/mosaic/ImageUtils.h |
| index 87782383..92965ca8 100644 |
| --- a/jni/feature_mos/src/mosaic/ImageUtils.h |
| +++ b/jni/feature_mos/src/mosaic/ImageUtils.h |
| @@ -47,7 +47,7 @@ public: |
| /** |
| * Definition of an empty image. |
| */ |
| - static const int IMAGE_TYPE_NOIMAGE = NULL; |
| + static const int IMAGE_TYPE_NOIMAGE = 0; |
| |
| /** |
| * Convert image from BGR (interlaced) to YVU (non-interlaced) |
| diff --git a/jni/feature_mos/src/mosaic/Log.h b/jni/feature_mos/src/mosaic/Log.h |
| index cf6f14b1..2adfeda9 100644 |
| --- a/jni/feature_mos/src/mosaic/Log.h |
| +++ b/jni/feature_mos/src/mosaic/Log.h |
| @@ -14,7 +14,7 @@ |
| * limitations under the License. |
| */ |
| #ifndef LOG_H_ |
| -#define LOG_H_ |
| +#define LOG_H_ |
| |
| #include <android/log.h> |
| #define LOGV(...) __android_log_print(ANDROID_LOG_SILENT, LOG_TAG, __VA_ARGS__) |
| diff --git a/jni/feature_mos/src/mosaic/Mosaic.cpp b/jni/feature_mos/src/mosaic/Mosaic.cpp |
| index f17c030b..4abc6f68 100644 |
| --- a/jni/feature_mos/src/mosaic/Mosaic.cpp |
| +++ b/jni/feature_mos/src/mosaic/Mosaic.cpp |
| @@ -26,9 +26,6 @@ |
| #include "Mosaic.h" |
| #include "trsMatrix.h" |
| |
| -#include "Log.h" |
| -#define LOG_TAG "MOSAIC" |
| - |
| Mosaic::Mosaic() |
| { |
| initialized = false; |
| @@ -47,6 +44,10 @@ Mosaic::~Mosaic() |
| delete frames; |
| delete rframes; |
| |
| + for (int j = 0; j < owned_size; j++) |
| + delete owned_frames[j]; |
| + delete owned_frames; |
| + |
| if (aligner != NULL) |
| delete aligner; |
| if (blender != NULL) |
| @@ -88,13 +89,10 @@ int Mosaic::initialize(int blendingType, int stripType, int width, int height, i |
| { |
| frames[i] = NULL; |
| } |
| - |
| - |
| } |
| |
| - LOGV("Initialize %d %d", width, height); |
| - LOGV("Frame width %d,%d", width, height); |
| - LOGV("Max num frames %d", max_frames); |
| + owned_frames = new ImageType[max_frames]; |
| + owned_size = 0; |
| |
| aligner = new Align(); |
| aligner->initialize(width, height,quarter_res,thresh_still); |
| @@ -107,7 +105,6 @@ int Mosaic::initialize(int blendingType, int stripType, int width, int height, i |
| blender->initialize(blendingType, stripType, width, height); |
| } else { |
| blender = NULL; |
| - LOGE("Error: Unknown blending type %d",blendingType); |
| return MOSAIC_RET_ERROR; |
| } |
| |
| @@ -123,7 +120,15 @@ int Mosaic::addFrameRGB(ImageType imageRGB) |
| imageYVU = ImageUtils::allocateImage(this->width, this->height, ImageUtils::IMAGE_TYPE_NUM_CHANNELS); |
| ImageUtils::rgb2yvu(imageYVU, imageRGB, width, height); |
| |
| - return addFrame(imageYVU); |
| + int existing_frames_size = frames_size; |
| + int ret = addFrame(imageYVU); |
| + |
| + if (frames_size > existing_frames_size) |
| + owned_frames[owned_size++] = imageYVU; |
| + else |
| + ImageUtils::freeImage(imageYVU); |
| + |
| + return ret; |
| } |
| |
| int Mosaic::addFrame(ImageType imageYVU) |
| @@ -146,8 +151,6 @@ int Mosaic::addFrame(ImageType imageYVU) |
| |
| if (frames_size >= max_frames) |
| { |
| - LOGV("WARNING: More frames than preallocated, ignoring." |
| - "Increase maximum number of frames (-f <max_frames>) to avoid this"); |
| return MOSAIC_RET_ERROR; |
| } |
| |
| diff --git a/jni/feature_mos/src/mosaic/Mosaic.h b/jni/feature_mos/src/mosaic/Mosaic.h |
| index fc6ecd90..9dea6642 100644 |
| --- a/jni/feature_mos/src/mosaic/Mosaic.h |
| +++ b/jni/feature_mos/src/mosaic/Mosaic.h |
| @@ -181,6 +181,12 @@ protected: |
| int frames_size; |
| int max_frames; |
| |
| + /** |
| + * Implicitly created frames, should be freed by Mosaic. |
| + */ |
| + ImageType *owned_frames; |
| + int owned_size; |
| + |
| /** |
| * Initialization state. |
| */ |
| diff --git a/jni/feature_mos/src/mosaic/Pyramid.cpp b/jni/feature_mos/src/mosaic/Pyramid.cpp |
| index 945eafba..b022d73d 100644 |
| --- a/jni/feature_mos/src/mosaic/Pyramid.cpp |
| +++ b/jni/feature_mos/src/mosaic/Pyramid.cpp |
| @@ -154,24 +154,30 @@ void PyramidShort::BorderExpandOdd(PyramidShort *in, PyramidShort *out, PyramidS |
| // Vertical Filter |
| for (j = -off; j < in->height + off; j++) { |
| int j2 = j * 2; |
| - for (i = -scr->border; i < scr->width + scr->border; i++) { |
| + int limit = scr->width + scr->border; |
| + for (i = -scr->border; i < limit; i++) { |
| + int t1 = in->ptr[j][i]; |
| + int t2 = in->ptr[j+1][i]; |
| scr->ptr[j2][i] = (short) |
| - ((6 * in->ptr[j][i] + (in->ptr[j-1][i] + in->ptr[j+1][i]) + 4) >> 3); |
| - scr->ptr[j2+1][i] = (short)((in->ptr[j][i] + in->ptr[j+1][i] + 1) >> 1); |
| + ((6 * t1 + (in->ptr[j-1][i] + t2) + 4) >> 3); |
| + scr->ptr[j2+1][i] = (short)((t1 + t2 + 1) >> 1); |
| } |
| } |
| |
| BorderSpread(scr, 0, 0, 3, 3); |
| |
| // Horizontal Filter |
| - for (i = -off; i < scr->width + off; i++) { |
| - int i2 = i * 2; |
| - for (j = -out->border; j < out->height + out->border; j++) { |
| + int limit = out->height + out->border; |
| + for (j = -out->border; j < limit; j++) { |
| + for (i = -off; i < scr->width + off; i++) { |
| + int i2 = i * 2; |
| + int t1 = scr->ptr[j][i]; |
| + int t2 = scr->ptr[j][i+1]; |
| out->ptr[j][i2] = (short) (out->ptr[j][i2] + |
| - (mode * ((6 * scr->ptr[j][i] + |
| - scr->ptr[j][i-1] + scr->ptr[j][i+1] + 4) >> 3))); |
| + (mode * ((6 * t1 + |
| + scr->ptr[j][i-1] + t2 + 4) >> 3))); |
| out->ptr[j][i2+1] = (short) (out->ptr[j][i2+1] + |
| - (mode * ((scr->ptr[j][i] + scr->ptr[j][i+1] + 1) >> 1))); |
| + (mode * ((t1 + t2 + 1) >> 1))); |
| } |
| } |
| |
| diff --git a/jni/feature_mos/src/mosaic_renderer/FrameBuffer.cpp b/jni/feature_mos/src/mosaic_renderer/FrameBuffer.cpp |
| index 9a07e496..a956f23b 100755 |
| --- a/jni/feature_mos/src/mosaic_renderer/FrameBuffer.cpp |
| +++ b/jni/feature_mos/src/mosaic_renderer/FrameBuffer.cpp |
| @@ -55,6 +55,8 @@ bool FrameBuffer::Init(int width, int height, GLenum format) { |
| GL_TEXTURE_2D, |
| mTextureName, |
| 0); |
| + checkFramebufferStatus("FrameBuffer.cpp"); |
| + checkGlError("framebuffertexture2d"); |
| |
| if (!checkGlError("texture setup")) { |
| return false; |
| @@ -94,6 +96,3 @@ int FrameBuffer::GetWidth() const { |
| int FrameBuffer::GetHeight() const { |
| return mHeight; |
| } |
| - |
| - |
| - |
| diff --git a/jni/feature_mos/src/mosaic_renderer/FrameBuffer.h b/jni/feature_mos/src/mosaic_renderer/FrameBuffer.h |
| index b6a20ad1..314b1262 100755 |
| --- a/jni/feature_mos/src/mosaic_renderer/FrameBuffer.h |
| +++ b/jni/feature_mos/src/mosaic_renderer/FrameBuffer.h |
| @@ -4,7 +4,10 @@ |
| #include <GLES2/gl2.h> |
| #include <GLES2/gl2ext.h> |
| |
| -extern bool checkGlError(const char* op); |
| +#define checkGlError(op) checkGLErrorDetail(__FILE__, __LINE__, (op)) |
| + |
| +extern bool checkGLErrorDetail(const char* file, int line, const char* op); |
| +extern void checkFramebufferStatus(const char* name); |
| |
| class FrameBuffer { |
| public: |
| diff --git a/jni/feature_mos/src/mosaic_renderer/Renderer.cpp b/jni/feature_mos/src/mosaic_renderer/Renderer.cpp |
| index c5c143f9..b9938eb6 100755 |
| --- a/jni/feature_mos/src/mosaic_renderer/Renderer.cpp |
| +++ b/jni/feature_mos/src/mosaic_renderer/Renderer.cpp |
| @@ -87,7 +87,7 @@ GLuint Renderer::createProgram(const char* pVertexSource, const char* pFragmentS |
| GLint linkStatus = GL_FALSE; |
| glGetProgramiv(program, GL_LINK_STATUS, &linkStatus); |
| |
| - LOGI("Program Linked!"); |
| + LOGI("Program Linked (%d)!", program); |
| |
| if (linkStatus != GL_TRUE) |
| { |
| diff --git a/jni/feature_stab/db_vlvm/db_utilities_constants.h b/jni/feature_stab/db_vlvm/db_utilities_constants.h |
| index 612fc783..07565efd 100644 |
| --- a/jni/feature_stab/db_vlvm/db_utilities_constants.h |
| +++ b/jni/feature_stab/db_vlvm/db_utilities_constants.h |
| @@ -64,7 +64,7 @@ |
| #define DB_DEFAULT_ABS_CORNER_THRESHOLD 50000000.0 |
| #define DB_DEFAULT_REL_CORNER_THRESHOLD 0.00005 |
| #define DB_DEFAULT_MAX_DISPARITY 0.1 |
| -#define DB_DEFAULT_NO_DISPARITY (-1.0) |
| +#define DB_DEFAULT_NO_DISPARITY -1.0 |
| #define DB_DEFAULT_MAX_TRACK_LENGTH 300 |
| |
| #define DB_DEFAULT_MAX_NR_CAMERAS 1000 |
| diff --git a/jni/feature_stab/src/dbreg/dbreg.cpp b/jni/feature_stab/src/dbreg/dbreg.cpp |
| index dc7d58fe..da06aa2a 100644 |
| --- a/jni/feature_stab/src/dbreg/dbreg.cpp |
| +++ b/jni/feature_stab/src/dbreg/dbreg.cpp |
| @@ -485,7 +485,8 @@ int db_FrameToReferenceRegistration::AddFrame(const unsigned char * const * im, |
| if(m_do_motion_smoothing) |
| SmoothMotion(); |
| |
| - db_PrintDoubleMatrix(m_H_ref_to_ins,3,3); |
| + // Disable debug printing |
| + // db_PrintDoubleMatrix(m_H_ref_to_ins,3,3); |
| |
| db_Copy9(H, m_H_ref_to_ins); |
| |
| diff --git a/jni/feature_stab/src/dbreg/dbstabsmooth.cpp b/jni/feature_stab/src/dbreg/dbstabsmooth.cpp |
| index dffff8ab..2bb5d2e5 100644 |
| --- a/jni/feature_stab/src/dbreg/dbstabsmooth.cpp |
| +++ b/jni/feature_stab/src/dbreg/dbstabsmooth.cpp |
| @@ -136,7 +136,7 @@ bool db_StabilizationSmoother::smoothMotionAdaptive(/*VP_BIMG *bimg,*/int hsize, |
| smoothFactor = minSmoothFactor; |
| |
| // Find the amount of motion that must be compensated so that no "border" pixels are seen in the stable video |
| - for (smoothFactor = smoothFactor; smoothFactor >= minSmoothFactor; smoothFactor -= 0.01) { |
| + for (; smoothFactor >= minSmoothFactor; smoothFactor -= 0.01) { |
| // Compute the smoothed motion |
| if(!smoothMotion(inmot, &tmpMotion, smoothFactor)) |
| break; |
| diff --git a/jni/feature_stab/src/dbreg/vp_motionmodel.h b/jni/feature_stab/src/dbreg/vp_motionmodel.h |
| index 71a7f7e7..a63ac001 100644 |
| --- a/jni/feature_stab/src/dbreg/vp_motionmodel.h |
| +++ b/jni/feature_stab/src/dbreg/vp_motionmodel.h |
| @@ -120,7 +120,7 @@ enum VP_MOTION_MODEL { |
| VP_VFE_AFFINE=120 |
| }; |
| |
| -#define VP_REFID (-1) /* Default ID used for reference frame */ |
| +#define VP_REFID -1 /* Default ID used for reference frame */ |
| |
| typedef struct { |
| VP_TRS par; /* Contains the motion paramerers. |
| @@ -205,16 +205,16 @@ typedef struct { |
| /* Warp a 2d point (assuming the z component is zero) */ |
| #define VP_WARP_POINT_2D(inx,iny,m,outx,outy) do {\ |
| VP_PAR vpTmpWarpPnt___= MWX(m)*(inx)+MWY(m)*(iny)+MWW(m); \ |
| - (outx) = (MXX(m)*((VP_PAR)(inx))+MXY(m)*((VP_PAR)(iny))+MXW(m))/vpTmpWarpPnt___; \ |
| - (outy) = (MYX(m)*((VP_PAR)(inx))+MYY(m)*((VP_PAR)(iny))+MYW(m))/vpTmpWarpPnt___; } while (0) |
| + outx = (MXX(m)*((VP_PAR)inx)+MXY(m)*((VP_PAR)iny)+MXW(m))/vpTmpWarpPnt___; \ |
| + outy = (MYX(m)*((VP_PAR)inx)+MYY(m)*((VP_PAR)iny)+MYW(m))/vpTmpWarpPnt___; } while (0) |
| |
| /* Warp a 3d point */ |
| #define VP_WARP_POINT_3D(inx,iny,inz,m,outx,outy,outz) do {\ |
| - VP_PAR vpTmpWarpPnt___= MWX(m)*(inx)+MWY(m)*(iny)+MWZ(m)*((VP_PAR)(inz))+MWW(m); \ |
| - (outx) = (MXX(m)*((VP_PAR)(inx))+MXY(m)*((VP_PAR)(iny))+MXZ(m)*((VP_PAR)(inz))+MXW(m))/vpTmpWarpPnt___; \ |
| - (outy) = (MYX(m)*((VP_PAR)(inx))+MYY(m)*((VP_PAR)(iny))+MYZ(m)*((VP_PAR)(inz))+MYW(m))/vpTmpWarpPnt___; \ |
| - (outz) = MZX(m)*((VP_PAR)(inx))+MZY(m)*((VP_PAR)(iny))+MZZ(m)*((VP_PAR)(inz))+MZW(m); \ |
| - if ((m).type==VP_MOTION_PROJ_3D) (outz)/=vpTmpWarpPnt___; } while (0) |
| + VP_PAR vpTmpWarpPnt___= MWX(m)*(inx)+MWY(m)*(iny)+MWZ(m)*((VP_PAR)inz)+MWW(m); \ |
| + outx = (MXX(m)*((VP_PAR)inx)+MXY(m)*((VP_PAR)iny)+MXZ(m)*((VP_PAR)inz)+MXW(m))/vpTmpWarpPnt___; \ |
| + outy = (MYX(m)*((VP_PAR)inx)+MYY(m)*((VP_PAR)iny)+MYZ(m)*((VP_PAR)inz)+MYW(m))/vpTmpWarpPnt___; \ |
| + outz = MZX(m)*((VP_PAR)inx)+MZY(m)*((VP_PAR)iny)+MZZ(m)*((VP_PAR)inz)+MZW(m); \ |
| + if ((m).type==VP_MOTION_PROJ_3D) outz/=vpTmpWarpPnt___; } while (0) |
| |
| /* Projections of each component */ |
| #define VP_PROJW_3D(m,x,y,z,f) ( MWX(m)*(x)+MWY(m)*(y)+MWZ(m)*(z)+MWW(m) ) |
| @@ -224,15 +224,15 @@ typedef struct { |
| |
| /* Scale Down a matrix by Sfactor */ |
| #define VP_SCALEDOWN(m,Sfactor) do { \ |
| - MXW(m) /= (VP_PAR)(Sfactor); MWX(m) *= (VP_PAR)(Sfactor); \ |
| - MYW(m) /= (VP_PAR)(Sfactor); MWY(m) *= (VP_PAR)(Sfactor); \ |
| - MZW(m) /= (VP_PAR)(Sfactor); MWZ(m) *= (VP_PAR)(Sfactor); } while (0) |
| + MXW(m) /= (VP_PAR)Sfactor; MWX(m) *= (VP_PAR)Sfactor; \ |
| + MYW(m) /= (VP_PAR)Sfactor; MWY(m) *= (VP_PAR)Sfactor; \ |
| + MZW(m) /= (VP_PAR)Sfactor; MWZ(m) *= (VP_PAR)Sfactor; } while (0) |
| |
| /* Scale Up a matrix by Sfactor */ |
| #define VP_SCALEUP(m,Sfactor) do { \ |
| - MXW(m) *= (VP_PAR)(Sfactor); MWX(m) /= (VP_PAR)(Sfactor); \ |
| - MYW(m) *= (VP_PAR)(Sfactor); MWY(m) /= (VP_PAR)(Sfactor); \ |
| - MZW(m) *= (VP_PAR)(Sfactor); MWZ(m) /= (VP_PAR)(Sfactor); } while (0) |
| + MXW(m) *= (VP_PAR)Sfactor; MWX(m) /= (VP_PAR)Sfactor; \ |
| + MYW(m) *= (VP_PAR)Sfactor; MWY(m) /= (VP_PAR)Sfactor; \ |
| + MZW(m) *= (VP_PAR)Sfactor; MWZ(m) /= (VP_PAR)Sfactor; } while (0) |
| |
| /* Normalize the transformation matrix so that MWW is 1 */ |
| #define VP_NORMALIZE(m) if (MWW(m)!=(VP_PAR)0.0) do { \ |
| @@ -253,15 +253,15 @@ typedef struct { |
| |
| /* w' projection given a point x,y,0,f */ |
| #define VP_PROJZ(m,x,y,f) ( \ |
| - MWX(m)*((VP_PAR)(x))+MWY(m)*((VP_PAR)(y))+MWW(m)*((VP_PAR)(f))) |
| + MWX(m)*((VP_PAR)x)+MWY(m)*((VP_PAR)y)+MWW(m)*((VP_PAR)f)) |
| |
| /* X Projection given a point x,y,0,f and w' */ |
| #define VP_PROJX(m,x,y,w,f) (\ |
| - (MXX(m)*((VP_PAR)(x))+MXY(m)*((VP_PAR)(y))+MXW(m)*((VP_PAR)(f)))/((VP_PAR)(w))) |
| + (MXX(m)*((VP_PAR)x)+MXY(m)*((VP_PAR)y)+MXW(m)*((VP_PAR)f))/((VP_PAR)w)) |
| |
| /* Y Projection given a point x,y,0,f and the w' */ |
| #define VP_PROJY(m,x,y,w,f) (\ |
| - (MYX(m)*((VP_PAR)(x))+MYY(m)*((VP_PAR)(y))+MYW(m)*((VP_PAR)(f)))/((VP_PAR)(w))) |
| + (MYX(m)*((VP_PAR)x)+MYY(m)*((VP_PAR)y)+MYW(m)*((VP_PAR)f))/((VP_PAR)w)) |
| |
| /* Set the reference id for a motion */ |
| #define VP_SET_REFID(m,id) do { (m).refid=id; } while (0) |