add Obstacle and Door Features
This commit is contained in:
parent
0ffdde5492
commit
dd215e3f3d
5 changed files with 138 additions and 10 deletions
|
@ -8,7 +8,7 @@ from django.forms.widgets import HiddenInput
|
|||
from shapely.geometry.geo import mapping
|
||||
|
||||
from c3nav.mapdata.models import Package
|
||||
from c3nav.mapdata.models.features import Inside, Room
|
||||
from c3nav.mapdata.models.features import Door, Inside, Obstacle, Room
|
||||
from c3nav.mapdata.permissions import get_unlocked_packages
|
||||
|
||||
|
||||
|
@ -82,3 +82,5 @@ def create_editor_form(feature_model, add_fields=None):
|
|||
def create_editor_forms():
|
||||
create_editor_form(Inside)
|
||||
create_editor_form(Room)
|
||||
create_editor_form(Obstacle, ['height'])
|
||||
create_editor_form(Door)
|
||||
|
|
|
@ -5,8 +5,9 @@ from rest_framework.response import Response
|
|||
from rest_framework.viewsets import ReadOnlyModelViewSet, ViewSet
|
||||
|
||||
from c3nav.mapdata.models import FEATURE_TYPES
|
||||
from c3nav.mapdata.models.features import Inside, Room
|
||||
from c3nav.mapdata.serializers.features import FeatureTypeSerializer, InsideSerializer, RoomSerializer
|
||||
from c3nav.mapdata.models.features import Door, Inside, Obstacle, Room
|
||||
from c3nav.mapdata.serializers.features import (DoorSerializer, FeatureTypeSerializer, InsideSerializer,
|
||||
ObstacleSerializer, RoomSerializer)
|
||||
|
||||
|
||||
class FeatureTypeViewSet(ViewSet):
|
||||
|
@ -58,3 +59,23 @@ class RoomViewSet(ReadOnlyModelViewSet):
|
|||
serializer_class = RoomSerializer
|
||||
lookup_field = 'name'
|
||||
lookup_value_regex = '[^/]+'
|
||||
|
||||
|
||||
class ObstacleViewSet(ReadOnlyModelViewSet):
|
||||
"""
|
||||
List and retrieve Obstcales
|
||||
"""
|
||||
queryset = Obstacle.objects.all()
|
||||
serializer_class = ObstacleSerializer
|
||||
lookup_field = 'name'
|
||||
lookup_value_regex = '[^/]+'
|
||||
|
||||
|
||||
class DoorViewSet(ReadOnlyModelViewSet):
|
||||
"""
|
||||
List and retrieve Doors
|
||||
"""
|
||||
queryset = Door.objects.all()
|
||||
serializer_class = DoorSerializer
|
||||
lookup_field = 'name'
|
||||
lookup_value_regex = '[^/]+'
|
||||
|
|
48
src/c3nav/mapdata/migrations/0002_door_obstacle.py
Normal file
48
src/c3nav/mapdata/migrations/0002_door_obstacle.py
Normal file
|
@ -0,0 +1,48 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Generated by Django 1.10.2 on 2016-10-16 11:13
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import c3nav.mapdata.fields
|
||||
from django.db import migrations, models
|
||||
import django.db.models.deletion
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('mapdata', '0001_initial'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.CreateModel(
|
||||
name='Door',
|
||||
fields=[
|
||||
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
|
||||
('name', models.SlugField(unique=True, verbose_name='Name')),
|
||||
('geometry', c3nav.mapdata.fields.GeometryField()),
|
||||
('level', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='doors', to='mapdata.Level', verbose_name='level')),
|
||||
('package', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='doors', to='mapdata.Package', verbose_name='map package')),
|
||||
],
|
||||
options={
|
||||
'verbose_name_plural': 'Doors',
|
||||
'verbose_name': 'Door',
|
||||
'default_related_name': 'doors',
|
||||
},
|
||||
),
|
||||
migrations.CreateModel(
|
||||
name='Obstacle',
|
||||
fields=[
|
||||
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
|
||||
('name', models.SlugField(unique=True, verbose_name='Name')),
|
||||
('geometry', c3nav.mapdata.fields.GeometryField()),
|
||||
('height', models.DecimalField(decimal_places=2, max_digits=4, null=True, verbose_name='height of the obstacle')),
|
||||
('level', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='obstacles', to='mapdata.Level', verbose_name='level')),
|
||||
('package', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='obstacles', to='mapdata.Package', verbose_name='map package')),
|
||||
],
|
||||
options={
|
||||
'verbose_name_plural': 'Obstacles',
|
||||
'verbose_name': 'Obstacle',
|
||||
'default_related_name': 'obstacles',
|
||||
},
|
||||
),
|
||||
]
|
|
@ -82,3 +82,50 @@ class Room(Feature):
|
|||
verbose_name = _('Room')
|
||||
verbose_name_plural = _('Rooms')
|
||||
default_related_name = 'rooms'
|
||||
|
||||
|
||||
@register_featuretype
|
||||
class Obstacle(Feature):
|
||||
"""
|
||||
An obstacle
|
||||
"""
|
||||
height = models.DecimalField(_('height of the obstacle'), null=True, max_digits=4, decimal_places=2)
|
||||
|
||||
geomtype = 'polygon'
|
||||
color = '#999999'
|
||||
|
||||
class Meta:
|
||||
verbose_name = _('Obstacle')
|
||||
verbose_name_plural = _('Obstacles')
|
||||
default_related_name = 'obstacles'
|
||||
|
||||
@classmethod
|
||||
def fromfile(cls, data, file_path):
|
||||
kwargs = super().fromfile(data, file_path)
|
||||
|
||||
if 'height' in data:
|
||||
if not isinstance(data['height'], (int, float)):
|
||||
raise ValueError('altitude has to be int or float.')
|
||||
kwargs['height'] = data['height']
|
||||
|
||||
return kwargs
|
||||
|
||||
def tofile(self):
|
||||
result = super().tofile()
|
||||
if self.height is not None:
|
||||
result['height'] = float(self.level.name)
|
||||
return result
|
||||
|
||||
|
||||
@register_featuretype
|
||||
class Door(Feature):
|
||||
"""
|
||||
A connection between two rooms
|
||||
"""
|
||||
geomtype = 'polygon'
|
||||
color = '#FF00FF'
|
||||
|
||||
class Meta:
|
||||
verbose_name = _('Door')
|
||||
verbose_name_plural = _('Doors')
|
||||
default_related_name = 'doors'
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
from rest_framework import serializers
|
||||
|
||||
from c3nav.mapdata.models.features import Inside, Room
|
||||
from c3nav.mapdata.models.features import Door, Inside, Obstacle, Room
|
||||
from c3nav.mapdata.serializers.fields import GeometryField
|
||||
|
||||
|
||||
|
@ -25,21 +25,31 @@ class FeatureTypeSerializer(serializers.Serializer):
|
|||
return obj._meta.default_related_name
|
||||
|
||||
|
||||
class InsideSerializer(serializers.ModelSerializer):
|
||||
class FeatureSerializer(serializers.ModelSerializer):
|
||||
level = serializers.SlugRelatedField(slug_field='name', read_only=True)
|
||||
package = serializers.SlugRelatedField(slug_field='name', read_only=True)
|
||||
geometry = GeometryField()
|
||||
|
||||
|
||||
class InsideSerializer(FeatureSerializer):
|
||||
class Meta:
|
||||
model = Inside
|
||||
fields = ('name', 'level', 'package', 'geometry')
|
||||
|
||||
|
||||
class RoomSerializer(serializers.ModelSerializer):
|
||||
level = serializers.SlugRelatedField(slug_field='name', read_only=True)
|
||||
package = serializers.SlugRelatedField(slug_field='name', read_only=True)
|
||||
geometry = GeometryField()
|
||||
|
||||
class RoomSerializer(FeatureSerializer):
|
||||
class Meta:
|
||||
model = Room
|
||||
fields = ('name', 'level', 'package', 'geometry')
|
||||
|
||||
|
||||
class ObstacleSerializer(FeatureSerializer):
|
||||
class Meta:
|
||||
model = Obstacle
|
||||
fields = ('name', 'level', 'package', 'geometry')
|
||||
|
||||
|
||||
class DoorSerializer(FeatureSerializer):
|
||||
class Meta:
|
||||
model = Door
|
||||
fields = ('name', 'level', 'package', 'geometry')
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue