⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 swfedit_file.c

📁 Swfdec is a decoder/renderer for Macromedia Flash animations. The decoding and rendering engine is
💻 C
字号:
/* Swfedit * Copyright (C) 2007 Benjamin Otte <otte@gnome.org> * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 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 * Lesser General Public License for more details. *  * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor,  * Boston, MA  02110-1301  USA */#ifdef HAVE_CONFIG_H#include "config.h"#endif#include <zlib.h>#include "libswfdec/swfdec_bits.h"#include "libswfdec/swfdec_buffer.h"#include "libswfdec/swfdec_debug.h"#include "libswfdec/swfdec_swf_decoder.h"#include "swfdec_out.h"#include "swfedit_file.h"#include "swfedit_tag.h"G_DEFINE_TYPE (SwfeditFile, swfedit_file, SWFEDIT_TYPE_TOKEN)static voidswfedit_file_dispose (GObject *object){  SwfeditFile *file = SWFEDIT_FILE (object);  g_free (file->filename);  G_OBJECT_CLASS (swfedit_file_parent_class)->dispose (object);}static void *zalloc (void *opaque, unsigned int items, unsigned int size){  return g_malloc (items * size);}static voidzfree (void *opaque, void *addr){  g_free (addr);}static SwfdecBuffer *swfenc_file_inflate (SwfdecBits *bits, guint size){  SwfdecBuffer *decoded, *encoded;  z_stream z;  int ret;  encoded = swfdec_bits_get_buffer (bits, -1);  if (encoded == NULL)    return NULL;  decoded = swfdec_buffer_new_and_alloc (size);  z.zalloc = zalloc;  z.zfree = zfree;  z.opaque = NULL;  z.next_in = encoded->data;  z.avail_in = encoded->length;  z.next_out = decoded->data;  z.avail_out = decoded->length;  ret = inflateInit (&z);  SWFDEC_DEBUG ("inflateInit returned %d", ret);  if (ret >= Z_OK) {    ret = inflate (&z, Z_SYNC_FLUSH);    SWFDEC_DEBUG ("inflate returned %d", ret);  }  inflateEnd (&z);  swfdec_buffer_unref (encoded);  if (ret < Z_OK) {    swfdec_buffer_unref (decoded);    return NULL;  }  return decoded;}static SwfdecBuffer *swf_parse_header1 (SwfeditFile *file, SwfdecBits *bits, GError **error){  guint sig1, sig2, sig3, bytes_total;  sig1 = swfdec_bits_get_u8 (bits);  sig2 = swfdec_bits_get_u8 (bits);  sig3 = swfdec_bits_get_u8 (bits);  if ((sig1 != 'F' && sig1 != 'C') || sig2 != 'W' || sig3 != 'S') {    g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,	"This is not a SWF file");    return NULL;  }  swfedit_token_add (SWFEDIT_TOKEN (file), "version", SWFEDIT_TOKEN_UINT8,       GUINT_TO_POINTER (swfdec_bits_get_u8 (bits)));  bytes_total = swfdec_bits_get_u32 (bits) - 8;  if (sig1 == 'C') {    /* compressed */    SwfdecBuffer *ret = swfenc_file_inflate (bits, bytes_total);    if (ret == NULL)      g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,	  "Unable to uncompress file");    return ret;  } else {    SwfdecBuffer *ret = swfdec_bits_get_buffer (bits, bytes_total);    if (ret == NULL)      g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,	  "File too small");    return ret;  }}static voidswf_parse_header2 (SwfeditFile *file, SwfdecBits *bits){  swfedit_tag_read_token (SWFEDIT_TOKEN (file), bits, "rect", SWFEDIT_TOKEN_RECT, NULL);  swfedit_tag_read_token (SWFEDIT_TOKEN (file), bits, "rate", SWFEDIT_TOKEN_UINT16, NULL);  swfedit_tag_read_token (SWFEDIT_TOKEN (file), bits, "frames", SWFEDIT_TOKEN_UINT16, NULL);}static gbooleanswfedit_file_parse (SwfeditFile *file, SwfdecBits *bits, GError **error){  SwfdecBuffer *next;    next = swf_parse_header1 (file, bits, error);  if (next == NULL)    return FALSE;  swfdec_bits_init (bits, next);  swf_parse_header2 (file, bits);  while (swfdec_bits_left (bits)) {    guint x = swfdec_bits_get_u16 (bits);    G_GNUC_UNUSED guint tag = (x >> 6) & 0x3ff;    guint tag_len = x & 0x3f;    SwfdecBuffer *buffer;    SwfeditTag *item;    if (tag_len == 0x3f)      tag_len = swfdec_bits_get_u32 (bits);    if (tag == 0)      break;    if (tag_len > 0)      buffer = swfdec_bits_get_buffer (bits, tag_len);    else      buffer = swfdec_buffer_new ();    if (buffer == NULL) {      g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,	  "Invalid contents in file");      return FALSE;    }    item = swfedit_tag_new (SWFEDIT_TOKEN (file), tag, buffer);    swfedit_token_add (SWFEDIT_TOKEN (file), 	swfdec_swf_decoder_get_tag_name (tag), 	SWFEDIT_TOKEN_OBJECT, item);  }  swfdec_buffer_unref (next);  return TRUE;}static voidswfedit_file_class_init (SwfeditFileClass *class){  GObjectClass *object_class = G_OBJECT_CLASS (class);  object_class->dispose = swfedit_file_dispose;}static voidswfedit_file_init (SwfeditFile *s){}SwfeditFile *swfedit_file_new (const char *filename, GError **error){  SwfeditFile *file;  SwfdecBuffer *buffer;  SwfdecBits bits;  char *absolute;  if (g_path_is_absolute (filename)) {    absolute = g_strdup (filename);  } else {    char *dir = g_get_current_dir ();    absolute = g_build_filename (dir, filename, NULL);    g_free (dir);  }  buffer = swfdec_buffer_new_from_file (filename, error);  if (buffer == NULL)    return NULL;  swfdec_bits_init (&bits, buffer);  file = g_object_new (SWFEDIT_TYPE_FILE, NULL);  file->filename = absolute;  if (!swfedit_file_parse (file, &bits, error)) {    swfdec_buffer_unref (buffer);    g_object_unref (file);    return NULL;  }  swfdec_buffer_unref (buffer);  return file;}static SwfdecBuffer *swfedit_file_write (SwfeditFile *file){  guint i;  SwfeditToken *token = SWFEDIT_TOKEN (file);  SwfdecBufferQueue *queue;  SwfdecBuffer *buffer;  SwfdecOut *out;  queue = swfdec_buffer_queue_new ();  /* write second part of header */  out = swfdec_out_open ();  swfedit_tag_write_token (token, out, 1);  swfedit_tag_write_token (token, out, 2);  swfedit_tag_write_token (token, out, 3);  swfdec_buffer_queue_push (queue, swfdec_out_close (out));  for (i = 4; i < token->tokens->len; i++) {    SwfeditTokenEntry *entry = &g_array_index (token->tokens, SwfeditTokenEntry, i);    g_assert (entry->type == SWFEDIT_TOKEN_OBJECT);    buffer = swfedit_tag_write (entry->value);    out = swfdec_out_open ();    swfdec_out_put_u16 (out, SWFEDIT_TAG (entry->value)->tag << 6 | 	MIN (buffer->length, 0x3f));    if (buffer->length >= 0x3f) {      swfdec_out_put_u32 (out, buffer->length);    }    swfdec_buffer_queue_push (queue, swfdec_out_close (out));    swfdec_buffer_queue_push (queue, buffer);  }  /* write closing tag */  buffer = swfdec_buffer_new_and_alloc0 (2);  swfdec_buffer_queue_push (queue, buffer);  /* FIXME: implement compression */  out = swfdec_out_open ();  swfdec_out_put_u8 (out, 'F');  swfdec_out_put_u8 (out, 'W');  swfdec_out_put_u8 (out, 'S');  swfedit_tag_write_token (token, out, 0);  swfdec_out_put_u32 (out, swfdec_buffer_queue_get_depth (queue) + 8);  swfdec_out_prepare_bytes (out, swfdec_buffer_queue_get_depth (queue));  while ((buffer = swfdec_buffer_queue_pull_buffer (queue))) {    swfdec_out_put_buffer (out, buffer);    swfdec_buffer_unref (buffer);  }  swfdec_buffer_queue_unref (queue);  return swfdec_out_close (out);}gbooleanswfedit_file_save (SwfeditFile *file, GError **error){  SwfdecBuffer *buffer;  gboolean ret;  g_return_val_if_fail (SWFEDIT_IS_FILE (file), FALSE);  buffer = swfedit_file_write (file);  if (buffer == NULL) {    g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,	"Failed to render file");    return FALSE;  }  ret = g_file_set_contents (file->filename, (char *) buffer->data,      buffer->length, error);  swfdec_buffer_unref (buffer);  return ret;}guintswfedit_file_get_version (SwfeditFile *file){  SwfeditTokenEntry *entry;  g_return_val_if_fail (SWFEDIT_FILE (file), 3);  entry = &g_array_index (SWFEDIT_TOKEN (file)->tokens, SwfeditTokenEntry, 0);  return GPOINTER_TO_UINT (entry->value);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -