Hooked up StreamableContent. Fix for #78890.
authorbillh <billh@e2bd861d-eb25-0410-b326-f6ed22b6b98c>
Wed, 11 Jun 2003 12:07:41 +0000 (12:07 +0000)
committerbillh <billh@e2bd861d-eb25-0410-b326-f6ed22b6b98c>
Wed, 11 Jun 2003 12:07:41 +0000 (12:07 +0000)
git-svn-id: http://svn.gnome.org/svn/at-spi/trunk@444 e2bd861d-eb25-0410-b326-f6ed22b6b98c

ChangeLog
NEWS
cspi/Makefile.am
cspi/spi-private.h
cspi/spi.h
cspi/spi_main.c
cspi/spi_streamablecontent.c
libspi/Makefile.am
libspi/streamablecontent.c [new file with mode: 0644]
libspi/streamablecontent.h [new file with mode: 0644]

index 123fe4e..86a13e7 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,21 @@
 2003-06-11  Bill Haneman <bill.haneman@sun.com>
 
-        Fix for #108664.
+       * libspi/streamablecontent.h:
+       * libspi/streamablecontent.c:
+       New files, provide implementation/wrappers for
+       Accessibility_StreamableContent.
+
+       * cspi/spi_streamablecontent.c:
+       Connected the C wrappers to the libspi C bindings.
+       (AccessibleStreamableContent_close): New method.
+
+       * cspi/spi.h:
+       (AccessibleStreamableContent_close): New method, needed
+       since we have an "open, [seek], read, close" model in cspi.
+       
+2003-06-11  Bill Haneman <bill.haneman@sun.com>
+
+        Fix for #108664; Padraig's revision of my original patch.
        
        * registryd/registry.h:
        Added event queue list, is_queuing, and exit_notify_timeout
diff --git a/NEWS b/NEWS
index c478536..92d12b4 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -2,6 +2,10 @@
 in HEAD:
 What's new in at-spi-1.3.1:
 
+* Fix for #113268.
+
+What's new in at-spi-1.3.1:
+
 * Fixes for 109626, 89350, 100424, 100426, 110419, 107261, 107479,
   108666, 104730, 111793.
 
index 89a1d22..e34da2b 100644 (file)
@@ -38,6 +38,7 @@ libcspi_la_SOURCES =          \
        spi-private.h           \
        spi_registry.c          \
        spi_selection.c         \
+       spi_streamablecontent.c \
        spi_table.c             \
        spi_text.c              \
        spi_value.c
index feec495..2f2bf4d 100644 (file)
@@ -67,17 +67,18 @@ struct _SPIException {
 
 #define CSPI_OBJREF(a) (((Accessible *)(a))->objref)
 
-CORBA_Environment     *cspi_ev               (void);
-SPIBoolean             cspi_exception        (void);
-Accessibility_Registry cspi_registry         (void);
-Accessible            *cspi_object_add       (CORBA_Object corba_object);
-void                   cspi_object_ref       (Accessible  *accessible);
-void                   cspi_object_unref     (Accessible  *accessible);
-Accessible            *cspi_object_borrow    (CORBA_Object corba_object);
-Accessible            *cspi_object_take      (CORBA_Object corba_object);
-void                   cspi_object_return    (Accessible  *accessible);
-SPIBoolean             cspi_accessible_is_a  (Accessible  *accessible,
-                                             const char  *interface_name);
+CORBA_Environment     *cspi_ev                (void);
+SPIBoolean             cspi_exception         (void);
+Accessibility_Registry cspi_registry          (void);
+Accessible            *cspi_object_add        (CORBA_Object corba_object);
+void                   cspi_object_ref        (Accessible  *accessible);
+void                   cspi_object_unref      (Accessible  *accessible);
+Accessible            *cspi_object_borrow     (CORBA_Object corba_object);
+Accessible            *cspi_object_take       (CORBA_Object corba_object);
+void                   cspi_object_return     (Accessible  *accessible);
+SPIBoolean             cspi_accessible_is_a   (Accessible  *accessible,
+                                              const char  *interface_name);
+void                   cspi_streams_close_all (void);
 
 #define cspi_return_if_fail(val)               \
        if (!(val))                             \
index 5b077d3..d386a1e 100644 (file)
@@ -714,6 +714,8 @@ SPIBoolean
 AccessibleStreamableContent_open (AccessibleStreamableContent *obj,
                                  const char *content_type);
 SPIBoolean
+AccessibleStreamableContent_close (AccessibleStreamableContent *obj);
+SPIBoolean
 AccessibleStreamableContent_seek (AccessibleStreamableContent *obj,
                                  long int offset,
                                  unsigned int seek_type);
index 8d7e50f..f2a4e46 100644 (file)
@@ -54,7 +54,7 @@ cspi_object_equal (gconstpointer a, gconstpointer b)
   CORBA_Object objecta = (CORBA_Object) a;
   CORBA_Object objectb = (CORBA_Object) b;
 
-  return CORBA_Object_is_equivalent (objecta, objectb, &ev);
+  return CORBA_Object_is_equivalent (objecta, objectb, cspi_ev ());
 }
 
 static void
@@ -325,6 +325,8 @@ cspi_cleanup (void)
 {
   GHashTable *refs;
 
+  cspi_streams_close_all ();
+
   refs = live_refs;
   live_refs = NULL;
   if (refs)
index 91df494..e20ebcc 100644 (file)
 
 #include <cspi/spi-private.h>
 
+
+/* TODO: factor/wrap Bonobo_Stream dependency to cspi/bonobo */
+
+struct StreamCacheItem {
+  Bonobo_Stream stream;
+  gchar *mimetype;
+};
+
+static gboolean
+streams_equal_func (gconstpointer a, gconstpointer b)
+{
+  const struct StreamCacheItem *c1 = a, *c2 = b;
+  return CORBA_Object_is_equivalent (c1->stream, c2->stream, cspi_ev ());
+}
+
+static void
+stream_release (gpointer a)
+{
+  bonobo_object_release_unref (a);
+}
+
+static void
+stream_cache_item_free (gpointer a)
+{
+  struct StreamCacheItem *cache_item = a;
+  if (cache_item) {
+    bonobo_object_release_unref (cache_item->stream);
+    SPI_freeString (cache_item->mimetype);
+    g_free (cache_item);
+  }
+}
+
+static GHashTable *streams = NULL;
+
+GHashTable *
+get_streams (void) 
+{
+  if (streams == NULL) {
+    streams = g_hash_table_new_full (g_direct_hash, streams_equal_func, 
+                                    stream_release, stream_cache_item_free);
+  }
+  return streams;
+}
+
+/* internal use only, declared in cspi-private.h */
+void
+cspi_streams_close_all (void)
+{
+  g_hash_table_destroy (get_streams ());
+}
+
 /**
  * AccessibleStreamableContent_ref:
  * @obj: a pointer to the #AccessibleStreamableContent implementor on which to
@@ -65,10 +116,20 @@ AccessibleStreamableContent_unref (AccessibleStreamableContent *obj)
 char **
 AccessibleStreamableContent_getContentTypes (AccessibleStreamableContent *obj)
 {
-  char **content_types = malloc (sizeof (char *));
-  content_types [0] = NULL;
+  Accessibility_StringSeq *mimeseq;
+  char **content_types;
+  int i;
+
+  mimeseq = Accessibility_StreamableContent_getContentTypes (CSPI_OBJREF (obj),
+                                                            cspi_ev ());
+
+  content_types = g_new0 (char *, mimeseq->_length + 1);
+  for (i = 0; i < mimeseq->_length; ++i) {
+    content_types[i] = CORBA_string_dup (mimeseq->_buffer[i]);
+  }
+  content_types [mimeseq->_length] = NULL;
+  CORBA_free (mimeseq);
 
-  /* TODO: connect this to the correct libspi implementation code */
   return content_types;
 }
 
@@ -88,7 +149,39 @@ SPIBoolean
 AccessibleStreamableContent_open (AccessibleStreamableContent *obj,
                                  const char *content_type)
 {
-  /* TODO: connect this to the correct libspi implementation code */
+  Bonobo_Stream stream;
+  struct StreamCacheItem *cache;
+  stream = Accessibility_StreamableContent_getContent (CSPI_OBJREF (obj),
+                                                      content_type,
+                                                      cspi_ev ());    
+  if (stream != CORBA_OBJECT_NIL) {
+    cache = g_new0 (struct StreamCacheItem, 1);
+    cache->stream = stream;
+    cache->mimetype = CORBA_string_dup (content_type);
+    g_hash_table_replace (get_streams (), stream, cache);
+    return TRUE;
+  }
+  return FALSE;
+}
+
+/**
+ * AccessibleStreamableContent_close:
+ * @obj: a pointer to the #AccessibleStreamableContent implementor on which to operate.
+ *
+ * Close the current streaming connection to an AccessibleStreamableContent implementor.
+ * This must be called before any subsequent AccessibleStreamableContent_open
+ * calls on the same object.
+ *
+ * Returns: #TRUE if successful, #FALSE if unsuccessful.
+ *
+ **/
+SPIBoolean
+AccessibleStreamableContent_close (AccessibleStreamableContent *obj)
+{
+  if (CSPI_OBJREF (obj) != CORBA_OBJECT_NIL) {
+    if (g_hash_table_remove (get_streams (), CSPI_OBJREF (obj)))
+      return TRUE;
+  }
   return FALSE;
 }
 
@@ -111,7 +204,7 @@ AccessibleStreamableContent_seek (AccessibleStreamableContent *obj,
                                  long int offset,
                                  unsigned int seek_type)
 {
-  /* TODO: connect this to the correct libspi implementation code */
+  /* currently Bonobo_Stream does not appear to support seek operations */
   return FALSE;
 }
 
@@ -136,7 +229,20 @@ AccessibleStreamableContent_read (AccessibleStreamableContent *obj,
                                  long int nbytes,
                                  unsigned int read_type)
 {
-  /* TODO: connect this to the correct libspi implementation code */
-  return -1;
+  Bonobo_Stream stream;
+  struct StreamCacheItem *cached; 
+  cached = g_hash_table_lookup (get_streams (), CSPI_OBJREF (obj));
+  if (cached) {
+    CORBA_long len_read;
+    stream = cached->stream;
+    if (stream != CORBA_OBJECT_NIL) {
+      guint8 *mem;
+      mem = bonobo_stream_client_read (stream, (size_t) nbytes, &len_read, cspi_ev ());
+      if (mem) memcpy (buff, mem, len_read);   
+      if (mem && ((nbytes == -1) || (len_read == nbytes)))
+       return TRUE;
+    }
+  }
+  return FALSE;
 }
 
index ed53902..440bc71 100644 (file)
@@ -33,6 +33,7 @@ libspiinclude_HEADERS =               \
        remoteobject.h          \
        selection.h             \
        stateset.h              \
+       streamablecontent.h     \
        table.h                 \
        text.h                  \
        value.h
@@ -81,6 +82,7 @@ libspi_la_SOURCES =           \
        remoteobject.c          \
        selection.c             \
        spi-private.h           \
+       streamablecontent.c     \
        stateset.c              \
        table.c                 \
        text.c                  \
diff --git a/libspi/streamablecontent.c b/libspi/streamablecontent.c
new file mode 100644 (file)
index 0000000..1c7f4e5
--- /dev/null
@@ -0,0 +1,120 @@
+/*
+ * AT-SPI - Assistive Technology Service Provider Interface
+ * (Gnome Accessibility Project; http://developer.gnome.org/projects/gap)
+ *
+ * Copyright 2001, 2002 Sun Microsystems Inc.,
+ * Copyright 2001, 2002 Ximian, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+/* streamablecontent.c : implements the StreamableContent interface */
+
+#include <config.h>
+#include <stdio.h>
+#include <libspi/accessible.h>
+#include <libspi/streamablecontent.h>
+
+/* Our parent Gtk object type */
+#define PARENT_TYPE SPI_TYPE_BASE
+
+/* A pointer to our parent object class */
+static GObjectClass *spi_streamable_parent_class;
+
+static AtkStreamableContent *
+get_streamable_from_servant (PortableServer_Servant servant)
+{
+  SpiBase *object = SPI_BASE (bonobo_object_from_servant (servant));
+  g_return_val_if_fail (object != NULL, NULL);
+  g_return_val_if_fail (ATK_IS_STREAMABLE_CONTENT(object->gobj), NULL);
+  return ATK_STREAMABLE_CONTENT (object->gobj);
+}
+
+/*
+ * CORBA Accessibility::StreamableContent::getContentTypes method implementation
+ */
+static Accessibility_StringSeq*
+impl_accessibility_streamable_get_content_types (PortableServer_Servant servant,
+                                                CORBA_Environment     *ev)
+{
+  Accessibility_StringSeq *typelist = Accessibility_StringSeq__alloc ();
+  AtkStreamableContent *streamable = get_streamable_from_servant (servant);
+  int n_types, i;
+
+  typelist->_length = 0;
+  g_return_val_if_fail (streamable != NULL, typelist);
+
+  n_types = atk_streamable_content_get_n_mime_types (streamable);
+  typelist->_length = n_types;
+  typelist->_buffer = Accessibility_StringSeq_allocbuf (n_types);
+  for (i = 0; i < n_types; ++i) {
+    const gchar *mimetype = atk_streamable_content_get_mime_type (streamable, i);
+    typelist->_buffer[i] = CORBA_string_dup (mimetype ? mimetype : "");
+  }
+
+  return typelist;
+}
+
+/*
+ * CORBA Accessibility::StreamableContent::getContent method implementation
+ */
+static Bonobo_Stream
+impl_accessibility_streamable_get_content (PortableServer_Servant servant,
+                                          const CORBA_char * content_type,
+                                          CORBA_Environment     *ev)
+{
+  Bonobo_Stream stream;
+  AtkStreamableContent *streamable = get_streamable_from_servant (servant);
+  GIOChannel *gio;
+
+  g_return_val_if_fail (streamable != NULL, NULL);
+
+  gio = atk_streamable_content_get_stream (streamable, content_type);
+
+  stream = CORBA_OBJECT_NIL; /* FIXME! */
+
+  return stream;
+}
+
+static void
+spi_streamable_class_init (SpiStreamableClass *klass)
+{
+        POA_Accessibility_StreamableContent__epv *epv = &klass->epv;
+        spi_streamable_parent_class = g_type_class_peek_parent (klass);
+
+        epv->getContentTypes = impl_accessibility_streamable_get_content_types;
+        epv->getContent = impl_accessibility_streamable_get_content;
+}
+
+static void
+spi_streamable_init (SpiStreamable *streamable)
+{
+}
+
+BONOBO_TYPE_FUNC_FULL (SpiStreamable,
+                      Accessibility_StreamableContent,
+                      PARENT_TYPE,
+                      spi_streamable)
+
+SpiStreamable *
+spi_streamable_interface_new (AtkObject *o)
+{
+    SpiStreamable *retval = g_object_new (SPI_STREAMABLE_TYPE, NULL);
+
+    spi_base_construct (SPI_BASE (retval), G_OBJECT(o));
+
+    return retval;
+}
diff --git a/libspi/streamablecontent.h b/libspi/streamablecontent.h
new file mode 100644 (file)
index 0000000..77a97d6
--- /dev/null
@@ -0,0 +1,52 @@
+/*
+ * AT-SPI - Assistive Technology Service Provider Interface
+ * (Gnome Accessibility Project; http://developer.gnome.org/projects/gap)
+ *
+ * Copyright 2001, 2002 Sun Microsystems Inc.,
+ * Copyright 2001, 2002 Ximian, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+#ifndef SPI_STREAMABLECONTENT_H_
+#define SPI_STREAMABLECONTENT_H_
+
+#include <libspi/base.h>
+#include <atk/atkstreamablecontent.h>
+
+G_BEGIN_DECLS
+
+#define SPI_STREAMABLE_TYPE        (spi_component_get_type ())
+#define SPI_STREAMABLE(o)          (G_TYPE_CHECK_INSTANCE_CAST ((o), SPI_STREAMABLE_TYPE, SpiStreamable))
+#define SPI_STREAMABLE_CLASS(k)    (G_TYPE_CHECK_CLASS_CAST((k), SPI_STREAMABLE_TYPE, SpiStreamableClass))
+#define SPI_IS_STREAMABLE(o)       (G_TYPE_CHECK_INSTANCE_TYPE ((o), SPI_STREAMABLE_TYPE))
+#define SPI_IS_STREAMABLE_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), SPI_STREAMABLE_TYPE))
+
+typedef struct {
+        SpiBase parent;
+} SpiStreamable;
+
+typedef struct {
+        SpiBaseClass parent_class;
+        POA_Accessibility_StreamableContent__epv epv;
+} SpiStreamableClass;
+
+GType         spi_streamable_get_type      (void);
+SpiStreamable *spi_streamable_interface_new (AtkObject *o);
+
+G_END_DECLS
+
+#endif /* SPI_STREAMABLECONTENT_H_ */