2015-05-29 38 views
5

目的: 我正在尋找一種方法將功能追加到按鈕的onClickListener。動態追加按鈕的onclicklistener功能Android

插圖

Button trigger = new Button(getActivity()); 
    trigger.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      method1(); 
     } 
    }); 

    Button runMethod2Button = new Button(getActivity()); 
    runMethod2Button.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      method1(); 
      method2(); 
     } 
    }); 

    Button runMethod3Button = new Button(getActivity()); 
    runMethod3Button.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      method1(); 
      method3(); 
      method4(); 
     } 
    }); 

我知道我們可以通過調用

@Override 
public void method(){ 
    super.method(); 
    // Do appended stuff 
} 

與繼承這樣做或者我們可以做到這一點內嵌

new Object(){ 
    @Override 
    public void method(){ 
     super(); 
     // Do appended stuff 
    } 
} 

事情我已經試過

擴展按鈕以包含可運行對象的列表。 然後設置點擊監聽器來觸發所有可運行的對象。

是否有不同的/更有效的方式來做到這一點?

回答

4

由於我們對於爲什麼要這樣做的背景並沒有太多的瞭解,所以很難做到最好。如果您希望原始偵聽器保持不變/未觸及,則可以使用裝飾器/包裝器模式。

Wikipedia Decorator Pattern

在具體情況下,這意味着,它是相當媲美你的Runnable的方法,但你不依賴於其他接口。寄託都通過View.OnClickListener,它具有以下優點處理:

  1. 它是一種通用方法與你甚至可以「擴展」到你沒有源代碼訪問或你不想修改的聽衆。
  2. 您可以在運行時創建的擴展行爲,你可以擴展已經實例化監聽器(相對於使用繼承)
  3. 的擴展不必知道他們是擴展,他們只是正常OnClickListeners。在您的Runnable方法中,擴展名是「特殊的」,例如,它們不會獲得通過onClick方法的參數View

    public class OriginalOnClickListener implements View.OnClickListener{ 
    
        @Override 
        public void onClick(View v) { 
         Toast.makeText(MainActivity.this,"Original Click Listener",Toast.LENGTH_LONG).show(); 
        } 
    } 
    
    public class ExtensionOnClickListener implements View.OnClickListener{ 
    
        @Override 
        public void onClick(View v) { 
         Toast.makeText(MainActivity.this,"Extension Click Listener",Toast.LENGTH_LONG).show(); 
        } 
    } 
    
    public class DecoratorOnClickListener implements View.OnClickListener { 
    
        private final List<View.OnClickListener> listeners = new ArrayList<>(); 
    
        public void add(View.OnClickListener l) { 
         listeners.add(l); 
        } 
    
        @Override 
        public void onClick(View v) { 
         for(View.OnClickListener l : listeners){ 
          l.onClick(v); 
         } 
        } 
    } 
    

而且用法是這樣的:

DecoratorOnClickListener dl = new DecoratorOnClickListener(); 

    dl.add(new OriginalOnClickListener()); 
    dl.add(new ExtensionOnClickListener()); 

    editText.setOnClickListener(dl); 
0

關於類似

Button trigger = new Button(getActivity()); 
trigger.setOnClickListener(new View.OnClickListener() { 
    @Override 
    public void onClick(View v) { 
     method1(); 
     if (someVar) method2(); 
     if (someVar2) method3(); 
    } 
}) 
1

我想了Runnable的想法是好的,根據你在這裏說的話。眼看我真的不知道爲什麼需要動態點擊處理,我認爲一個可能的解決辦法是這個樣子:

private class DynamicOnClickListener implements View.OnClickListener { 

    private final List<Runnable> mRunnables = new ArrayList<>(); 

    public void add(Runnable r) { 
     mRunnables.add(r); 
    } 

    @Override 
    public void onClick(View v) { 
     for (Runnable r : mRunnables) { 
      r.run(); 
     } 
    } 
} 

你會使用這樣的:

DynamicOnClickListener listener = new DynamicOnClickListener(); 

    listener.add(new Runnable() { 
     @Override 
     public void run() { 
      doSomething(); 
     } 
    }); 

    listener.add(new Runnable() { 
     @Override 
     public void run() { 
      doSomethingElse(); 
     } 
    }); 

    mButton.setOnClickListener(listener);