2

I am converting a survey from a Form to a ModelForm in Django 1.6.2.

Can anyone tell me what is the equal of forms.ChoiceField(widget=forms.Select(), and forms.ChoiceField(widget=forms.RadioSelect() using ModelForm?

I have tried widget=models.Select() or widget=models.RadioSelect() but it keeps giving the error

AttributeError: 'module' object has no attribute 'Select'

AttributeError: 'module' object has no attribute 'RadioSelect'

Old Code

forms.py

class SurveyFormB(forms.Form): 

    #Do you own a Smartphone?   
    YES_SMARTPHONE = 'Yes'
    NO_SMARTPHONE = 'No'    

    SMART_PHONE_OWNERSHIP = (
        (YES_SMARTPHONE, 'Yes'),
        (NO_SMARTPHONE, 'No'),
               )    
    smart_phone_ownership = forms.ChoiceField(widget=forms.RadioSelect(), choices=SMART_PHONE_OWNERSHIP, initial= "", label='Do you own a Smartphone?', required = False)


    #If 'Yes' How many hours a day do you access the Internet on it?
    SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY = 'Less than one hour  day'
    SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY = '1 - 2 Hours a day'
    SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY = '2 - 4 hours a day'
    SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY = '4 - 6 hours a day'
    SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY = '6 - 8 hours a day'
    SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY = '8 + hours a day'


    SMART_PHONE_USAGE = (
        ("", "----------"),
        (SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY, 'Less than one hour a day'),
        (SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY, '1 - 2 Hours a day'),
        (SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY, '2 - 4 hours a day'),
        (SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY, '4 - 6 hours a Day'),
        (SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY, '6 - 8 hours a day'),
        (SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY, '8 + hours a day'),
               )

    smart_phone_usage = forms.ChoiceField(widget=forms.Select(), choices=SMART_PHONE_USAGE, initial= "", label='If Yes, How many hours a day do you access the Internet on it?', required = False)

New Code (not working)

modules.py

#Do you own a Smartphone?   
    YES_SMARTPHONE = 'Yes'
    NO_SMARTPHONE = 'No'


    SMART_PHONE_OWNERSHIP = (
        (YES_SMARTPHONE, 'Yes'),
        (NO_SMARTPHONE, 'No'),
               )    
    smart_phone_ownership = models.CharField(null=True, max_length=1, widget=models.RadioSelect(), choices=SMART_PHONE_OWNERSHIP, verbose_name='Do you own a Smartphone?')



#If 'Yes' How many hours a day do you access the Internet on it?
    SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY = 'Less than one hour  day'
    SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY = '1 - 2 Hours a day'
    SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY = '2 - 4 hours a day'
    SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY = '4 - 6 hours a day'
    SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY = '6 - 8 hours a day'
    SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY = '8 + hours a day'


    SMART_PHONE_USAGE = (
        (SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY, 'Less than one hour a day'),
        (SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY, '1 - 2 Hours a day'),
        (SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY, '2 - 4 hours a day'),
        (SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY, '4 - 6 hours a Day'),
        (SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY, '6 - 8 hours a day'),
        (SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY, '8 + hours a day'),
               )

    smart_phone_usage = models.CharField(null=True, blank=True, max_length=1, widget=models.Select(), choices=SMART_PHONE_USAGE, verbose_name='If Yes, How many hours a day do you access the Internet on it?')

I have also tried overwriting it in the forms.py as was necessary for SelectDateWidget but did not get it

Any help is as always much appreciated

Thanks

Deepend
  • 4,057
  • 17
  • 60
  • 101

1 Answers1

9

Django model doesn’t provide RadioSelect or Select widget. You need to add this in Model form.

forms.py

class SmartPhoneForm(forms.ModelForm):
    class Meta:
        model = Phone
        fields = ['smart_phone_ownership', 'smart_phone_usage']
        widgets = {
            'smart_phone_ownership': forms.RadioSelect,
            'smart_phone_usage': forms.Select,
        }

models.py

class SmartPhone(models.Model):
    # Do you own a Smartphone?
    YES_SMARTPHONE = 'Yes'
    NO_SMARTPHONE = 'No'


    SMART_PHONE_OWNERSHIP = (
        (YES_SMARTPHONE, 'Yes'),
        (NO_SMARTPHONE, 'No'),
               )    
    smart_phone_ownership = models.CharField(
        null=True, max_length=1,
        default=None, 
        choices=SMART_PHONE_OWNERSHIP, verbose_name='Do you own a Smartphone?')



#If 'Yes' How many hours a day do you access the Internet on it?
    SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY = 'Less than one hour  day'
    SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY = '1 - 2 Hours a day'
    SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY = '2 - 4 hours a day'
    SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY = '4 - 6 hours a day'
    SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY = '6 - 8 hours a day'
    SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY = '8 + hours a day'


    SMART_PHONE_USAGE = (
        (SMART_PHONE_LESS_THAN_ONE_HOUR_A_DAY, 'Less than one hour a day'),
        (SMART_PHONE_ONE_TO_TWO_HOURS_A_DAY, '1 - 2 Hours a day'),
        (SMART_PHONE_TWO_TO_FOUR_HOURS_A_DAY, '2 - 4 hours a day'),
        (SMART_PHONE_FOUR_TO_SIX_HOURS_A_DAY, '4 - 6 hours a Day'),
        (SMART_PHONE_SIX_TO_EIGHT_HOURS_A_DAY, '6 - 8 hours a day'),
        (SMART_PHONE_EIGHT_PLUS_HOURS_A_DAY, '8 + hours a day'),
               )

    smart_phone_usage = models.CharField(
        null=True, blank=True, max_length=1,
        choices=SMART_PHONE_USAGE,
        # default=None,
        verbose_name='If Yes, How many hours a day do you access the Internet on it?'
        )
moonstruck
  • 2,729
  • 2
  • 26
  • 29
  • Thanks @moonstruck, with your solution I am able to display the choices correctly. However `default=None` does not remove the "-------" from `forms.RadioSelect` but it does from `forms.Select` – Deepend May 13 '15 at 11:24
  • This is strange because using `default=0` on the `forms.RadioSelect` leaves the "-------" in place but it is not selected by default when the user sees it. Why would `default=0` work but `default=None` not? – Deepend May 13 '15 at 11:27
  • It turns out that if you also pass `blank=True` as an argument on `forms.RadioSelect` it will leave the default option "-------" in place even if you use `default=None`. You have to remove `blank=True`. – Deepend May 13 '15 at 11:33
  • @Deepend Yes, you are right. Settings `blank=False` or removing it on RadioSelect will not render the default option "-------". Setting `default=None` on Select will not render the default option "-------" as well if model field is set to `blank=False`. – moonstruck May 13 '15 at 11:50