pdf-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[pdf-devel] Polymorphism on GNU Pdf


From: Juan Pedro Bolivar Puente
Subject: [pdf-devel] Polymorphism on GNU Pdf
Date: Sat, 04 Oct 2008 20:52:37 +0200
User-agent: Mozilla-Thunderbird 2.0.0.16 (X11/20080724)

There are certainly some polymorphic types on GNU Pdf, the most clear
example are stream filters and stream backends. However, although it is
true that we must handle with C limitations on this point, I think that
we are not doing it on the right way.

I mean, it is cool to have a filter interface that we can handle
homogenously, but it is not so cool if we need a
pdf_stream_install_filter that gets a fixed enum to identify the
filter... what if the library client wants to define a new kind of
filter? He can't... Even worse, stream backends have a defined interface
but we are using a switch () {} on every stream function to dispatch the
correct one instead of using function pointers...


My proposal is to define a clear metodology for polymorphic types that
makes the gnupdf API more consistent and that causes less coupling among
modules. My purposed method is the one used by GNUlib data structures:

*1.* Have a public structure that contains pointers to the
implementation functions. For example:

pdf-stm-filter.h:
  struct pdf_stm_filter_impl
  {
    pdf_stm_f_init_fn_t init;
    pdf_stm_f_apply_fn_t apply;
    pdf_stm_f_dispose_fn_t dispose;
  };

*2.* For each polymorphic type, a global structure which is an instance
of its implemetation structure, that encapsulates the information about
its implementation. For example:

pdf-stm-f-null.h:
  extern struct pdf_stm_f_null_impl;

pdf-stm-f-null.c:
  struct pdf_stm_filter_impl pdf_stm_f_null_impl =
  {
    init: pdf_stm_f_null_init,
    apply: pdf_stm_f_null_apply,
    dispose: pdf_stm_f_null_dispose
  };

*3.* When some needs to create an instance of the polymorphic type, he
gets a pointer to its implementation. For example:

pdf-stm.c
  pdf_status_t
  pdf_stm_add_filter (pdf_stm_t stm,
                      struct pdf_stm_f_impl* filter_impl,
                      ...)
  {
    ...
    pdf_stm_filter_t = pdf_stm_filter_new (filter_impl, ...);
    ...
  }

pdf-stm-filter.h:
  struct pdf_stm_filter
  {
    struct pdf_stm_filter_impl* impl;
    ...
  }

pdf-stm-filter.c:
  pdf_stm_filter_t
  pdf_stm_filter_new (filter_impl)
  {
    pdf_stm_filter_t filter;
    ...
    filter->impl = filter_impl;
    filter->impl->init (...);
    ...
  }

  pdf_status_t
  pdf_stm_filter_apply (pdf_stm_filter_t filter)
  {
   ...
   filter->impl->apply (...);
   ...
  }


This methodology is quite similar to the one we are now using on the
filter's interface, but a little bit improved for decoupling's sake.
What do you think?

Regards,
JP




reply via email to

[Prev in Thread] Current Thread [Next in Thread]