Archive for November 18th, 2009


[GTK编程]如何读取网络中的图片创建image控件

November 18th, 2009 — 11:00pm

发个牢骚,五千万个干!昨天可是想破头了,今天起来翻翻文档就实现了。
代码相当的ugly,希望有高手赐教更方便的方法,
实现方法很简单就是通过curl访问读取到内存中,
然后调用gdk_pixbuf_new_from_stream,
最后通过gtk_image_new_from_pixbuf创建。

/*
功能:演示在GTK中如何读取网络中的图片创建image控件
编译:gcc -Wall -g `pkg-config –cflags –libs gtk+-2.0`  pixbuf.c -o pixbuf
作者:SuPanYong@Gmail.com
主页:http://www.spy8888.com
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <gtk/gtk.h>
#include <curl/curl.h>
#include <curl/types.h>
#include <curl/easy.h>
#include <gio/gio.h>
 
struct MemoryStruct {
  char *memory;
  size_t size;
};
 /*
 代码出处http://curl.haxx.se/libcurl/c/getinmemory.html
 */
static void *myrealloc(void *ptr, size_t size)
{
  if(ptr)
    return realloc(ptr, size);
  else
    return malloc(size);
}
 
static size_t
WriteMemoryCallback(void *ptr, size_t size, size_t nmemb, void *data)
{
  size_t realsize = size * nmemb;
  struct MemoryStruct *mem = (struct MemoryStruct *)data;
 
  mem->memory = myrealloc(mem->memory, mem->size + realsize + 1);
  if (mem->memory) {
    memcpy(&(mem->memory[mem->size]), ptr, realsize);
    mem->size += realsize;
    mem->memory[mem->size] = 0;
  }
  return realsize;
}
/*网络图片地址*/
gchar *url=
“http://spy8888.com/wp-content/uploads/2009/11/gun-1255533971-stone-arshavin.jpg”;

int main(int argc, char **argv)
{
  GtkWidget *window,*image;
  GdkPixbuf *pixbuf;
  GInputStream *input_stream;
  CURL *curl_handle;
  GError *gerror=NULL;
  struct MemoryStruct chunk;
  chunk.memory=NULL;
  chunk.size = 0;   
 
  curl_global_init(CURL_GLOBAL_ALL);
  gtk_init (&argc, &argv);
 
  curl_handle = curl_easy_init();
  curl_easy_setopt(curl_handle, CURLOPT_URL, url);
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);
  /*访问并读取到内存*/
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&chunk);
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, “libcurl-agent/1.0″);
  curl_easy_perform(curl_handle);
  curl_easy_cleanup(curl_handle);
  curl_global_cleanup();
  /*从内存读取*/
  input_stream = g_memory_input_stream_new_from_data(chunk.memory, chunk.size, NULL);
  /*创建pixbuf来自stream*/
  pixbuf = gdk_pixbuf_new_from_stream(input_stream, NULL, &gerror);
  /*释放*/
  g_input_stream_close(input_stream, NULL, NULL);
  g_object_unref(input_stream);

  window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
  gtk_window_set_title (GTK_WINDOW (window), “Pixbuf Image”);
 
  g_signal_connect (G_OBJECT (window), “destroy”,
                    G_CALLBACK (gtk_main_quit), NULL);                  
  /*创建image来自pixbuf*/
  image = gtk_image_new_from_pixbuf(pixbuf);
 
  gtk_container_add (GTK_CONTAINER (window), image);
  gtk_widget_show_all (window);
  gtk_main ();

  return 0;
}

Comment » | 技术

Back to top