summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--chimere/admin.py35
-rw-r--r--chimere/feeds.py22
-rw-r--r--chimere/forms.py26
-rw-r--r--chimere/migrations/0031_auto__chg_field_picturefile_width__chg_field_picturefile_height.py230
-rw-r--r--chimere/models.py63
-rw-r--r--chimere/static/chimere/js/jquery.chimere.js2
-rw-r--r--chimere/static/chimere/js/menu-sort.js20
-rw-r--r--chimere/templates/chimere/feeds/rss_descr.html11
-rw-r--r--chimere/widgets.py2
9 files changed, 340 insertions, 71 deletions
diff --git a/chimere/admin.py b/chimere/admin.py
index 53362ec..24d28ed 100644
--- a/chimere/admin.py
+++ b/chimere/admin.py
@@ -170,14 +170,6 @@ class AreaAdmin(admin.ModelAdmin):
exclude = ['upper_left_corner', 'lower_right_corner']
inlines = [LayerInline]
-class SubCategoryAdmin(admin.ModelAdmin):
- """
- Specialized the subcategory admin
- """
- list_display = ('name', 'category', 'available')
- list_filter = ('category',)
- form = SubCategoryAdminForm
-
def importing(modeladmin, request, queryset):
for importer in queryset:
importer.state = unicode(tasks.IMPORT_MESSAGES['import_pending'][0])
@@ -226,11 +218,17 @@ class NewsAdmin(admin.ModelAdmin):
"""
form = NewsAdminForm
+class SubcatInline(admin.TabularInline):
+ model = SubCategory
+ extra = 1
+
class CategoryAdmin(admin.ModelAdmin):
"""
Use the TinyMCE widget for categories
"""
form = CategoryAdminForm
+ inlines = [SubcatInline]
+ list_display = ['name', 'order']
class ColorInline(admin.TabularInline):
model = Color
@@ -241,28 +239,11 @@ class ColorThemeAdmin(admin.ModelAdmin):
class IconAdmin(admin.ModelAdmin):
exclude = ['height', 'width']
-class RouteFileAdmin(admin.ModelAdmin):
- list_display = ['name', 'file_type']
-
-class MultimediaExtensionAdmin(admin.ModelAdmin):
- list_display = ('name', 'multimedia_type')
- list_filter = ('multimedia_type',)
-
class MultimediaTypeAdmin(admin.ModelAdmin):
search_fields = ("name",)
list_display = ('name', 'media_type', 'mime_type', 'iframe', 'available')
list_filter = ('media_type', 'available')
-class MultimediaFileAdmin(admin.ModelAdmin):
- search_fields = ("name",)
- list_display = ('name', 'multimedia_type', 'order')
- list_filter = ('multimedia_type',)
-
-class PictureFileAdmin(admin.ModelAdmin):
- search_fields = ("name",)
- list_display = ('name', 'picture', 'miniature', 'order')
- list_filter = ('miniature',)
-
class PropertyModelChoiceInline(admin.TabularInline):
model = PropertyModelChoice
extra = 1
@@ -274,15 +255,11 @@ admin.site.register(Page, PageAdmin)
admin.site.register(News, NewsAdmin)
admin.site.register(Category, CategoryAdmin)
admin.site.register(Icon, IconAdmin)
-admin.site.register(SubCategory, SubCategoryAdmin)
admin.site.register(Marker, MarkerAdmin)
-admin.site.register(RouteFile, RouteFileAdmin)
admin.site.register(Route, RouteAdmin)
admin.site.register(PropertyModel, PropertyModelAdmin)
admin.site.register(Area, AreaAdmin)
admin.site.register(ColorTheme, ColorThemeAdmin)
admin.site.register(MultimediaExtension, MultimediaExtensionAdmin)
admin.site.register(MultimediaType, MultimediaTypeAdmin)
-admin.site.register(MultimediaFile, MultimediaFileAdmin)
-admin.site.register(PictureFile, PictureFileAdmin)
admin.site.register(Layer)
diff --git a/chimere/feeds.py b/chimere/feeds.py
index 057fe5e..c4ee7a5 100644
--- a/chimere/feeds.py
+++ b/chimere/feeds.py
@@ -40,7 +40,7 @@ class BaseFeed(Feed):
cat = 0
if item.categories.all() and item.categories.all()[0]:
cat = item.categories.all()[0].pk
- return reverse('chimere:index') + '?zoom=16&lat=%d&lon=%d&'\
+ return reverse('chimere:index') + '?zoom=16&lat=%f&lon=%f&'\
'current_feature=%d&checked_categories=%d' % (coord.y, coord.x, item.id,
cat)
@@ -57,8 +57,8 @@ class LatestPOIsByCategory(BaseFeed):
'''
Last Points of interests by category in Feeds
'''
- title_template = "rss_title.html"
- description_template = "rss_descr.html"
+ title_template = "chimere/feeds/rss_title.html"
+ description_template = "chimere/feeds/rss_descr.html"
def get_object(self, request, category_id, area_name=''):
return get_object_or_404(Category, id=category_id)
@@ -92,8 +92,8 @@ class LatestPOIsBySubCategory(BaseFeed):
'''
Last Points of interests by SubCategory in Feeds
'''
- title_template = "rss_title.html"
- description_template = "rss_descr.html"
+ title_template = "chimere/feeds/rss_title.html"
+ description_template = "chimere/feeds/rss_descr.html"
def get_object(self, request, category_id, area_name=''):
return get_object_or_404(SubCategory, id=category_id)
@@ -117,8 +117,8 @@ class LatestPOIs(BaseFeed):
'''
Last Points of interests
'''
- title_template = "rss_title.html"
- description_template = "rss_descr.html"
+ title_template = "chimere/feeds/rss_title.html"
+ description_template = "chimere/feeds/rss_descr.html"
def title(self):
return settings.PROJECT_NAME + u" - " + _(u"Last points of interest")
@@ -138,8 +138,8 @@ class LatestPOIsByZone(BaseFeed):
'''
Last Points of interests by zone by coordinates
'''
- title_template = "rss_title.html"
- description_template = "rss_descr.html"
+ title_template = "chimere/feeds/rss_title.html"
+ description_template = "chimere/feeds/rss_descr.html"
upper_left_lat = 0
upper_left_lon = 0
lower_right_lat = 0
@@ -200,8 +200,8 @@ class LatestPOIsByZoneID(BaseFeed):
'''
Last Points of interests by zone by id
'''
- title_template = "rss_title.html"
- description_template = "rss_descr.html"
+ title_template = "chimere/feeds/rss_title.html"
+ description_template = "chimere/feeds/rss_descr.html"
def get_object(self, request, area_id, area_name=''):
return get_object_or_404(Area, id=area_id)
diff --git a/chimere/forms.py b/chimere/forms.py
index 5cf2c63..b584f4f 100644
--- a/chimere/forms.py
+++ b/chimere/forms.py
@@ -130,6 +130,10 @@ class CategoryAdminForm(forms.ModelForm):
Main form for categories
"""
description = forms.CharField(widget=TextareaWidget, required=False)
+ class Media:
+ js = list(settings.JQUERY_JS_URLS) + [
+ '%schimere/js/menu-sort.js' % settings.STATIC_URL,
+ ]
class Meta:
model = Category
@@ -333,25 +337,11 @@ class RouteForm(RouteAdminForm):
file_pk = int(self.cleaned_data['associated_file_id'])
new_route.associated_file = RouteFile.objects.get(pk=file_pk)
new_route.save()
- marker_fields = [f.attname for f in Marker._meta.fields]
- marker_dct = dict([(k, self.cleaned_data[k]) for k in self.cleaned_data
- if k in marker_fields])
- marker_dct['status'] = new_route.status
- categories = []
- if not marker_dct['point']:
- first_point = new_route.route.coords[0]
- marker_dct['point'] = 'POINT(%f %f)' % (first_point[0],
- first_point[1])
- new_marker, created = Marker.objects.get_or_create(route=new_route,
- defaults=marker_dct)
- if not created:
- for att in marker_dct.keys():
- setattr(new_marker, att, marker_dct[att])
+ new_marker = Marker.objects.get(route=new_route)
+ # save description
+ if self.cleaned_data['description']:
+ new_marker.description = self.cleaned_data['description']
new_marker.save()
- new_marker.categories.clear()
- for category in self.cleaned_data['categories']:
- new_marker.categories.add(category)
- new_marker.save()
# save properties
properties = dict([(k.split('_')[-1], self.cleaned_data[k]) \
for k in self.cleaned_data.keys() if k.startswith('property_')])
diff --git a/chimere/migrations/0031_auto__chg_field_picturefile_width__chg_field_picturefile_height.py b/chimere/migrations/0031_auto__chg_field_picturefile_width__chg_field_picturefile_height.py
new file mode 100644
index 0000000..dac7145
--- /dev/null
+++ b/chimere/migrations/0031_auto__chg_field_picturefile_width__chg_field_picturefile_height.py
@@ -0,0 +1,230 @@
+# -*- coding: utf-8 -*-
+import datetime
+from south.db import db
+from south.v2 import SchemaMigration
+from django.db import models
+
+
+class Migration(SchemaMigration):
+
+ def forwards(self, orm):
+
+ # Changing field 'PictureFile.width'
+ db.alter_column('chimere_picturefile', 'width', self.gf('django.db.models.fields.IntegerField')(null=True))
+
+ # Changing field 'PictureFile.height'
+ db.alter_column('chimere_picturefile', 'height', self.gf('django.db.models.fields.IntegerField')(null=True))
+
+ def backwards(self, orm):
+
+ # Changing field 'PictureFile.width'
+ db.alter_column('chimere_picturefile', 'width', self.gf('django.db.models.fields.IntegerField')(default=0))
+
+ # Changing field 'PictureFile.height'
+ db.alter_column('chimere_picturefile', 'height', self.gf('django.db.models.fields.IntegerField')(default=0))
+
+ models = {
+ 'chimere.area': {
+ 'Meta': {'ordering': "('order', 'name')", 'object_name': 'Area'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'default': ('django.db.models.fields.NullBooleanField', [], {'null': 'True', 'blank': 'True'}),
+ 'default_subcategories': ('chimere.widgets.SelectMultipleField', [], {'to': "orm['chimere.SubCategory']", 'symmetrical': 'False', 'blank': 'True'}),
+ 'dynamic_categories': ('django.db.models.fields.NullBooleanField', [], {'null': 'True', 'blank': 'True'}),
+ 'external_css': ('django.db.models.fields.URLField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'layers': ('chimere.widgets.SelectMultipleField', [], {'symmetrical': 'False', 'related_name': "'areas'", 'blank': 'True', 'through': "orm['chimere.AreaLayers']", 'to': "orm['chimere.Layer']"}),
+ 'lower_right_corner': ('django.contrib.gis.db.models.fields.PointField', [], {'default': "'POINT(0 0)'"}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {}),
+ 'restrict_to_extent': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'subcategories': ('chimere.widgets.SelectMultipleField', [], {'symmetrical': 'False', 'related_name': "'areas'", 'blank': 'True', 'db_table': "'chimere_subcategory_areas'", 'to': "orm['chimere.SubCategory']"}),
+ 'upper_left_corner': ('django.contrib.gis.db.models.fields.PointField', [], {'default': "'POINT(0 0)'"}),
+ 'urn': ('django.db.models.fields.SlugField', [], {'unique': 'True', 'max_length': '50', 'blank': 'True'}),
+ 'welcome_message': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'})
+ },
+ 'chimere.arealayers': {
+ 'Meta': {'ordering': "('order',)", 'object_name': 'AreaLayers'},
+ 'area': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.Area']"}),
+ 'default': ('django.db.models.fields.NullBooleanField', [], {'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'layer': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.Layer']"}),
+ 'order': ('django.db.models.fields.IntegerField', [], {})
+ },
+ 'chimere.category': {
+ 'Meta': {'ordering': "['order']", 'object_name': 'Category'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'description': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {})
+ },
+ 'chimere.color': {
+ 'Meta': {'ordering': "['order']", 'object_name': 'Color'},
+ 'code': ('django.db.models.fields.CharField', [], {'max_length': '6'}),
+ 'color_theme': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.ColorTheme']"}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {})
+ },
+ 'chimere.colortheme': {
+ 'Meta': {'object_name': 'ColorTheme'},
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'})
+ },
+ 'chimere.icon': {
+ 'Meta': {'object_name': 'Icon'},
+ 'height': ('django.db.models.fields.IntegerField', [], {}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'image': ('django.db.models.fields.files.ImageField', [], {'max_length': '100'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'width': ('django.db.models.fields.IntegerField', [], {})
+ },
+ 'chimere.importer': {
+ 'Meta': {'object_name': 'Importer'},
+ 'categories': ('chimere.widgets.SelectMultipleField', [], {'to': "orm['chimere.SubCategory']", 'symmetrical': 'False'}),
+ 'default_name': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'filtr': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'importer_type': ('django.db.models.fields.CharField', [], {'max_length': '4'}),
+ 'source': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'srid': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'state': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'zipped': ('django.db.models.fields.BooleanField', [], {'default': 'False'})
+ },
+ 'chimere.layer': {
+ 'Meta': {'object_name': 'Layer'},
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'layer_code': ('django.db.models.fields.TextField', [], {'max_length': '300'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'})
+ },
+ 'chimere.marker': {
+ 'Meta': {'ordering': "('status', 'name')", 'object_name': 'Marker'},
+ 'available_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}),
+ 'categories': ('chimere.widgets.SelectMultipleField', [], {'to': "orm['chimere.SubCategory']", 'symmetrical': 'False'}),
+ 'description': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'}),
+ 'end_date': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'import_key': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'import_source': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'import_version': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'modified_since_import': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'not_for_osm': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'point': ('chimere.widgets.PointField', [], {}),
+ 'ref_item': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'submited_marker'", 'null': 'True', 'to': "orm['chimere.Marker']"}),
+ 'route': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'associated_marker'", 'null': 'True', 'to': "orm['chimere.Route']"}),
+ 'start_date': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}),
+ 'status': ('django.db.models.fields.CharField', [], {'max_length': '1'}),
+ 'submiter_comment': ('django.db.models.fields.TextField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'submiter_email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'null': 'True', 'blank': 'True'}),
+ 'submiter_name': ('django.db.models.fields.CharField', [], {'max_length': '40', 'null': 'True', 'blank': 'True'}),
+ 'submiter_session_key': ('django.db.models.fields.CharField', [], {'max_length': '40', 'null': 'True', 'blank': 'True'})
+ },
+ 'chimere.multimediafile': {
+ 'Meta': {'object_name': 'MultimediaFile'},
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'marker': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'multimedia_files'", 'to': "orm['chimere.Marker']"}),
+ 'miniature': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'multimedia_type': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.MultimediaType']"}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {'default': '1'}),
+ 'url': ('django.db.models.fields.URLField', [], {'max_length': '200'})
+ },
+ 'chimere.multimediatype': {
+ 'Meta': {'object_name': 'MultimediaType'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'iframe': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'media_type': ('django.db.models.fields.CharField', [], {'max_length': '1'}),
+ 'mime_type': ('django.db.models.fields.CharField', [], {'max_length': '50', 'null': 'True', 'blank': 'True'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'})
+ },
+ 'chimere.news': {
+ 'Meta': {'object_name': 'News'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'content': ('django.db.models.fields.TextField', [], {}),
+ 'date': ('django.db.models.fields.DateField', [], {'auto_now_add': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'title': ('django.db.models.fields.CharField', [], {'max_length': '150'})
+ },
+ 'chimere.picturefile': {
+ 'Meta': {'object_name': 'PictureFile'},
+ 'height': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'marker': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'pictures'", 'to': "orm['chimere.Marker']"}),
+ 'miniature': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {'default': '1'}),
+ 'picture': ('django.db.models.fields.files.ImageField', [], {'max_length': '100'}),
+ 'thumbnailfile': ('django.db.models.fields.files.ImageField', [], {'max_length': '100', 'null': 'True', 'blank': 'True'}),
+ 'thumbnailfile_height': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'thumbnailfile_width': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'width': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'})
+ },
+ 'chimere.property': {
+ 'Meta': {'object_name': 'Property'},
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'marker': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.Marker']"}),
+ 'propertymodel': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.PropertyModel']"}),
+ 'value': ('django.db.models.fields.TextField', [], {})
+ },
+ 'chimere.propertymodel': {
+ 'Meta': {'ordering': "('order',)", 'object_name': 'PropertyModel'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'mandatory': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {}),
+ 'subcategories': ('chimere.widgets.SelectMultipleField', [], {'symmetrical': 'False', 'related_name': "'properties'", 'blank': 'True', 'to': "orm['chimere.SubCategory']"}),
+ 'type': ('django.db.models.fields.CharField', [], {'max_length': '1'})
+ },
+ 'chimere.route': {
+ 'Meta': {'ordering': "('status', 'name')", 'object_name': 'Route'},
+ 'associated_file': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.RouteFile']", 'null': 'True', 'blank': 'True'}),
+ 'categories': ('chimere.widgets.SelectMultipleField', [], {'to': "orm['chimere.SubCategory']", 'symmetrical': 'False'}),
+ 'end_date': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}),
+ 'height': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'import_key': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'import_source': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'import_version': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}),
+ 'modified_since_import': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'not_for_osm': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'picture': ('django.db.models.fields.files.ImageField', [], {'max_length': '100', 'null': 'True', 'blank': 'True'}),
+ 'ref_item': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'submited_route'", 'null': 'True', 'to': "orm['chimere.Route']"}),
+ 'route': ('chimere.widgets.RouteField', [], {}),
+ 'start_date': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}),
+ 'status': ('django.db.models.fields.CharField', [], {'max_length': '1'}),
+ 'submiter_comment': ('django.db.models.fields.TextField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}),
+ 'submiter_email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'null': 'True', 'blank': 'True'}),
+ 'submiter_name': ('django.db.models.fields.CharField', [], {'max_length': '40', 'null': 'True', 'blank': 'True'}),
+ 'submiter_session_key': ('django.db.models.fields.CharField', [], {'max_length': '40', 'null': 'True', 'blank': 'True'}),
+ 'width': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'})
+ },
+ 'chimere.routefile': {
+ 'Meta': {'ordering': "('name',)", 'object_name': 'RouteFile'},
+ 'file_type': ('django.db.models.fields.CharField', [], {'max_length': '1'}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'raw_file': ('django.db.models.fields.files.FileField', [], {'max_length': '100'}),
+ 'simplified_file': ('django.db.models.fields.files.FileField', [], {'max_length': '100', 'null': 'True', 'blank': 'True'})
+ },
+ 'chimere.subcategory': {
+ 'Meta': {'ordering': "['category', 'order']", 'object_name': 'SubCategory'},
+ 'available': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
+ 'category': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.Category']"}),
+ 'color_theme': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.ColorTheme']", 'null': 'True', 'blank': 'True'}),
+ 'icon': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['chimere.Icon']"}),
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'item_type': ('django.db.models.fields.CharField', [], {'max_length': '1'}),
+ 'name': ('django.db.models.fields.CharField', [], {'max_length': '150'}),
+ 'order': ('django.db.models.fields.IntegerField', [], {})
+ },
+ 'chimere.tinyurl': {
+ 'Meta': {'object_name': 'TinyUrl'},
+ 'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
+ 'parameters': ('django.db.models.fields.CharField', [], {'max_length': '500'})
+ }
+ }
+
+ complete_apps = ['chimere'] \ No newline at end of file
diff --git a/chimere/models.py b/chimere/models.py
index 30dda7c..20c598e 100644
--- a/chimere/models.py
+++ b/chimere/models.py
@@ -34,7 +34,7 @@ from django.contrib import admin
from django.core.files import File
from django.core.exceptions import ValidationError
from django.core.urlresolvers import reverse
-from django.db.models.signals import post_save, pre_save
+from django.db.models.signals import post_save, pre_save, m2m_changed
from django import forms
from django.template import defaultfilters
from django.utils.translation import ugettext_lazy as _
@@ -208,7 +208,7 @@ class SubCategory(models.Model):
icon = models.ForeignKey(Icon, verbose_name=_(u"Icon"))
color_theme = models.ForeignKey(ColorTheme, verbose_name=_(u"Color theme"),
blank=True, null=True)
- order = models.IntegerField(_(u"Order"))
+ order = models.IntegerField(_(u"Order"), default=1000)
dated = models.BooleanField(_(u"Is dated"), default=False)
TYPE = (('M', _(u'Marker')),
('R', _(u'Route')),
@@ -242,15 +242,19 @@ class SubCategory(models.Model):
subcategories = subcategories.filter(id__in=sub_ids)
selected_cats = [subcat.pk
for subcat in area.default_subcategories.all()]
- for sub_category in subcategories:
+ for sub_category in subcategories.order_by('order'):
if sub_category.category not in sub_categories:
sub_categories[sub_category.category] = []
if sub_category.id in selected_cats:
sub_category.selected = True
sub_category.category.selected = True
sub_categories[sub_category.category].append(sub_category)
- return [(category, sub_cats) for category, sub_cats \
- in sub_categories.items()]
+
+ subcategories = [(cat, subcats) \
+ for cat, subcats in sub_categories.items()]
+ get_cat_order = lambda cat_tuple: cat_tuple[0].order
+ subcategories = sorted(subcategories, key=get_cat_order)
+ return subcategories
@classmethod
def getAvailableTuples(cls, area_name=None):
@@ -673,8 +677,8 @@ class PictureFile(models.Model):
name = models.CharField(_(u"Name"), max_length=150)
picture = models.ImageField(_(u"Image"), upload_to='pictures',
height_field='height', width_field='width')
- height = models.IntegerField(_(u"Height"))
- width = models.IntegerField(_(u"Width"))
+ height = models.IntegerField(_(u"Height"), blank=True, null=True)
+ width = models.IntegerField(_(u"Width"), blank=True, null=True)
miniature = models.BooleanField(_(u"Display inside the description?"),
default=settings.CHIMERE_MINIATURE_BY_DEFAULT)
thumbnailfile = models.ImageField(_(u"Thumbnail"), upload_to='pictures',
@@ -925,7 +929,50 @@ def route_pre_save(sender, **kwargs):
pre_save_route_values[instance.pk] = (instance.name, instance.route,
instance.import_version)
pre_save.connect(route_pre_save, sender=Route)
-post_save.connect(geometry_post_save(pre_save_route_values), sender=Route)
+
+def route_post_save(sender, **kwargs):
+ if not kwargs['instance']:
+ return
+ geometry_post_save(pre_save_route_values)
+ instance = kwargs['instance']
+ marker_fields = [f.attname for f in Marker._meta.fields]
+ route_fields = [f.attname for f in Route._meta.fields]
+ marker_dct = dict([(k, getattr(instance, k)) for k in marker_fields
+ if k in route_fields and k not in ('id', 'ref_item_id')])
+ marker_dct['point'] = "SRID=%d;POINT(%f %f)" % (instance.route.srid,
+ instance.route[0][0], instance.route[0][1])
+ marker, created = Marker.objects.get_or_create(route=instance,
+ defaults=marker_dct)
+ if not created:
+ marker.status = instance.status
+ marker.save()
+ properties = {}
+ for pm in instance.properties():
+ prop = instance.getProperty(pm)
+ if prop:
+ properties[pm.pk] = prop.python_value
+ # fix mis-initialized markers
+ if created:
+ for cat in instance.categories.all():
+ marker.categories.add(cat)
+ marker.saveProperties(properties)
+
+post_save.connect(route_post_save, sender=Route)
+
+def sync_m2m_route(sender, **kwargs):
+ if kwargs['action'] not in ('post_add', 'post_clear', 'post_remove'):
+ return
+ route = kwargs['instance']
+ marker = route.associated_marker
+ if not marker.count:
+ return
+ marker = marker.all()[0]
+ marker.categories.clear()
+ if kwargs['action'] == 'post_clear':
+ return
+ for cat in route.categories.all():
+ marker.categories.add(cat)
+m2m_changed.connect(sync_m2m_route, sender=Route.categories.through)
def getDateCondition():
'''
diff --git a/chimere/static/chimere/js/jquery.chimere.js b/chimere/static/chimere/js/jquery.chimere.js
index 68a621e..c5a88a5 100644
--- a/chimere/static/chimere/js/jquery.chimere.js
+++ b/chimere/static/chimere/js/jquery.chimere.js
@@ -486,6 +486,7 @@ OpenLayers.Layer.MapQuestOSM = OpenLayers.Class(OpenLayers.Layer.XYZ, {
* Add event listener in categories DOM elements
*/
$('#categories #ul_categories > li > input').bind("click", function () {
+ methods.hidePopup();
_toggle_subcategories($(this));
methods.loadGeoObjects();
settings.permalink.updateLink();
@@ -496,6 +497,7 @@ OpenLayers.Layer.MapQuestOSM = OpenLayers.Class(OpenLayers.Layer.XYZ, {
methods.subcategory_detail(
c_name.substr(c_name.lastIndexOf("_")+1));
}
+ methods.hidePopup();
methods.loadGeoObjects();
_toggle_categories($(this));
settings.permalink.updateLink();
diff --git a/chimere/static/chimere/js/menu-sort.js b/chimere/static/chimere/js/menu-sort.js
new file mode 100644
index 0000000..ad1da39
--- /dev/null
+++ b/chimere/static/chimere/js/menu-sort.js
@@ -0,0 +1,20 @@
+jQuery(function($) {
+ $('div.inline-group tbody').sortable({
+ /*containment: 'parent',
+ zindex: 10, */
+ update: function() {
+ $(this).find('tr').each(function(i) {
+ if ($(this).find('input[id$=name]').val()) {
+ $(this).find('input[id$=order]').val(i+1);
+ }
+ });
+ }
+ });
+ $('div.inline-group tbody tr').css('cursor', 'move');
+ $('div.inline-group tbody tr td').each(function (idx){
+ if($(this).is('*.field-order')){
+ $(this).hide();
+ $('div.inline-group thead th:nth-child('+idx+')').hide();
+ }
+ });
+});
diff --git a/chimere/templates/chimere/feeds/rss_descr.html b/chimere/templates/chimere/feeds/rss_descr.html
index 4f75ac6..48f72df 100644
--- a/chimere/templates/chimere/feeds/rss_descr.html
+++ b/chimere/templates/chimere/feeds/rss_descr.html
@@ -1,8 +1,11 @@
{% load i18n %}
{% load sanitize %}
<div id='detail_content'>
-{% if obj.picture %}<img src='{{obj.picture.url}}' alt="{{obj.name}}"/>{%endif%}
-<div>{% for property in obj.getProperties %}
-<p id='{{property.propertymodel.getNamedId}}'>{{ property.value|sanitize:"p b i br hr strong em span:style a:href:target ul li ol h1 h2 h3 h4"|safe }}</p>
-{% endfor %}</div>
+{% for picture in obj.pictures.all %}<a href='{{picture.picture.url}}'><img src='{{picture.thumbnailfile.url}}' alt="{{picture.name}}"/></a>{% endfor %}
+<ul>
+{% if obj.description %}<li class='description'><strong>{% trans "Description:" %}</strong> {{ obj.description|sanitize:"p b i br hr strong em span:style a:href:target ul li ol h1 h2 h3 h4"|safe }}</li>{% endif %}
+{% for property in obj.getProperties %}
+{% if property.value %}<li id='{{property.propertymodel.getNamedId}}'><strong>{{property.propertymodel.name}}{% trans ":"%}</strong> {{ property.value|sanitize:"p b i br hr strong em span:style a:href:target ul li ol h1 h2 h3 h4"|safe }}</li>{% endif %}
+{% endfor %}
+</ul>
</div>
diff --git a/chimere/widgets.py b/chimere/widgets.py
index c0f08c7..158df00 100644
--- a/chimere/widgets.py
+++ b/chimere/widgets.py
@@ -1,6 +1,6 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
-# Copyright (C) 2008-2011 Étienne Loks <etienne.loks_AT_peacefrogsDOTnet>
+# Copyright (C) 2008-2012 Étienne Loks <etienne.loks_AT_peacefrogsDOTnet>
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as