{"id":1221,"date":"2016-02-11T11:15:54","date_gmt":"2016-02-11T03:15:54","guid":{"rendered":"https:\/\/ai.zhousir.top\/?p=1221"},"modified":"2016-02-11T11:24:00","modified_gmt":"2016-02-11T03:24:00","slug":"localbroadcastmanager-%e7%9a%84%e5%ae%9e%e7%8e%b0%e5%8e%9f%e7%90%86%ef%bc%8c%e8%bf%98%e6%98%af-binder%ef%bc%9f","status":"publish","type":"post","link":"https:\/\/ai.zhousir.top\/?p=1221","title":{"rendered":"LocalBroadcastManager \u7684\u5b9e\u73b0\u539f\u7406\uff0c\u8fd8\u662f Binder\uff1f"},"content":{"rendered":"<p>\u5bf9 LocalBroadcastManager \u5927\u5bb6\u5e94\u8be5\u90fd\u4e0d\u964c\u751f\uff0c\u76f8\u5bf9 BroadcastReceiver\uff0c\u5b83\u53ea\u80fd\u7528\u4e8e\u5e94\u7528\u5185\u901a\u4fe1\uff0c\u5b89\u5168\u6027\u66f4\u597d\uff0c\u540c\u65f6\u62e5\u6709\u66f4\u9ad8\u7684\u8fd0\u884c\u6548\u7387\u3002\u4e5f\u662f\u9700\u8981\u53d1\u9001\u5e94\u7528\u5185\u5e7f\u64ad\u65f6\u7684\u5b98\u65b9\u63a8\u8350\u3002<!--more--><\/p>\n<p>\u5927\u5bb6\u4e5f\u90fd\u77e5\u9053BroadcastReceiver\u7684\u901a\u4fe1\u662f\u8d70 Binder \u673a\u5236\u7684\uff0c\u800c LocalBroadcastManager \u56e0\u4e3a\u53ebLocalBroadcast\uff0c\u53ef\u80fd\u8ba9\u4eba\u4ea7\u751f\u4e00\u79cd\u5b83\u4e5f\u662f\u4ee5 Binder \u901a\u8baf\u65b9\u5f0f\u4e3a\u5e95\u5c42\u5b9e\u73b0\u7684\u9519\u89c9\uff0c\u70b9\u8fdb\u6e90\u7801\uff0c\u6211\u4eec\u4f1a\u53d1\u73b0\u8fd9\u4e2a\u66f4\u5b89\u5168\u9ad8\u6548\u7684\u5b9e\u73b0\u539f\u6765\u5982\u6b64\u719f\u6089\u3002<\/p>\n<p>\u8fd8\u662f\u5148\u7b80\u5355\u63d0\u4e0b LocalBroadcastManager \u4f7f\u7528\uff0c\u66f4\u591a\u53ef\u89c1\uff1aBroadcastReceiver \u8be6\u7ec6\u4ecb\u7ecd\u3002<\/p>\n<p>1. LocalBroadcastManager \u4f7f\u7528<br \/>\nLocalBroadcastManager \u7684\u4f7f\u7528\u8ddf\u4e00\u822c BroadcastReceiver \u5dee\u522b\u4e0d\u5927\u3002<br \/>\n(1) \u81ea\u5b9a\u4e49 BroadcastReceiver \u5b50\u7c7b<\/p>\n<p>[java]public class LocalBroadcastReceiver extends BroadcastReceiver {<\/p>\n<p>    @Override<br \/>\n    public void onReceive(Context context, Intent intent) {<br \/>\n        localMsg.setText(intent.getStringExtra(MSG_KEY));<br \/>\n    }<br \/>\n}[\/java]<\/p>\n<p>(2) \u6ce8\u518c\u63a5\u6536\u5668<\/p>\n<p>[java]LocalBroadcastReceiver localReceiver = new LocalBroadcastReceiver();<br \/>\nLocalBroadcastManager.getInstance(context).registerReceiver(localReceiver, new IntentFilter(ACTION_LOCAL_SEND));[\/java]<\/p>\n<p>(3) \u53d1\u9001\u5e7f\u64ad<\/p>\n<p>[java]LocalBroadcastManager.getInstance(context).sendBroadcast(new Intent(ACTION_LOCAL_SEND));[\/java]<\/p>\n<p>(4) \u53d6\u6d88\u6ce8\u518c<\/p>\n<p>[java]LocalBroadcastManager.getInstance(context).unregisterReceiver(localReceiver);[\/java]<\/p>\n<p>2. \u5b9e\u73b0<br \/>\nLocalBroadcastManager \u6e90\u4ee3\u7801\u53ef\u89c1\uff1aLocalBroadcastManager.java<br \/>\n(1) \u6784\u9020\u51fd\u6570<\/p>\n<p>[java]public static LocalBroadcastManager getInstance(Context context) {<br \/>\n    synchronized (mLock) {<br \/>\n        if (mInstance == null) {<br \/>\n            mInstance = new LocalBroadcastManager(context.getApplicationContext());<br \/>\n        }<br \/>\n        return mInstance;<br \/>\n    }<br \/>\n}<\/p>\n<p>private LocalBroadcastManager(Context context) {<br \/>\n    mAppContext = context;<br \/>\n    mHandler = new Handler(context.getMainLooper()) {<\/p>\n<p>        @Override<br \/>\n        public void handleMessage(Message msg) {<br \/>\n            switch (msg.what) {<br \/>\n                case MSG_EXEC_PENDING_BROADCASTS:<br \/>\n                    executePendingBroadcasts();<br \/>\n                    break;<br \/>\n                default:<br \/>\n                    super.handleMessage(msg);<br \/>\n            }<br \/>\n        }<br \/>\n    };<br \/>\n}[\/java]<\/p>\n<p>\u5148\u770b\u6784\u9020\u51fd\u6570\uff0c\u5355\u4f8b\u5b9e\u73b0\u56e0\u800c\u79c1\u6709\u5316\u6784\u9020\u51fd\u6570\u3002<br \/>\n\u6ce8\u610f\u7684\u662f\u57fa\u4e8e\u4e3b\u7ebf\u7a0b\u7684 Looper \u65b0\u5efa\u4e86\u4e00\u4e2a Handler\uff0chandleMessage\u4e2d\u4f1a\u8c03\u7528\u63a5\u6536\u5668\u5bf9\u5e7f\u64ad\u7684\u6d88\u606f\u8fdb\u884c\u5904\u7406\uff0c\u4e5f\u662f LocalBroadcastManager \u7684\u6838\u5fc3\u90e8\u5206\uff0c\u5177\u4f53\u89c1\u540e\u9762executePendingBroadcasts()\u4ecb\u7ecd\u3002<\/p>\n<p>\u5355\u4f8b\u51fd\u6570\u8fd8\u53ef\u4ee5\u901a\u8fc7\u53cc\u5c42\u6761\u4ef6\u5224\u65ad\u63d0\u9ad8\u6548\u7387\uff0c\u53cc\u5c42\u6761\u4ef6\u5224\u65ad\u7684\u5199\u6cd5\u53ef\u89c1\uff1a\u5355\u4f8b\u6a21\u5f0f<\/p>\n<p>(2) \u6ce8\u518c\u63a5\u6536\u5668<\/p>\n<p>[java]HashMap&lt;BroadcastReceiver, ArrayList&lt;IntentFilter&gt;&gt; mReceivers<br \/>\n            = new HashMap&lt;BroadcastReceiver, ArrayList&lt;IntentFilter&gt;&gt;();<br \/>\nHashMap&lt;String, ArrayList&lt;ReceiverRecord&gt;&gt; mActions<br \/>\n            = new HashMap&lt;String, ArrayList&lt;ReceiverRecord&gt;&gt;();<\/p>\n<p>public void registerReceiver(BroadcastReceiver receiver, IntentFilter filter) {<br \/>\n    synchronized (mReceivers) {<br \/>\n        ReceiverRecord entry = new ReceiverRecord(filter, receiver);<br \/>\n        ArrayList&lt;IntentFilter&gt; filters = mReceivers.get(receiver);<br \/>\n        if (filters == null) {<br \/>\n            filters = new ArrayList&lt;IntentFilter&gt;(1);<br \/>\n            mReceivers.put(receiver, filters);<br \/>\n        }<br \/>\n        filters.add(filter);<br \/>\n        for (int i=0; i&lt;filter.countActions(); i++) {<br \/>\n            String action = filter.getAction(i);<br \/>\n            ArrayList&lt;ReceiverRecord&gt; entries = mActions.get(action);<br \/>\n            if (entries == null) {<br \/>\n                entries = new ArrayList&lt;ReceiverRecord&gt;(1);<br \/>\n                mActions.put(action, entries);<br \/>\n            }<br \/>\n            entries.add(entry);<br \/>\n        }<br \/>\n    }<br \/>\n}  [\/java]<\/p>\n<p>mReceivers \u5b58\u50a8\u5e7f\u64ad\u548c\u8fc7\u6ee4\u5668\u4fe1\u606f\uff0c\u4ee5BroadcastReceiver\u4f5c\u4e3a key\uff0cIntentFilter\u94fe\u8868\u4f5c\u4e3a value\u3002<br \/>\nmReceivers \u662f\u63a5\u6536\u5668\u548cIntentFilter\u7684\u5bf9\u5e94\u8868\uff0c\u4e3b\u8981\u4f5c\u7528\u662f\u65b9\u4fbf\u5728unregisterReceiver(\u2026)\u53d6\u6d88\u6ce8\u518c\uff0c\u540c\u65f6\u4f5c\u4e3a\u5bf9\u8c61\u9501\u9650\u5236\u6ce8\u518c\u63a5\u6536\u5668\u3001\u53d1\u9001\u5e7f\u64ad\u3001\u53d6\u6d88\u63a5\u6536\u5668\u6ce8\u518c\u7b49\u51e0\u4e2a\u8fc7\u7a0b\u7684\u5e76\u53d1\u8bbf\u95ee\u3002<\/p>\n<p>mActions \u4ee5Action\u4e3a key\uff0c\u6ce8\u518c\u8fd9\u4e2aAction\u7684BroadcastReceiver\u94fe\u8868\u4e3a value\u3002mActions \u7684\u4e3b\u8981\u4f5c\u7528\u662f\u65b9\u4fbf\u5728\u5e7f\u64ad\u53d1\u9001\u540e\u5feb\u901f\u5f97\u5230\u53ef\u4ee5\u63a5\u6536\u5b83\u7684BroadcastReceiver\u3002<\/p>\n<p>(3) \u53d1\u9001\u5e7f\u64ad<\/p>\n<p>[java]public boolean sendBroadcast(Intent intent) {<br \/>\n    synchronized (mReceivers) {<br \/>\n        final String action = intent.getAction();<br \/>\n        final String type = intent.resolveTypeIfNeeded(mAppContext.getContentResolver());<br \/>\n        final Uri data = intent.getData();<br \/>\n        final String scheme = intent.getScheme();<br \/>\n        final Set&lt;String&gt; categories = intent.getCategories();<br \/>\n        \u2026\u2026<br \/>\n        ArrayList&lt;ReceiverRecord&gt; entries = mActions.get(intent.getAction());<br \/>\n        if (entries != null) {<br \/>\n            if (debug) Log.v(TAG, &quot;Action list: &quot; + entries);<\/p>\n<p>            ArrayList&lt;ReceiverRecord&gt; receivers = null;<br \/>\n            for (int i=0; i&lt;entries.size(); i++) {<br \/>\n                ReceiverRecord receiver = entries.get(i);<br \/>\n                if (receiver.broadcasting) {<br \/>\n                    if (debug) {<br \/>\n                        Log.v(TAG, &quot;  Filter&#8217;s target already added&quot;);<br \/>\n                    }<br \/>\n                    continue;<br \/>\n                }<\/p>\n<p>                int match = receiver.filter.match(action, type, scheme, data,<br \/>\n                        categories, &quot;LocalBroadcastManager&quot;);<br \/>\n                if (match &gt;= 0) {<br \/>\n                    if (debug) Log.v(TAG, &quot;  Filter matched!  match=0x&quot; +<br \/>\n                            Integer.toHexString(match));<br \/>\n                    if (receivers == null) {<br \/>\n                        receivers = new ArrayList&lt;ReceiverRecord&gt;();<br \/>\n                    }<br \/>\n                    receivers.add(receiver);<br \/>\n                    receiver.broadcasting = true;<br \/>\n                } else {<br \/>\n                    \u2026\u2026<br \/>\n                }<br \/>\n            }<\/p>\n<p>            if (receivers != null) {<br \/>\n                for (int i=0; i&lt;receivers.size(); i++) {<br \/>\n                    receivers.get(i).broadcasting = false;<br \/>\n                }<br \/>\n                mPendingBroadcasts.add(new BroadcastRecord(intent, receivers));<br \/>\n                if (!mHandler.hasMessages(MSG_EXEC_PENDING_BROADCASTS)) {<br \/>\n                    mHandler.sendEmptyMessage(MSG_EXEC_PENDING_BROADCASTS);<br \/>\n                }<br \/>\n                return true;<br \/>\n            }<br \/>\n        }<br \/>\n    }<br \/>\n    return false;<br \/>\n}[\/java]<\/p>\n<p>\u5148\u6839\u636eAction\u4ecemActions\u4e2d\u53d6\u51faReceiverRecord\u5217\u8868\uff0c\u5faa\u73af\u6bcf\u4e2aReceiverRecord\u5224\u65ad filter \u548c intent \u4e2d\u7684 action\u3001type\u3001scheme\u3001data\u3001categoried \u662f\u5426 match\uff0c\u662f\u7684\u8bdd\u5219\u4fdd\u5b58\u5230receivers\u5217\u8868\u4e2d\uff0c\u53d1\u9001 what \u4e3aMSG_EXEC_PENDING_BROADCASTS\u7684\u6d88\u606f\uff0c\u901a\u8fc7 Handler \u53bb\u5904\u7406\u3002<\/p>\n<p>\u5173\u4e8e match \u89c4\u5219\u53ef\u89c1\uff1aIntent Filter\u4ecb\u7ecd\u3002<\/p>\n<p>(4) \u6d88\u606f\u5904\u7406<\/p>\n<p>[java]private void executePendingBroadcasts() {<br \/>\n    while (true) {<br \/>\n        BroadcastRecord[] brs = null;<br \/>\n        synchronized (mReceivers) {<br \/>\n            final int N = mPendingBroadcasts.size();<br \/>\n            if (N &lt;= 0) {<br \/>\n                return;<br \/>\n            }<br \/>\n            brs = new BroadcastRecord[N];<br \/>\n            mPendingBroadcasts.toArray(brs);<br \/>\n            mPendingBroadcasts.clear();<br \/>\n        }<br \/>\n        for (int i=0; i&lt;brs.length; i++) {<br \/>\n            BroadcastRecord br = brs[i];<br \/>\n            for (int j=0; j&lt;br.receivers.size(); j++) {<br \/>\n                br.receivers.get(j).receiver.onReceive(mAppContext, br.intent);<br \/>\n            }<br \/>\n        }<br \/>\n    }<br \/>\n}[\/java]<\/p>\n<p>\u4ee5\u4e0a\u4e3a\u6d88\u606f\u5904\u7406\u7684\u51fd\u6570\u3002mPendingBroadcasts\u8f6c\u6362\u4e3a\u6570\u7ec4BroadcastRecord\uff0c\u5faa\u73af\u6bcf\u4e2areceiver\uff0c\u8c03\u7528\u5176onReceive\u51fd\u6570\uff0c\u8fd9\u6837\u4fbf\u5b8c\u6210\u4e86\u5e7f\u64ad\u7684\u6838\u5fc3\u903b\u8f91\u3002<\/p>\n<p>(5) \u53d6\u6d88\u6ce8\u518c<\/p>\n<p>[java]public void unregisterReceiver(BroadcastReceiver receiver) {<br \/>\n    synchronized (mReceivers) {<br \/>\n        ArrayList&lt;IntentFilter&gt; filters = mReceivers.remove(receiver);<br \/>\n        if (filters == null) {<br \/>\n            return;<br \/>\n        }<br \/>\n        for (int i=0; i&lt;filters.size(); i++) {<br \/>\n            IntentFilter filter = filters.get(i);<br \/>\n            for (int j=0; j&lt;filter.countActions(); j++) {<br \/>\n                String action = filter.getAction(j);<br \/>\n                ArrayList&lt;ReceiverRecord&gt; receivers = mActions.get(action);<br \/>\n                if (receivers != null) {<br \/>\n                    for (int k=0; k&lt;receivers.size(); k++) {<br \/>\n                        if (receivers.get(k).receiver == receiver) {<br \/>\n                            receivers.remove(k);<br \/>\n                            k&#8211;;<br \/>\n                        }<br \/>\n                    }<br \/>\n                    if (receivers.size() &lt;= 0) {<br \/>\n                        mActions.remove(action);<br \/>\n                    }<br \/>\n                }<br \/>\n            }<br \/>\n        }<br \/>\n    }<br \/>\n}[\/java]<\/p>\n<p>\u4ecemReceivers\u53camActions\u4e2d\u79fb\u9664\u76f8\u5e94\u5143\u7d20\u3002<\/p>\n<p>\u5230\u6b64\u4e3a\u6b62\u6211\u4eec\u4fbf\u975e\u5e38\u6e05\u6670\u4e86\uff1a<br \/>\n(1) LocalBroadcastManager \u7684\u6838\u5fc3\u5b9e\u73b0\u5b9e\u9645\u8fd8\u662f Handler\uff0c\u53ea\u662f\u5229\u7528\u5230\u4e86 IntentFilter \u7684 match \u529f\u80fd\uff0c\u81f3\u4e8e BroadcastReceiver \u6362\u6210\u5176\u4ed6\u63a5\u53e3\u4e5f\u65e0\u6240\u8c13\uff0c\u987a\u4fbf\u5229\u7528\u4e86\u73b0\u6210\u7684\u7c7b\u548c\u6982\u5ff5\u800c\u5df2\u3002<br \/>\n(2) \u56e0\u4e3a\u662f Handler \u5b9e\u73b0\u7684\u5e94\u7528\u5185\u7684\u901a\u4fe1\uff0c\u81ea\u7136\u5b89\u5168\u6027\u66f4\u597d\uff0c\u6548\u7387\u66f4\u9ad8\u3002<\/p>\n","protected":false},"excerpt":{"rendered":"<p>\u5bf9 LocalBroadcastManager \u5927\u5bb6\u5e94\u8be5\u90fd\u4e0d\u964c\u751f\uff0c\u76f8\u5bf9 BroadcastReceiver\uff0c\u5b83 [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[5],"tags":[],"_links":{"self":[{"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/posts\/1221"}],"collection":[{"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1221"}],"version-history":[{"count":4,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/posts\/1221\/revisions"}],"predecessor-version":[{"id":1225,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=\/wp\/v2\/posts\/1221\/revisions\/1225"}],"wp:attachment":[{"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1221"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1221"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/ai.zhousir.top\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1221"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}