0

さまざまなボタンをさまざまなアクティビティにリンクしようとしています。つまり、実質的にナビゲーション メニューを作成します。

私はより少ないコードを使用しようとしているので、ボタンIDを動的に識別してアクティビティへのリンクを与えるために値を渡すことができる1つの関数を作成しようとしています.

ここに私のxmlがあります:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <Button
        android:id="@+id/nav1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_alignParentRight="true"
        android:layout_alignParentTop="true"
        android:text="@string/nav1" />

    <Button
        android:id="@+id/nav2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_alignParentRight="true"
        android:layout_below="@+id/nav1"
        android:text="@string/nav2" />

</RelativeLayout>

これが私のJavaです:

package com.example.myfirstapp;

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;

public class Nav extends Activity {

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

        String nav1 = "nav1";
        String nav2 = "nav2";

        String MainActivity = "MainActivity";
        String SQLite = "SQLite";

        navButton(nav1, MainActivity);
        navButton(nav2, SQLite);
    }

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

    private void navButton(String buttonId, String activityName){
        String bId = buttonId;
        final Class<?> aName = Class.forName(activityName);
        int resId = getResources().getIdentifier(bId, "id", getPackageName());
        Button b = (Button) findViewById(resId);
        OnClickListener onClickListener = new OnClickListener(){
            @Override
            public void onClick(View v) {
                Intent i = new Intent(Nav.this, aName);
                startActivity(i);
            }};
        b.setOnClickListener(onClickListener);
    }
}

オンラインでエラーが発生します:

final Class<?> aName = Class.forName(activityName);

そしてそれは言います:

Unhandled exception type ClassNotFoundException

または、これを行うための最良の方法は何ですか

4

3 に答える 3

3

Class.forName を使用するときはいつでも、「mypackage.myclass」などの修飾名を渡します。非修飾名で機能するかどうかはわかりません。

いずれにせよ、なぜ文字列を渡してから forName を実行するのでしょうか? 署名を変更して Class オブジェクトを取得し、MainActivity.class などを渡すだけにしないのはなぜですか? 次に、実行時ではなくコンパイル時に、欠落しているクラスやスペルミスを見つけます。

コメントに応じて更新

public class Nav extends Activity { 

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

    navButton("nav1", MainActivity.class); 
    navButton("nav2", SQLite.class); 
} 

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

private void navButton(String buttonId, Class aName){ 
    String bId = buttonId; 
    // aName now passed in so doesn't need to be looked up
    ... etc ...
} 
} 

上記はコンパイルして実行する必要があると思います。試したことはありませんが、似たようなことをしたことがあります。パッケージの設定方法によっては、.class.

于 2012-07-31T16:01:58.417 に答える
0

アプリケーションでアクティビティを定義しましたAndroidManifest.xmlか?

于 2012-07-31T15:57:31.283 に答える
0

チェックされた例外をキャッチしていませんClassNotFoundException。関連するコードをtry/catchブロックでラップする必要があります。

try {
    final Class<?> aName = Class.forName(activityName);
    //etc...
} catch (ClassNotFoundException e) {
    //Do whatever cleanup you have to do in case this situation occurs.
}

ただし、これはクリックリスナーを設定するための非常に厄介な方法のようです。リフレクションを実行する代わりに、クラス自体をnavButtonメソッドに渡すことができないのはなぜですか(代替手段がある場合は常に最後の手段になるはずです)。

于 2012-07-31T16:02:57.493 に答える