class RadioWidget(Widget): template = make_stl_template(""" <stl:block stl:repeat="option options"> <input type="radio" id="${id}-${option/name}" name="${name}" value="${option/name}" checked="${option/selected}" /> <label for="${id}-${option/name}">${option/value}</label> <br stl:if="not oneline" /> </stl:block>""") oneline = False def options(self): datatype = self.datatype value = self.value # Case 1: Enumerate if issubclass(datatype, Enumerate): # Check whether the value is already a list of options # FIXME This is done to avoid a bug when using a select widget in # an auto-form, where the 'datatype.get_namespace' method is # called twice (there may be a better way of handling this). if type(value) is not list: options = datatype.get_namespace(value) else: options = value # Select item if there is only one if len(options) == 1: options[0]['selected'] = True return options # Case 2: Boolean if issubclass(datatype, Boolean): default_labels = {'yes': MSG(u'Yes'), 'no': MSG(u'No')} labels = getattr(self, 'labels', default_labels) yes_selected = value in [True, 1, '1'] return [{ 'name': '1', 'value': labels['yes'], 'selected': yes_selected }, { 'name': '0', 'value': labels['no'], 'selected': not yes_selected }] # Case 3: Error err = 'datatype "%s" should be enumerate or boolean' raise ValueError, err % self.name
class FileWidget(Widget): title = MSG(u'File') download_file_title = MSG(u'Download') template = make_stl_template(""" <input type="file" id="${id}" name="${name}" maxlength="${maxlength}" size="${size}" class="${css}" /> <br/> <div stl:if="preview"> <a href="${preview/link}" target="_blank"> <div stl:if="preview/image"> <img src="${preview/image}"/> </div> ${download_file_title} </a> </div> <label class="language" for="${id}" stl:if="language" >${language}</label> """) width = 128 height = 128 fit = 1 @proto_lazy_property def preview(self): context = get_context() handler = context.resource.get_value(self.field_name, language=self.language_name) if handler is None: return None # Params params = 'name={field_name}' if self.language_name: params += '&language={language_name}' # Download link kw = { 'field_name': self.field_name, 'width': self.width, 'height': self.height, 'language_name': self.language_name } link = ';get_file?' + params.format(**kw) # Image link image = None if isinstance(handler, Image): image = ';get_image?width={width}&height={height}&' + params image = image.format(**kw) # Ok return {'link': link, 'image': image}
class FolderWidget(SelectWidget): has_empty_option = True template = make_stl_template(""" <select id="${id}" name="${name}" onchange="clean_subfolders(${lower}); $('#f${lower}').load('/;get_folders?level${level}='+$(this).val())"> <option value="" stl:if="has_empty_option"></option> <option stl:repeat="option options" value="${option/name}" selected="${option/selected}">${option/value}</option> </select> """) @proto_property def value(self): return quote(self._value)
class ColorPickerWidget(TextWidget): template = make_stl_template(""" <div id="${id}-picker" /> <input type="${type}" id="${id}" name="${name}" value="${value}" maxlength="${maxlength}" size="${size}" class="${css}"/> <label class="language" for="${id}" stl:if="language">${language}</label> <script> $(document).ready(function() { $('#${id}-picker').farbtastic('#${id}'); }); </script>""") scripts = ['/ui/js/farbtastic/farbtastic.js'] styles = ['/ui/js/farbtastic/farbtastic.css']
class DateWidget(Widget): template = make_stl_template(""" <input type="text" name="${name}" value="${value_}" id="${id}" class="dateField" size="${size}" /> <button class="${css} button-selector button-selector-agenda">...</button> <script type="text/javascript"> jQuery( "input#${id}" ).dynDateTime({ ifFormat: "${format}", showsTime: ${show_time_js}, timeFormat: "24", button: ".next()" }); </script>""") styles = ['/ui/ikaaro/js_calendar/calendar-aruni.css'] css = None format = '%Y-%m-%d' size = 10 show_time = False tip = MSG( u'Click on button "..." to choose a date (Format: "yyyy-mm-dd").') @proto_lazy_property def scripts(self): return get_dynDateTime_scripts() @proto_lazy_property def show_time_js(self): # True -> true for Javascript return 'true' if self.show_time else 'false' @proto_lazy_property def value_(self): value = self.value if value is None: return '' # ['2007-08-01\r\n2007-08-02'] if self.datatype.multiple and isinstance(value, list): value = value[0] if type(value) is not str: return value.strftime(self.format) return value @proto_lazy_property def dates(self): return self.value_.splitlines()
class MultilineWidget(Widget): template = make_stl_template(""" <label class="language block" for="${id}" stl:if="language" >${language}</label> <textarea rows="${rows}" cols="${cols}" id="${id}" name="${name}" class="${css}">${value_}</textarea>""") rows = 5 cols = 60 @proto_lazy_property def value_(self): value = self.value if type(value) is str: return value return str(value)
class FileWidget(Widget): title = MSG(u'File') template = make_stl_template(""" <input type="file" id="${id}" name="${name}" maxlength="${maxlength}" size="${size}" class="${css}" /> <label class="language" for="${id}" stl:if="language" >${language}</label> <br/> <img src=";get_image?name=${name}&width=${width}&height=${height}" stl:if="thumb"/>""") width = 128 height = 128 fit = 1 def thumb(self): return isinstance(self.value, Image)
class ImageSelectorWidget(PathSelectorWidget): action = 'add_image' width = 128 height = 128 tip = MSG(u'Click on button "..." to select a file.') template = make_stl_template(""" <input type="text" id="selector-${id}" size="${size}" name="${name}" value="${value}" /> <button id="selector-button-${id}" class="button-selector button-selector-image" name="selector_button_${name}" onclick="return popup(';${action}?target_id=selector-${id}&mode=input', 640, 480);">...</button> <label class="language" for="${id}" stl:if="language" >${language}</label> <br/> <img src="${value}/;thumb?width=${width}&height=${height}" stl:if="value"/>""" )
class Location_Widget(SelectWidget): """This widget is only used in add forms. It is a hack because it is a composite widget and ikaaro does not allow to do this easily. """ title = MSG(u'Location') template = make_stl_template(""" <select id="${id}" name="${name}" class="${css}"> <option stl:repeat="option options" value="${option/name}" selected="${option/selected}">${option/value}</option> </select> <input type="text" id="name" name="name" value="${name_value}" maxlength="80" size="40" style="width: 50%" /> """) def name_value(self): return get_context().query['name']
class RecaptchaWidget(Widget): title = MSG(u"Please enter the words below") public_key = None template = make_stl_template(""" <input type="hidden" name="${name}" value="Check"/> <script type="text/javascript"> var RecaptchaOptions = { theme : 'clean' }; </script> <script type="text/javascript" src="http://api.recaptcha.net/challenge?k=${public_key}"/> <noscript> <iframe src="http://api.recaptcha.net/noscript?k=${public_key}" height="300" width="500" frameborder="0"/><br/> <textarea name="recaptcha_challenge_field" rows="3" cols="40"/> <input type='hidden' name='recaptcha_response_field' value='manual_challenge'/> </noscript> """)
class ChoosePassword_Widget(Widget): """Include a js password strength meter. """ title = MSG(u'Password') template = make_stl_template(""" <input type="password" id="${id}" name="${name}" maxlength="${maxlength}" size="${size}" class="${css}"/> <script type="text/javascript"> jQuery( "#${id}" ).passStrength({ userid: "#${userid}" }); </script>""") @proto_property def scripts(self): context = get_context() handler = context.get_template('/ui/js/password_strength_plugin.js') return ['/ui/js/%s' % basename(handler.key)] # Password meter configuration userid = None
class CheckboxWidget(Widget): template = make_stl_template(""" <stl:block stl:repeat="option options"> <input type="checkbox" id="${id}-${option/name}" name="${name}" value="${option/name}" checked="${option/selected}" /> <label for="${id}-${option/name}">${option/value}</label> <br stl:if="not oneline" /> </stl:block>""") oneline = False label = MSG(u'Yes') def options(self): datatype = self.datatype value = self.value # Case 1: Enumerate if issubclass(datatype, Enumerate): # Check whether the value is already a list of options # FIXME This is done to avoid a bug when using a select widget in # an auto-form, where the 'datatype.get_namespace' method is # called twice (there may be a better way of handling this). if type(value) is not list: return datatype.get_namespace(value) return value # Case 2: Boolean if issubclass(datatype, Boolean): return [{ 'name': '1', 'value': self.label, 'selected': value in [True, 1, '1'] }] # Case 3: Error raise ValueError, 'expected boolean or enumerate datatype'
class FoldersWidget(Widget): template = make_stl_template(""" <script type="text/javascript"> $(function(){ $("#folder0").change(function(){ $("#f1").load('/;get_folders?level0='+$(this).val()); }); }); </script> <div id="f0">${folder0}</div> <div id="f1">${folder1}</div> <div id="f2">${folder2}</div> <div id="f3">${folder3}</div> <div id="f4">${folder4}</div> """) folder = None def folderX(self, x): """ folders -> folder courant folder -> folder complet value -> folder fils sélectionné """ if self.folder is None: return None name = 'folder%s' % x folder_path = self.folder.abspath value = quote(str(folder_path[:x + 1])) if len(folder_path) < x: return None base_folder = folder_path[:x] base_folder = get_context().database.get_resource(base_folder) # On affiche la liste si elle contient des items if list(base_folder.search_resources(format='folder')): return FolderWidget( name, datatype=FoldersEnumerate(base_folder=base_folder), value=value, lower=x + 1, level=x).render() return None @proto_lazy_property def folder0(self): return self.folderX(0) @proto_lazy_property def folder1(self): return self.folderX(1) @proto_lazy_property def folder2(self): return self.folderX(2) @proto_lazy_property def folder3(self): return self.folderX(3) @proto_lazy_property def folder4(self): return self.folderX(4)