1

我有这种带有监听器的 Java 源代码。

public static class FragmentA extends ListFragment {
    OnArticleSelectedListener mListener;
    ...
    // Container Activity must implement this interface
    public interface OnArticleSelectedListener {
        public void onArticleSelected(int position);
    }
    ...
    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        try {
            mListener = (OnArticleSelectedListener) activity;
        } catch (ClassCastException e) {
            throw new ClassCastException(
                "Activity must implement OnArticleSelectedListener");
        }
    }
    ...
    @Override
    public void onListItemClick(ListView l, View v, int position, long id) {
        // Send the event to the host activity
        mListener.onArticleSelected(position);
    }
}

我以这种方式实现它:

public class MyActivity implements FragmentA.OnArticleSelectedListener {
    ...
    @Override
    public void onArticleSelected(int pos) {
        // do something
    }
}

所以,现在我想把它转换成 Scala。我想,我应该使用特质。[已解决:在这堂课中,我得到了错误onAttach] not found: value OnArticleSelectedListener

class FragmentA extends ListFragment {
    var mListener: OnArticleSelectedListener = null
    ...
    trait OnArticleSelectedListener {
        def onArticleSelected(position: Int)
    }
    ...
    override def onAttach(activity: Activity) {
        super.onAttach(activity)
        mListener = (OnArticleSelectedListener) activity;
    }
    ...
    override def onListItemClick(l: ListView, v: View, position: Int, id: Long) {
        // Send the event to the host activity
        mListener.onArticleSelected(position);
    }
}

在活动中,我不知道如何“实现”特征。我知道关键字是“with”,但extends ... with FragmentA.OnArticleSelectedListenerextends ... with OnArticleSelectedListener显示错误not found: type FragmentAnot found: type OnArticleSelectedListener.

有人知道如何解决这个问题吗?

4

1 回答 1

2

在 Scala 中,您可以使用asInstanceOf[Foo]. 在这种情况下,Scala 编译器认为您指的是一个被调用的值OnArticleSelectedListener但找不到它,因为它不是一个值而是一个类型。要activity转换为OnArticleSelectedListener,您可以使用以下代码:

activity.asInstanceOf[OnArticleSelectedListener]

但是,首选方法是使用此处描述的模式匹配。如果你采用这种方法,你可以写:

mListener = activity match {
    case myActivity: OnArticleSelectedListener => activity
    case _ => throw new ClassCastException 
}

在这种情况下我会坚持使用asInstanceOf,因为语义完全相同并且更简洁。

如果您将定义移到类OnArticleSelectedListener之外FragmentA,您应该能够像这样扩展它:

 trait OnArticleSelectedListener { def onArticleSelected(position: Int) }
 class MyActivity extends OnArticleSelectedListener {
   def onArticleSelected(position: Int) { ... }
 }
于 2013-03-05T17:30:53.833 回答