source: products/quintagroup.portlet.cumulus/trunk/quintagroup/portlet/cumulus/cumulusportlet.py @ 3361

Last change on this file since 3361 was 3361, checked in by kroman0, 12 years ago

Implemented max. number of tags to be displayed (Suresh V)

File size: 9.0 KB
RevLine 
[1035]1import urllib
[1003]2
3from zope.interface import implements
[1035]4from zope.component import getMultiAdapter
[1036]5from zope.component import getAdapter
[1003]6
7from plone.portlets.interfaces import IPortletDataProvider
8from plone.app.portlets.portlets import base
[1037]9from plone.memoize.instance import memoize
[1003]10
11from zope import schema
12from zope.formlib import form
13from Products.Five.browser.pagetemplatefile import ViewPageTemplateFile
14
15from quintagroup.portlet.cumulus import CumulusPortletMessageFactory as _
[1036]16from quintagroup.portlet.cumulus.interfaces import ITagsRetriever
[1003]17
18class ICumulusPortlet(IPortletDataProvider):
[1035]19    """ A cumulus tag cloud portlet.
[1003]20    """
[1035]21    # options for generating <embed ... /> tag
22    width = schema.Int(
23        title=_(u'Width of the Flash tag cloud'),
24        description=_(u'Width in pixels (500 or more is recommended).'),
25        required=True,
[1041]26        default=152)
[1003]27
[1035]28    height = schema.Int(
29        title=_(u'Height of the Flash tag cloud'),
30        description=_(u'Height in pixels (ideally around 3/4 of the width).'),
31        required=True,
[1041]32        default=152)
[1003]33
[1035]34    tcolor = schema.TextLine(
35        title=_(u'Color of the tags'),
36        description=_(u'This and next 3 fields should be 6 character hex color values without the # prefix (000000 for black, ffffff for white).'),
37        required=True,
[1037]38        default=u'5391d0')
[1003]39
[1035]40    tcolor2 = schema.TextLine(
41        title=_(u'Optional second color for gradient'),
42        description=_(u'When this color is available, each tag\'s color will be from a gradient between the two. This allows you to create a multi-colored tag cloud.'),
43        required=False,
[1037]44        default=u'333333')
[1003]45
[1035]46    hicolor = schema.TextLine(
47        title=_(u'Optional highlight color'),
48        description=_(u'Color of the tag when mouse is over it.'),
49        required=False,
[1037]50        default=u'578308')
[1035]51
52    bgcolor = schema.TextLine(
53        title=_(u'Background color'),
54        description=_(u'The hex value for the background color you\'d like to use. This options has no effect when \'Use transparent mode\' is selected.'),
55        required=True,
[1037]56        default=u'ffffff')
[1035]57
58    trans = schema.Bool(
59        title=_(u'Use transparent mode'),
60        description=_(u'Switches on Flash\'s wmode-transparent setting.'),
61        required=True,
62        default=False)
63
64    speed = schema.Int(
65        title=_(u'Rotation speed'),
66        description=_(u'Speed of the sphere. Options between 25 and 500 work best.'),
67        required=True,
68        default=100)
69
70    distr = schema.Bool(
71        title=_(u'Distribute tags evenly on sphere'),
72        description=_(u'When enabled, the movie will attempt to distribute the tags evenly over the surface of the sphere.'),
73        required=True,
74        default=True)
75
76    compmode = schema.Bool(
77        title=_(u'Use compatibility mode?'),
78        description=_(u'Enabling this option switches the plugin to a different way of embedding Flash into the page. Use this if your page has markup errors or if you\'re having trouble getting tag cloud to display correctly.'),
79        required=True,
80        default=False)
81
82    # options for generating tag cloud data
83    smallest = schema.Int(
84        title=_(u'Smallest tag size'),
85        description=_(u'The text size of the tag with the smallest count value (units given by unit parameter).'),
86        required=True,
87        default=8)
88
89    largest = schema.Int(
90        title=_(u'Largest tag size'),
91        description=_(u'The text size of the tag with the highest count value (units given by the unit parameter).'),
92        required=True,
93        default=22)
94
95    unit = schema.TextLine(
96        title=_(u'Unit of measure'),
97        description=_(u'Unit of measure as pertains to the smallest and largest values. This can be any CSS length value, e.g. pt, px, em, %.'),
98        required=True,
99        default=u'pt')
100
[3361]101    max_tags = schema.Int(
102        title=_(u'Maximum number of tags to display'),
103        description=_(u'Used when too many tags make the display ugly.'),
104        required=True,
105        default=50)
106
[1003]107class Assignment(base.Assignment):
108    """Portlet assignment.
109
110    This is what is actually managed through the portlets UI and associated
111    with columns.
112    """
113
114    implements(ICumulusPortlet)
115
[1041]116    width    = 152;
117    height   = 152;
[1037]118    tcolor   = u'5391d0'
119    tcolor2  = u'333333'
120    hicolor  = u'578308'
121    bgcolor  = u'ffffff'
[1035]122    speed    = 100
123    trans    = False
124    distr    = True
125    compmode = False
[1003]126
[1035]127    smallest = 8
128    largest  = 22
129    unit     = u'pt'
[3361]130    max_tags = 50
[1003]131
[1035]132    def __init__(self, **kw):
133        for k, v in kw.items():
134            setattr(self, k, v)
[1003]135
136    @property
137    def title(self):
138        """This property is used to give the title of the portlet in the
139        "manage portlets" screen.
140        """
[1037]141        return _("Tag Cloud (cumulus)")
[1003]142
143
144class Renderer(base.Renderer):
145    """Portlet renderer.
146    """
147
148    render = ViewPageTemplateFile('cumulusportlet.pt')
149
[1035]150    def __init__(self, context, request, view, manager, data):
151        base.Renderer.__init__(self, context, request, view, manager, data)
152        portal_state = getMultiAdapter((context, request), name=u'plone_portal_state')
153        self.portal_url = portal_state.portal_url()
[1039]154        portal_properties = getMultiAdapter((context, request), name=u'plone_tools').properties()
155        self.default_charset = portal_properties.site_properties.getProperty('default_charset', 'utf-8')
[1003]156
[1037]157    @property
158    def title(self):
159        return _("Tag Cloud")
160
[1038]161    @property
162    def compmode(self):
163        return self.data.compmode
164
[1003]165    def getScript(self):
[1038]166        params = self.getParams()
[1003]167        return """<script type="text/javascript">
[1041]168                var so = new SWFObject("%(url)s", "tagcloudflash", "%(width)s", "%(height)s", "9", "#%(bgcolor)s");
169                %(trans)s
170                so.addParam("allowScriptAccess", "always");
171                so.addVariable("tcolor", "0x%(tcolor)s");
172                so.addVariable("tcolor2", "0x%(tcolor2)s");
173                so.addVariable("hicolor", "0x%(hicolor)s");
174                so.addVariable("tspeed", "%(tspeed)s");
175                so.addVariable("distr", "%(distr)s");
176                so.addVariable("mode", "%(mode)s");
177                so.addVariable("tagcloud", "%(tagcloud)s");
178                so.write("comulus");
179            </script>""" % params
[1003]180
[1038]181    def getParams(self):
[1039]182        tagcloud = '<tags>%s</tags>' % self.getTagAnchors()
183        tagcloud = tagcloud.encode(self.default_charset)
184        tagcloud = urllib.quote(tagcloud)
[1038]185        params = {
186            'url': self.portal_url + '/++resource++tagcloud.swf',
187            'width': self.data.width,
188            'height': self.data.height,
189            'bgcolor': self.data.bgcolor,
190            'trans': self.data.trans and 'so.addParam("wmode", "transparent");' or '',
191            'tcolor': self.data.tcolor,
192            'tcolor2': self.data.tcolor2 or self.data.tcolor,
193            'hicolor': self.data.hicolor or self.data.tcolor,
194            'tspeed': self.data.speed,
195            'distr': self.data.distr and 'true' or 'false',
196            'mode': 'tags',
[1039]197            'tagcloud': tagcloud,
[1038]198        }
199        flashvars = []
200        for var in ('tcolor', 'tcolor2', 'hicolor', 'tspeed', 'distr', 'mode', 'tagcloud'):
201            flashvars.append('%s=%s' % (var, params[var]))
202        params['flashvars'] = '&'.join(flashvars)
203        return params
204
[1037]205    @memoize
206    def getTagAnchors(self):
207        tags = ''
[1035]208        for tag in self.getTags():
[1037]209            tags += '<a href="%s" title="%s entries" rel="tag" style="font-size: %.1f%s;">%s</a>\n' % \
[1035]210                (tag['url'], tag['number_of_entries'], tag['size'], self.data.unit, tag['name'])
[1037]211        return tags
[1035]212
[1036]213    def getTags(self):
214        tags = ITagsRetriever(self.context).getTags()
215        if tags == []:
216            return []
217
[3361]218        tags.sort(lambda x,y: (x[1]<y[1] and 1) or (x[1]>y[1] and -1) or 0)
219        tags = tags[:self.data.max_tags]
220
[1036]221        number_of_entries = [i[1] for i in tags]
222
[1035]223        min_number = min(number_of_entries)
224        max_number = max(number_of_entries)
225        distance = float(max_number - min_number) or 1
226        step = (self.data.largest - self.data.smallest) / distance
227
228        result = []
[1036]229        for name, number, url in tags:
[1035]230            size = self.data.smallest + step * (number - min_number)
231            result.append({
232                'name': name,
233                'size': size,
234                'number_of_entries': number,
[1036]235                'url': url
[1035]236            })
237        return result
238
[1003]239class AddForm(base.AddForm):
240    """Portlet add form.
241
242    This is registered in configure.zcml. The form_fields variable tells
243    zope.formlib which fields to display. The create() method actually
244    constructs the assignment that is being added.
245    """
246    form_fields = form.Fields(ICumulusPortlet)
247
248    def create(self, data):
249        return Assignment(**data)
250
251class EditForm(base.EditForm):
252    """Portlet edit form.
253
254    This is registered with configure.zcml. The form_fields variable tells
255    zope.formlib which fields to display.
256    """
257    form_fields = form.Fields(ICumulusPortlet)
Note: See TracBrowser for help on using the repository browser.