17

数日前、ネイティブではない OpenCV コードを実行していることについて質問しました。UnsatisfiedLinkErrorEclipseを再インストールし、すべてのパッケージを閉じて再度開くと問題は解決したと思っていましたが、OpenCVコードを既存のonCreate()メソッドに入れたらまた戻ってきました。

Start というアクティビティを含む新しい Android アプリケーションを作成しました。次に、プロジェクトのプロパティに移動し、OpenCV をライブラリとして追加しました。アクティビティのコードは次のとおりです ( Start.java):

package com.test;

import org.opencv.core.Mat;
import org.opencv.highgui.Highgui;

import android.os.Bundle;
import android.app.Activity;
import android.app.AlertDialog;
import android.view.Menu;

public class Start extends Activity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_start);

        Mat Image = Highgui.imread("/image.jpg");
        if (Image == null) {
            AlertDialog ad = new AlertDialog.Builder(this).create(); 
            ad.setMessage("Fatal error: can't open /image.jpg!");  
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.activity_start, menu);
        return true;
    }
}

そして、ここにログがあります:

08-13 12:26:14.791: E/Trace(1067): error opening trace file: No such file or directory (2)
08-13 12:26:15.191: W/dalvikvm(1067): No implementation found for native Lorg/opencv/highgui/Highgui;.imread_1:(Ljava/lang/String;)J
08-13 12:26:15.191: D/AndroidRuntime(1067): Shutting down VM
08-13 12:26:15.191: W/dalvikvm(1067): threadid=1: thread exiting with uncaught exception (group=0x40a13300)
08-13 12:26:15.201: E/AndroidRuntime(1067): FATAL EXCEPTION: main
08-13 12:26:15.201: E/AndroidRuntime(1067): java.lang.UnsatisfiedLinkError: Native method not found: org.opencv.highgui.Highgui.imread_1:(Ljava/lang/String;)J
08-13 12:26:15.201: E/AndroidRuntime(1067):     at org.opencv.highgui.Highgui.imread_1(Native Method)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at org.opencv.highgui.Highgui.imread(Highgui.java:324)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at com.test.Start.onCreate(Start.java:18)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.Activity.performCreate(Activity.java:5008)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1079)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2023)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2084)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.ActivityThread.access$600(ActivityThread.java:130)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1195)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.os.Handler.dispatchMessage(Handler.java:99)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.os.Looper.loop(Looper.java:137)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at android.app.ActivityThread.main(ActivityThread.java:4745)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at java.lang.reflect.Method.invokeNative(Native Method)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at java.lang.reflect.Method.invoke(Method.java:511)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:786)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
08-13 12:26:15.201: E/AndroidRuntime(1067):     at dalvik.system.NativeStart.main(Native Method)

繰り返しますが、これは非ネイティブ コードであるため、Unsatisfied Link Error が発生してもあまり意味がありません。

4

8 に答える 8

38

たくさんの検索の後、私はこれを見つけまし

「3. アプリケーション プロジェクトに JNI 部分がない場合は、対応する OpenCV ネイティブ ライブラリを /sdk/native/libs/ からプロジェクト ディレクトリの libs/ フォルダにコピーするだけです。」

つまり、\armeabi、\armeabi-v7a、\x86 フォルダーをコピーします。

「4. アプリケーションで OpenCV を有効にする最後のステップは、OpenCV API を呼び出す前の Java 初期化コードです。たとえば、Activity クラスの静的セクションで実行できます。これは、インスタンスの前に一度だけ実行されます。クラスが作成されます:

static {
    if (!OpenCVLoader.initDebug()) {
        // Handle initialization error
    }
}

または、onCreate メソッド内に配置することもできます。

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_load_image);
    if (!OpenCVLoader.initDebug()) {
        // Handle initialization error
    }
    [...]
}

今それは動作します!

于 2012-08-14T01:32:16.963 に答える
8

あなたが使用する必要があります

if (!OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_2, this, mOpenCVCallBack))
{
    Log.e("TEST", "Cannot connect to OpenCV Manager");
}

OnCreate() で使用する

private BaseLoaderCallback  mOpenCVCallBack = new BaseLoaderCallback(this) {
    @Override
    public void onManagerConnected(int status) {
        switch (status) {
                case LoaderCallbackInterface.SUCCESS:
                {
                               Mat Image = Highgui.imread("/image.jpg");
                               if (Image == null) {
                                   AlertDialog ad = new AlertDialog.Builder(this).create(); 
                                   ad.setMessage("Fatal error: can't open /image.jpg!");  
                                }
                } break;
                default:
                {
                    super.onManagerConnected(status);
                } break;
            }
    }
    };
于 2012-10-05T09:02:48.010 に答える
3

Android Studio のプロジェクトに opencv を追加していました。このエラーは、ネイティブ ファイルが実行時に利用できない場合に発生します。そのため、ネイティブ ファイルを正しい場所にコピーする必要があります。

最初jniLibsにこの場所に を作成/app/src/main/し、*.so ファイル (armeabi、armeabi-v7a、mips、x86) を含むすべてのフォルダーを OpenCV SDK の jniLibs にコピーし、0.7.2 以上の gradle プラグインを作成します。

ここに画像の説明を入力

于 2014-03-16T16:22:05.313 に答える
2

問題は、 OpenCV4Androidライブラリの読み込みが完了する前にHighgui.imreadメソッドを使用していることです。Android は、 OpenCV4Androidライブラリをロードする前に「onCreate」メソッドを呼び出します。したがって、次のように OpenCV コード用に別のメソッドを作成します:-

public class Start extends Activity {

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_start);
   }

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    getMenuInflater().inflate(R.menu.activity_start, menu);
    return true;
   }

public void readImage {
    Mat Image = Highgui.imread("/image.jpg");
    if(Image=null) {
    Log.i("Start", "--------Image Cannot be Loaded--------");
    else if(!Image=null) {
    Log.i("Start", "--------Image Loaded Successfully--------");
   }

}

于 2013-08-27T17:10:53.447 に答える
1

答えのリンクが機能していなかったので、うまくいった解決策を探すためにしばらく掘り下げる必要がありました。

私は最初にクラスで定義された BaseLoaderCallback を持っていました

private BaseLoaderCallback  mLoaderCallback = new BaseLoaderCallback(this) {
    @Override
    public void onManagerConnected(int status) {
        switch (status) {
            case LoaderCallbackInterface.SUCCESS:
            {
                Log.i(TAG, "OpenCV loaded successfully");
               // any immediate code for using OpenCV
            } break;
            default:
            {
                super.onManagerConnected(status);
            } break;
        }
    }
};

次に、onResume関数に次のものがありました:

@Override
public void onResume()
{
    super.onResume();
    if (!OpenCVLoader.initDebug()) {
        Log.d(TAG, "Internal OpenCV library not found. Using OpenCV Manager for initialization");
        OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_3_0_0, this, mLoaderCallback);
    } else {
        Log.d(TAG, "OpenCV library found inside package. Using it!");
        mLoaderCallback.onManagerConnected(LoaderCallbackInterface.SUCCESS);

    }
}

次のことを確認してください

1.バージョンに応じてOPENCV_VERSION_3_0_0を変更しています

  1. ロードする前に opencv ライブラリを実行しないでください。であってもonCreate()、opencv はまだロードされていません。OpenCV が正常にロードさonManagerConnected()れた switch ケースの関数に入れておくとよいでしょう。
于 2016-04-24T15:20:56.950 に答える