la lista de Android se actualiza solo desde un vacío y no desde otro

esto es bastante extraño para mí: en mi proyecto (que por cierto se deriva de Yaxim, por lo que es una aplicación de chat para Android), estoy tratando de implementar la notificación de escritura a través del messageeventlistener. Recibo el evento de notificación. Para que aparezca en el listview (que está en otra clase) estoy agregando una fila en la base de datos, como si fuera un mensaje (solo el texto es "..."). Agregué un contador y la fila se insertó correctamente en la base de datos (posteriormente, la fila se elimina de la base de datos cuando llega el mensaje real). La notificación de cambios también se llama correctamente. Lo extraño es que, a pesar de todo esto, la fila no aparece en la vista de lista. Si muevo el procedimiento unas pocas líneas más abajo, en el detector de paquetes para los mensajes regulares, se inserta. Sin embargo, no puedo dejarlo así porque el paquete de escucha no recibe correctamente todas las notificaciones de composición, por lo que no funciona todo el tiempo para ese propósito. Además, aunque la notificación de escritura se inserta correctamente en la base de datos, si mantengo el procedimiento en el mensajeEventNotificationListener(), el mensaje de notificación de escritura no se elimina cuando llega el mensaje real (y el iCount sigue aumentando); si pongo el procedimiento en el paqueteListener lo hace (por lo tanto, iCount es igual a 0 después de que el mensaje se inserta en la base de datos)

Este es el detector de eventos del mensaje:

private void messageEventNotificationListener(){
    // Create a MessageEventManager
    if (mMessageEventManager == null)
        mMessageEventManager = new MessageEventManager(mXMPPConnection);
      // Add the listener that will react to the event notifications
    mMessageEventManager.addMessageEventNotificationListener(new MessageEventNotificationListener() {
          public void deliveredNotification(String from, String packetID) {
              Log.d(TAG, "The message has been delivered (" + from + ", " + packetID + ")");
          }

          public void displayedNotification(String from, String packetID) {
              Log.d(TAG, "The message has been displayed (" + from + ", " + packetID + ")");
          }

          public void composingNotification(String from, String packetID) {
              Log.d(TAG, "The message's receiver is composing a reply (" + from + ", " + packetID + ")");
              //controlla se l'utente non sta già scrivendo 
              String selection = ChatConstants.JID + " = '" + from + "' AND " +
                        ChatConstants.DELIVERY_STATUS + " = " + ChatConstants.DS_WRITING;

                Cursor cursor = mContentResolver.query(ChatProvider.CONTENT_URI,
                            new String[] { "count(" + ChatConstants._ID + ")" },
                            selection, null, null);
                cursor.moveToFirst();
                int iCount = cursor.getInt(0);
                //if (iCount == 0)
                //{
                    addChatMessageToDB(ChatConstants.INCOMING, from, "...", ChatConstants.DS_WRITING, System.currentTimeMillis(), packetID);

                //}

          }

          public void offlineNotification(String from, String packetID) {
              Log.d(TAG, "The message's receiver is offline (" + from + ", " + packetID + ")");
          }

          public void cancelledNotification(String from, String packetID) {
              Log.d(TAG, "The message's receiver cancelled composing a reply (" + from + ", " + packetID + ")");


          }
      });   

}

y aquí está el paquete de escucha:

private void registerMessageListener() {
    // do not register multiple packet listeners
    if (mPacketListener != null)
        mXMPPConnection.removePacketListener(mPacketListener);

    PacketTypeFilter filter = new PacketTypeFilter(Message.class);

    mPacketListener = new PacketListener() {
        public void processPacket(Packet packet) {
            try {
            if (packet instanceof Message) {
                Message msg = (Message) packet;
                String chatMessage = msg.getBody();

                DeliveryReceipt dr = (DeliveryReceipt)msg.getExtension("received", DeliveryReceipt.NAMESPACE);
                if (dr != null) {
                    Log.d(TAG, "got delivery receipt for " + dr.getId());
                    changeMessageDeliveryStatus(dr.getId(), ChatConstants.DS_DELIVERED);
                }


                if (chatMessage == null)
                    return;

                if (msg.getType() == Message.Type.error) {
                    chatMessage = "<Error> " + chatMessage;
                }

                long ts;
                DelayInfo timestamp = (DelayInfo)msg.getExtension("delay", "urn:xmpp:delay");
                if (timestamp == null)
                    timestamp = (DelayInfo)msg.getExtension("x", "jabber:x:delay");
                if (timestamp != null)
                    ts = timestamp.getStamp().getTime();
                else
                    ts = System.currentTimeMillis();

                String fromJID = getJabberID(msg.getFrom());

                //elimina il messaggio "writing" se esiste
                     deleteWritingChatMessageFromDB(fromJID);

                    if (msg.getExtension("request", DeliveryReceipt.NAMESPACE) != null) {
                        // got XEP-0184 request, send receipt
                        sendReceipt(msg.getFrom(), msg.getPacketID());
                    }

                    addChatMessageToDB(ChatConstants.INCOMING, fromJID, chatMessage, ChatConstants.DS_NEW, ts, msg.getPacketID());
                    mServiceCallBack.newMessage(fromJID, chatMessage);
                }
            }
            } catch (Exception e) {
                // SMACK silently discards exceptions dropped from processPacket :(
                Log.e(TAG, "failed to process packet:");
                e.printStackTrace();
            }

    };

    mXMPPConnection.addPacketListener(mPacketListener, filter);
}

y finalmente el método de inserción y eliminación

private void addChatMessageToDB(int direction, String JID,
        String message, int delivery_status, long ts, String packetID) {
    ContentValues values = new ContentValues();

    values.put(ChatConstants.DIRECTION, direction);
    values.put(ChatConstants.JID, JID);
    values.put(ChatConstants.MESSAGE, message);
    values.put(ChatConstants.DELIVERY_STATUS, delivery_status);
    values.put(ChatConstants.DATE, ts);
    values.put(ChatConstants.PACKET_ID, packetID);

    Uri noteUri = mContentResolver.insert(ChatProvider.CONTENT_URI, values);
    //mContentResolver.notifyChange(noteUri, null);
}

private void deleteWritingChatMessageFromDB(String JID) {
    int count = mContentResolver.delete(ChatProvider.CONTENT_URI,
            ChatConstants.JID + " = ? AND " + ChatConstants.MESSAGE + " = ? AND " + ChatConstants.DELIVERY_STATUS + " = ?", new String[] { JID, "...", "3" });
    debugLog("deleteWritingChatMessageEntryFromDB: Deleted " + count + " entries");

}

ambos métodos son llamados a la clase ChatProvider y terminan con getContext().getContentResolver().notifyChange(url, null);

preguntado el 08 de septiembre de 12 a las 09:09

1 Respuestas

Resulta que el problema era diferente: publico esto en caso de que alguien más tenga el mismo problema. De hecho, el mensaje se insertó en la base de datos, pero mientras que el detector de paquetes devuelve solo el jid, el detector de eventos del mensaje también devuelve el jid con el recurso al final, que debe eliminarse antes de la inserción. Hecho eso, el mensaje apareció en la lista. Además: el código que publiqué no es completamente correcto para manejar el evento de mensaje. Los oyentes deben llamarse directamente desde el paqueteListener.

Respondido el 13 de Septiembre de 12 a las 18:09

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.