#------------------------------------------------------------------------------
# Copyright (c) 2005, Enthought, Inc.
# All rights reserved.
# 
# This software is provided without warranty under the terms of the BSD
# license included in enthought/LICENSE.txt and may be redistributed only
# under the conditions described in the aforementioned license.  The license
# is also available online at http://www.enthought.com/licenses/BSD.txt
# Thanks for using Enthought open source!
# 
# Author: Enthought, Inc.
# Description: <Enthought pyface package component>
#------------------------------------------------------------------------------
""" An image resource. """


# Standard library imports.
import os

# Enthought library imports.
from enthought.resource.resource_path import resource_path
from enthought.traits.api import Any, HasPrivateTraits, List, Property, Str

# Local imports.
from resource_manager import resource_manager


class ImageResource(HasPrivateTraits):
    """ An image resource.

    An image resource describes the location of an image and provides a way
    to create a toolkit-specific image on demand.

    """

    #### 'ImageResource' interface ############################################

    # The absolute path to the image.
    absolute_path = Property(Str)

    # The name of the image.
    name = Str

    # A list of directories, classes or instances that will be used to search
    # for the image (see the resource manager for more details).
    search_path = List

    #### Private interface ####################################################

    # The resource manager reference for the image.
    _ref = Any
    
    ###########################################################################
    # 'object' interface.
    ###########################################################################

    def __init__(self, name, search_path=None):
        """ Creates a new image resource. """

        self.name = name

        if search_path is not None:
            self.search_path = search_path

        else:
            self.search_path = [resource_path()]

        return

    ###########################################################################
    # 'ImageResource' interface.
    ###########################################################################

    #### Properties ###########################################################

    def _get_absolute_path(self):
        """ Returns the absolute path to the image. """

        # fixme: This doesn't quite wotk the new notion of image size. We
        # should find out who is actually using this trait, and for what!
        ref = self._get_ref()
        if ref is not None:
            absolute_path = os.path.abspath(self._ref.filename)

        else:
            absolute_path = IMAGE_NOT_FOUND.absolute_path
            
        return absolute_path
    
    #### Methods ##############################################################
    
    def create_image(self, size=None):
        """ Creates a toolkit-specific image for this resource. """

        ref = self._get_ref(size)
        if ref is not None:
            image = ref.load()

        else:
            image = self._get_image_not_found_image()
            
        return image

    def create_bitmap(self, size=None):
        """ Creates a bitmap for this resource. """

        ref = self._get_ref(size)
        if ref is not None:
            image = ref.load()

        else:
            image = self._get_image_not_found_image()
            
        return image.ConvertToBitmap()

    def create_icon(self, size=None):
        """ Creates a toolkit-specific icon for this resource.

        This assumes that the file is in an icon file (i.e., it has the '.ico'
        extension).

        """

        # Major package imports.
        import wx

        ref = self._get_ref(size)
        if ref is not None:
            icon = wx.Icon(self.absolute_path, wx.BITMAP_TYPE_ICO)

        # If we can't find the '.ico' file then we create an icon from the
        # 'image not found' image!
        else:
            image = self._get_image_not_found_image()

            # We have to convert the image to a bitmap first and then create
            # an icon from that.
            bmp   = image.ConvertToBitmap()
            icon  = wx.EmptyIcon()
            icon.CopyFromBitmap(bmp)

        return icon

    ###########################################################################
    # Private interface.
    ###########################################################################

    def _get_ref(self, size=None):
        """ Return the resource manager reference to the image. """

        if self._ref is None:
            self._ref = resource_manager.locate_image(
                self.name, self.search_path, size
            )

        return self._ref

    def _get_image_not_found_image(self):
        """ Returns the 'image not found' image. """
        
        if self is not IMAGE_NOT_FOUND:
            image = IMAGE_NOT_FOUND.create_image()

        # If we can't find the 'image not found' image then the installer must
        # be broken!
        else:
            raise ValueError("Rick's installer is broken")

        return image

    
# The image that is used if the specified image could not be found.
IMAGE_NOT_FOUND = ImageResource('image_not_found')

#### EOF ######################################################################
