2013-02-20 89 views
15

मैंने शुरुआत में अपनी गतिविधि में एक एसिंक कार्य लागू किया जो सर्वर को डेटा भेजता है। लेकिन जब मैंने गतिविधियों को बदल दिया तो कनेक्शन खो गया था। यह मेरा दृष्टिकोण से बचने के लिए एक सेवा है जो नेटवर्क आपरेशन केंद्रीकृत और सर्वर से डेटा भेजता है और इस सेवा के लिए कोडएंड्रॉइड क्लाइंट सर्वर से कनेक्ट गतिविधि को बदलने और सर्वर पर डेटा भेजने के लिए कैसे रखें?

import java.io.BufferedWriter; 
import java.io.OutputStreamWriter; 
import java.io.PrintWriter; 
import java.net.InetAddress; 
import java.net.Socket; 

import android.app.Service; 
import android.content.Intent; 
import android.os.Binder; 
import android.os.IBinder; 
import android.util.Log; 
import android.widget.Toast; 

public class SocketService extends Service { 
    public static final String SERVERIP = ""; //your computer IP address should be written here 
    public static final int SERVERPORT = 5000; 
    PrintWriter out; 
    Socket socket; 
    InetAddress serverAddr; 

@Override 
public IBinder onBind(Intent intent) { 
    // TODO Auto-generated method stub 
    System.out.println("I am in Ibinder onBind method"); 
     return myBinder; 
} 

    private final IBinder myBinder = new LocalBinder(); 
    TCPClient mTcpClient = new TCPClient(); 

    public class LocalBinder extends Binder { 
     public SocketService getService() { 
      System.out.println("I am in Localbinder "); 
      return SocketService.this; 

     } 
    } 

    @Override 
    public void onCreate() { 
     super.onCreate(); 
     System.out.println("I am in on create");  
    } 

    public void IsBoundable(){ 
     Toast.makeText(this,"I bind like butter", Toast.LENGTH_LONG).show(); 
    } 

    public void sendMessage(String message){ 
     if (out != null && !out.checkError()) { 
      System.out.println("in sendMessage"+message); 
      out.println(message); 
      out.flush(); 
     } 
    } 

    @Override 
    public int onStartCommand(Intent intent,int flags, int startId){ 
     super.onStartCommand(intent, flags, startId); 
     System.out.println("I am in on start"); 
     // Toast.makeText(this,"Service created ...", Toast.LENGTH_LONG).show(); 
     Runnable connect = new connectSocket(); 
     new Thread(connect).start(); 
     return START_STICKY; 
    } 


    class connectSocket implements Runnable { 

     @Override 
     public void run() { 


      try { 
       //here you must put your computer's IP address. 
       serverAddr = InetAddress.getByName(SERVERIP); 
       Log.e("TCP Client", "C: Connecting..."); 
       //create a socket to make the connection with the server 

       socket = new Socket(serverAddr, SERVERPORT); 

       try { 


        //send the message to the server 
        out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())), true); 


        Log.e("TCP Client", "C: Sent."); 

        Log.e("TCP Client", "C: Done."); 


        } 
       catch (Exception e) { 

        Log.e("TCP", "S: Error", e); 

       } 
      } catch (Exception e) { 

       Log.e("TCP", "C: Error", e); 

      } 

     } 

    } 


    @Override 
    public void onDestroy() { 
     super.onDestroy(); 
      try { 
       socket.close(); 
      } catch (Exception e) { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
      } 
      socket = null; 
     } 


    } 

नीचे दी गई है Rotator.java मेरी गतिविधि है जो मैं इस सेवा पर बने रहें है लागू करने के लिए किया गया था। मेरी गतिविधि से कोड के कुछ टुकड़े निम्नलिखित हैं।

private ServiceConnection mConnection = new ServiceConnection() { 
      //EDITED PART 
    @Override 
    public void onServiceConnected(ComponentName name, IBinder service) { 
     // TODO Auto-generated method stub 
     mBoundService = ((SocketService.LocalBinder)service).getService(); 

    } 

    @Override 
    public void onServiceDisconnected(ComponentName name) { 
     // TODO Auto-generated method stub 
     mBoundService = null; 
    } 

    }; 


    private void doBindService() { 
     bindService(new Intent(Rotator.this, SocketService.class), mConnection, Context.BIND_AUTO_CREATE); 
     mIsBound = true; 
     if(mBoundService!=null){ 
     mBoundService.IsBoundable(); 
     } 
    } 


    private void doUnbindService() { 
     if (mIsBound) { 
      // Detach our existing connection. 
      unbindService(mConnection); 
      mIsBound = false; 
     } 
    } 

@Override 
public void onCreate(Bundle savedInstanceState) 
{ 
     super.onCreate(savedInstanceState); 
     gestureDetector = new GestureDetector(this, new GestureListener()); 
     setContentView(R.layout.activity_rotator); 


     //Binding the activity to the service to perform client-server operations 
     //start service on create 
     startService(new Intent(Rotator.this,SocketService.class)); 
     doBindService(); 
        ........... 
        ........... 
} 


@Override 
protected void onDestroy() { 
    super.onDestroy(); 
    doUnbindService(); 
} 

अब इस सेवा, पृष्ठभूमि में चलता है के रूप में अगर मैं निम्नलिखित

if(mBoundService!=null) 
{ 
    mBoundService.sendMessage("right"); 
} 

उत्तर

5

कोड सही है। एकमात्र गलती यह थी कि मैं सेवा कनेक्ट() विधि और दूसरी बार क्रिएट() विधि में सेवा शुरू करने की कोशिश कर रहा था।

मैंने लॉन्चर गतिविधि में केवल क्रिएट() विधि में सेवा शुरू करने के लिए अपना कोड बदल दिया। बाकी गतिविधियां सीधे doBindService() विधि

+0

आपने अभी अपना समय बचाया है। – BSKANIA

+0

आपका उपरोक्त कोड सही है या आपने उपरोक्त कोड में दो बार सेवा शुरू की है? आप कोड से ऊपर बदल गए? मैं देख सकता हूं कि आपने startervice विधि का उपयोग करके एक बार शुरू किया और एक बार doBindservice विधि का उपयोग कर। कृपया सही करें। मैं इस –

+0

@sam_k पढ़ने के बाद एक conffuse मैंने केवल प्रारंभिकता पर startService विधि का उपयोग किया है जो सेवा शुरू करता है। शेष गतिविधियां केवल doBindService() विधि को क्रेट में उपयोग करती हैं। उपरोक्त कोड सही कोड के साथ संपादित किया गया है। मैं आपके भ्रम को समझ नहीं पा रहा हूं – Giz

2

एक सेवा एक Activity के लिए बाध्य है जब सर्वर मैं उपयोग करने के लिए कुछ डेटा भेजने के लिए चाहते हैं, यह मार डाला हो जाता है जब गतिविधि बंद हो गई है, यह केवल Activity के लिए पृष्ठभूमि सेवा की तरह है। इसलिए, इसे चलाने के लिए, onStartCommand() विधि को अपने Service कक्षा में लागू करें और this.START_STICKY लौटाएं। और प्रबंधन करें कि आप इस विधि में सेवा कर रहे हैं।

+0

का उपयोग कर सेवा से जुड़ती हैं मैंने अपने सेवा कोड में पहले से ही ऐसा किया है। लेकिन मुझे नहीं पता कि सर्वर को भेजने के लिए एसिंक कार्य को डेटा कैसे भेजना है। – Giz

+0

गतिविधि में एमटीसीपी क्लाइंट हमेशा शून्य है। – Giz

+0

नहीं, 'सेवा' के एंड्रॉइड दस्तावेज़ों की जांच करें, यदि आप इसे 'बाइंडर' का उपयोग करके 'गतिविधि' पर बाध्य कर रहे हैं तो यह स्वचालित रूप से बंद हो जाता है। इसे 'बाइंडर' से हटाने का प्रयास करें और इसके बजाय इसे स्टार्ट कमांड() पर आज़माएं। यही वह है जो मैं आपको बता रहा हूं। – AbdulHannan