#! /usr/bin/python # -*- coding: utf-8 -*- # $Id$ """ Copyright (C) 2007, 2008 by Martin Thorsen Ranang This file is part of InTeX. InTeX is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. InTeX 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 General Public License for more details. You should have received a copy of the GNU General Public License along with InTeX. If not, see . """ __author__ = "Martin Thorsen Ranang " __revision__ = "$Rev$" __version__ = "@VERSION@" import logging from entry import Entry from config import FIELD_SEPARATORS class AcronymEntry(Entry): _generated_fields = [ # The values of REFERENCE are how this entry will be # referred to in the text (\co{}). 'reference', 'reference_short', # The values of TYPESET_IN_TEXT determines how the entry # will be typeset in the text. If it was referred to in # its plural form, the entry typeset will also be typeset # with plural inflection. 'typeset_in_text_short', # The values of TYPESET_IN_INDEX defines how the entry will be # typeset in the index. 'typeset_in_index_short', 'sort_as_short', 'typeset_in_text_long', 'typeset_in_index_long', 'sort_as_long', ] # Different constants used for output formatting. _label_width = len('typeset_in_index_short') def __init__(self, index, parent, acronym=None, indent_level=None, full_form=None, meta=None, alias=None, **rest): # Set a couple of defining attributes before calling our base # constructor. for attribute in self._generated_fields: setattr(self, attribute, dict.fromkeys([Entry.INFLECTION_SINGULAR, Entry.INFLECTION_PLURAL])) # Register this entry in the INDEX, set our PARENT and if we # do have a parent, add ourselves to that PARENT's set of # children. Entry.__init__(self, index, parent, meta) # If this entry is an alias for another entry, indicate that # here. self.alias = alias self._setup(acronym, full_form, self._meta, indent_level) # To enable a ConceptEntry to refer to an AcronymEntry: self.typeset_in_index = self.typeset_in_index_long def get_index_entry(self, length, inflection): sort_as = getattr(self, 'sort_as_' + length)[inflection] typeset_in_index = getattr(self, 'typeset_in_index_' + length)[inflection] return '%(sort_as)s@%(typeset_in_index)s' % locals() def generate_index_entries(self, page, typeset_page_number=''): inflection = self.index_inflection if self.META_SORT_AS in self._meta: sort_as_long = self._meta[self.META_SORT_AS] logging.debug('Explicit sort key given "%s" (on page %s) => "%s".', self.sort_as_long[inflection], page, sort_as_long) else: sort_as_long = self.sort_as_long[inflection] sort_as_short = self.sort_as_short[inflection] typeset_in_index_long = self.typeset_in_index_long[inflection] typeset_in_index_short = self.typeset_in_index_short[inflection] parent = self.parent if parent: parent_sort_as_long = parent.sort_as_long[inflection] parent_typeset_in_index_long \ = parent.typeset_in_index_long[inflection] parent_sort_as_short = parent.sort_as_short[inflection] parent_typeset_in_index_short \ = parent.typeset_in_index_short[inflection] yield '\indexentry{' \ '%(parent_sort_as_long)s@%(parent_typeset_in_index_long)s!' \ '%(sort_as_long)s@%(typeset_in_index_long)s' \ '%(typeset_page_number)s}{%(page)s}' % locals() yield '\indexentry{' \ '%(parent_sort_as_short)s@%(parent_typeset_in_index_short)s' \ '|see{%(parent_typeset_in_index_long)s}}' \ '{0}' % locals() yield '\indexentry{' \ '%(parent_sort_as_short)s@%(parent_typeset_in_index_short)s!' \ '%(sort_as_short)s@%(typeset_in_index_short)s' \ '|see{---, %(typeset_in_index_long)s}}' \ '{0}' % locals() else: yield '\indexentry{' \ '%(sort_as_long)s@%(typeset_in_index_long)s' \ '%(typeset_page_number)s}' \ '{%(page)s}' % locals() yield '\indexentry{%(sort_as_short)s@' \ '%(typeset_in_index_short)s|see{%(typeset_in_index_long)s}}' \ '{0}' % locals() def generate_internal_macros(self, inflection): type_name = self.get_entry_type() reference = self.reference[inflection] typeset_in_text_short = self.typeset_in_text_short[inflection] typeset_in_text_full = self.typeset_in_text_long[inflection] yield '\\new%(type_name)s{%(reference)s}{%(typeset_in_text_short)s}' \ '{%(typeset_in_text_full)s}' \ % locals() if self.use_short_reference and self.reference_short[inflection]: reference = self.reference_short[inflection] yield '\\new%(type_name)s{%(reference)s}' \ '{%(typeset_in_text_short)s}' \ '{%(typeset_in_text_full)s}' \ % locals() def get_plain_header(self): return self._line_format \ % ('', self.bold_it('singular'.center(self._column_width)), self.bold_it('plural'.center(self._column_width))) def __str__(self): if self.alias: alias_line = '\n' + self._line_format % ('alias', self.alias, '', ) else: alias_line = '' return '\n'.join([self._line_format \ % (attribute, getattr(self, attribute)['singular'], getattr(self, attribute)['plural'],) for attribute in self._generated_fields]) \ + alias_line def _setup(self, concept, full_form, meta, indent_level): # Trying to figure out the most appropriate features to # represent a concept entry: (current_inflection, complement_inflection) = \ self.get_current_and_complement_inflection(meta) # The INDEX_INFLECTION value defines how the entry should be # sorted in the index. The value is determined by the value # of INDEX.DEFAULT_INFLECTION and the given inflection of the # current entry. self.index_inflection = current_inflection field_variable_map = [ ('reference', 'reference'), ('reference_short', 'reference_short'), ('sort_as_short', 'reference'), ('typeset_in_text_short', 'typeset'), ('typeset_in_index_short', 'typeset'), ('sort_as_long', 'sort_as_long'), ('typeset_in_text_long', 'typeset_long'), ('typeset_in_index_long', 'typeset_long'), ] if indent_level == 0: # Main entry. if not full_form: raise MissingAcronymExpansionError(concept) reference, typeset = self.format_reference_and_typeset(concept) reference_short = [] # Only used for sub-entries. sort_as_long, typeset_long \ = self.format_reference_and_typeset(full_form) if self.META_SORT_AS in self._meta: sort_as_long = [self._meta[self.META_SORT_AS]] for field, variable in field_variable_map: value = ' '.join(locals()[variable]) getattr(self, field)[current_inflection] = value if meta.has_key(Entry.META_COMPLEMENT_INFLECTION): reference, typeset \ = self.format_reference_and_typeset(\ meta[Entry.META_COMPLEMENT_INFLECTION]) else: reference, typeset = \ self.get_complement_inflections(reference, typeset, current_inflection) sort_as_long, typeset_long = \ self.get_complement_inflections(sort_as_long, typeset_long, current_inflection) for field, variable in field_variable_map: value = ' '.join(locals()[variable]) getattr(self, field)[complement_inflection] = value else: # Sub-entry. if full_form is None: full_form = concept for inflection in (current_inflection, complement_inflection): for field, value \ in self.expand_sub_entry(concept, inflection, current_inflection, field_variable_map, full_form).items(): value = self.unescape(value.strip(), FIELD_SEPARATORS + '-') getattr(self, field)[inflection] = value if current_inflection == Entry.INFLECTION_NONE: for (inflection, attribute) in cartesian( (Entry.INFLECTION_SINGULAR, Entry.INFLECTION_PLURAL, ), [field for field, variable in field_variable_map]): getattr(self, attribute)[inflection] = \ getattr(self, attribute)[Entry.INFLECTION_NONE]