Skip to content

Commit

Permalink
Merge branch 'bst_field' into ai_field
Browse files Browse the repository at this point in the history
  • Loading branch information
allholy committed Jan 16, 2025
2 parents 5b3f540 + 8103cb6 commit 1b35d58
Show file tree
Hide file tree
Showing 10 changed files with 194 additions and 48 deletions.
66 changes: 33 additions & 33 deletions .github/workflows/unit-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -20,17 +20,17 @@ jobs:
install: true
driver: docker

- name: Notify workflow starting
uses: voxmedia/github-action-slack-notify-build@v1
continue-on-error: true
if: success()
id: slack
with:
channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
status: STARTING
color: warning
env:
SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}
#- name: Notify workflow starting
# uses: voxmedia/github-action-slack-notify-build@v1
# continue-on-error: true
# if: success()
# id: slack
# with:
# channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
# status: STARTING
# color: warning
# env:
# SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}

- name: Setup
run: bash -c 'mkdir -p ./freesound-data/{packs,uploads,avatars} && echo FS_USER_ID_FROM_ENV=$(id -u) > .env && cp freesound/local_settings.example.py freesound/local_settings.py'
Expand All @@ -57,25 +57,25 @@ jobs:
- name: Run tests
run: docker compose -f docker-compose.test.yml run --rm test_runner python manage.py test --noinput --settings=freesound.test_settings

- name: Notify success
uses: voxmedia/github-action-slack-notify-build@v1
continue-on-error: true
if: success()
with:
message_id: ${{ steps.slack.outputs.message_id }}
channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
status: SUCCESS
color: good
env:
SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}

- name: Notify failure
uses: voxmedia/github-action-slack-notify-build@v1
if: failure()
with:
message_id: ${{ steps.slack.outputs.message_id }}
channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
status: FAILED
color: danger
env:
SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}
#- name: Notify success
# uses: voxmedia/github-action-slack-notify-build@v1
# continue-on-error: true
# if: success()
# with:
# message_id: ${{ steps.slack.outputs.message_id }}
# channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
# status: SUCCESS
# color: good
# env:
# SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}

#- name: Notify failure
# uses: voxmedia/github-action-slack-notify-build@v1
# if: failure()
# with:
# message_id: ${{ steps.slack.outputs.message_id }}
# channel_id: ${{ secrets.SLACK_NOTIFICATIONS_CHANNEL_ID }}
# status: FAILED
# color: danger
# env:
# SLACK_BOT_TOKEN: ${{ secrets.SLACK_NOTIFICATIONS_BOT_TOKEN }}
10 changes: 5 additions & 5 deletions freesound/settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -465,19 +465,19 @@
{'category_code': 'm-sp', 'level': 2, 'name': 'Solo percussion', 'description': 'Music excerpts with solo percussive instruments.'},
{'category_code': 'm-si', 'level': 2, 'name': 'Solo instrument', 'description': 'Music excerpts with only one instrument, excluding percussion.'},
{'category_code': 'm-m', 'level': 2, 'name': 'Multiple instruments', 'description': 'Music excerpts with more than one instrument.'},
{'category_code': 'm-other', 'level': 2, 'name': 'Other (music)', 'description': 'Music that doesn\'t belong to any of the above categories.'},
{'category_code': 'm-other', 'level': 2, 'name': 'Other', 'description': 'Music that doesn\'t belong to any of the above categories.'},
{'category_code': 'is', 'level': 1, 'name': 'Instrument samples', 'description': 'Single notes from musical instruments, various versions of the same note, and scales.'},
{'category_code': 'is-p', 'level': 2, 'name': 'Percussion', 'description': 'Instrument samples that are percussive (idiophones or membraphones).'},
{'category_code': 'is-s', 'level': 2, 'name': 'String', 'description': 'Instrument samples that belong to the string instrument family.'},
{'category_code': 'is-w', 'level': 2, 'name': 'Wind', 'description': 'Instrument samples that belong to the wind instrument family (aerophones).'},
{'category_code': 'is-k', 'level': 2, 'name': 'Piano / Keyboard instruments', 'description': 'Instrument samples of piano or other keyboard instruments, not synthesized.'},
{'category_code': 'is-e', 'level': 2, 'name': 'Synths / Electronic', 'description': 'Instrument samples synthesized or produced by electronic means.'},
{'category_code': 'is-other', 'level': 2, 'name': 'Instrument samples (other)', 'description': 'Instrument samples that don\'t belong to any of the above categories.'},
{'category_code': 'is-other', 'level': 2, 'name': 'Other', 'description': 'Instrument samples that don\'t belong to any of the above categories.'},
{'category_code': 'sp', 'level': 1, 'name': 'Speech', 'description': 'Sounds where human voice is prominent.'},
{'category_code': 'sp-s', 'level': 2, 'name': 'Solo speech', 'description': 'Recording of a single voice speaking, excluding singing.'},
{'category_code': 'sp-c', 'level': 2, 'name': 'Conversation / Crowd', 'description': 'Several people talking, having a conversation or dialogue.'},
{'category_code': 'sp-p', 'level': 2, 'name': 'Processed / Synthetic', 'description': 'Voice(s) from an indirect source (e.g. radio), processed or synthesized.'},
{'category_code': 'sp-other', 'level': 2, 'name': 'Other (speech)', 'description': 'Voice-predominant recordings that don\'t belong to any of the above categories.'},
{'category_code': 'sp-other', 'level': 2, 'name': 'Other', 'description': 'Voice-predominant recordings that don\'t belong to any of the above categories.'},
{'category_code': 'fx', 'level': 1, 'name': 'Sound effects', 'description': 'Isolated sound effects or sound events, each happening one at a time.'},
{'category_code': 'fx-o', 'level': 2, 'name': 'Objects / House appliances', 'description': 'Everyday objects, inside the home or smaller in size.'},
{'category_code': 'fx-v', 'level': 2, 'name': 'Vehicles', 'description': 'Sounds produced from a vehicle.'},
Expand All @@ -487,13 +487,13 @@
{'category_code': 'fx-n', 'level': 2, 'name': 'Natural elements and explosions', 'description': 'Sound events occuring by natural processes.'},
{'category_code': 'fx-ex', 'level': 2, 'name': 'Experimental', 'description': 'Experimental sounds or heavily processed audio recordings.'},
{'category_code': 'fx-el', 'level': 2, 'name': 'Electronic / Design', 'description': 'Sound effects that are computer-made or designed for user interfaces or animations.'},
{'category_code': 'fx-other', 'level': 2, 'name': 'Other (sound effects)', 'description': 'Sound effects that don\'t belong to any of the above categories.'},
{'category_code': 'fx-other', 'level': 2, 'name': 'Other', 'description': 'Sound effects that don\'t belong to any of the above categories.'},
{'category_code': 'ss', 'level': 1, 'name': 'Soundscapes', 'description': 'Ambiances, field-recordings with multiple events and sound environments.'},
{'category_code': 'ss-n', 'level': 2, 'name': 'Nature', 'description': 'Soundscapes from natural habitats.'},
{'category_code': 'ss-i', 'level': 2, 'name': 'Indoors', 'description': 'Soundscapes from closed or indoor spaces.'},
{'category_code': 'ss-u', 'level': 2, 'name': 'Urban', 'description': 'Soundscapes from cityscapes or outdoor places with human intervention.'},
{'category_code': 'ss-s', 'level': 2, 'name': 'Synthetic / Artificial', 'description': 'Soundscapes that are synthesized or computer-made ambiences.'},
{'category_code': 'ss-other', 'level': 2, 'name': 'Other (soundscapes)', 'description': 'Soundscapes that don\'t belong to any of the above categories.'},
{'category_code': 'ss-other', 'level': 2, 'name': 'Other', 'description': 'Soundscapes that don\'t belong to any of the above categories.'},
]

# -------------------------------------------------------------------------------
Expand Down
5 changes: 4 additions & 1 deletion freesound/static/bw-frontend/src/components/modal.js
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,10 @@ const bindConfirmationModalElements = (container) => {

// Logic to bind default modals

const handleDefaultModal = (modalUrl, modalActivationParam, element) => {
const handleDefaultModal = (modalUrl, modalActivationParam, atPage) => {
if ((atPage !== undefined) && modalUrl.indexOf('&page') == -1){
modalUrl += '&page=' + atPage;
}
handleGenericModal(modalUrl, undefined, undefined, true, true, modalActivationParam);
}

Expand Down
4 changes: 3 additions & 1 deletion freesound/static/bw-frontend/src/pages/editDescribeSounds.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,4 +28,6 @@ inputTypeSubmitElements.forEach(button => {
}
});
});
});
});

// Move json for BST category field in description form here
11 changes: 9 additions & 2 deletions sounds/forms.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@

from captcha.fields import ReCaptchaField
from django import forms
from django.core.exceptions import PermissionDenied
from django.core.exceptions import PermissionDenied, ValidationError
from django.db.models import Q
from django.forms import ModelForm, Textarea, TextInput
from django.core.signing import BadSignature, SignatureExpired
Expand Down Expand Up @@ -247,7 +247,8 @@ class SoundEditAndDescribeForm(forms.Form):
widget=forms.TextInput(attrs={'size': 65, 'class': 'inputText'}))
bst_category = forms.ChoiceField(
choices=Sound.BST_CATEGORY_CHOICES,
required=False
help_text="Choose the most appropriate catgeory and subcatgoery (you can only choose one). This category will be displayed as a filtering option in the Freesound side bar.",
required=True,
)
tags = TagField(
widget=forms.Textarea(attrs={'cols': 80, 'rows': 3}),
Expand Down Expand Up @@ -350,6 +351,12 @@ def clean_sources(self):

def clean_pack(self):
return _pack_form_clean_pack_helper(self.cleaned_data)

def clean_bst_category(self):
value = self.cleaned_data['bst_category']
if not '-' in value:
raise ValidationError("Please choose a subcategory.")
return value


class SoundCSVDescriptionForm(SoundEditAndDescribeForm):
Expand Down
4 changes: 2 additions & 2 deletions sounds/migrations/0054_alter_sound_bst_category.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Generated by Django 3.2.23 on 2024-12-23 17:10
# Generated by Django 3.2.23 on 2025-01-16 15:18

from django.db import migrations, models

Expand All @@ -13,6 +13,6 @@ class Migration(migrations.Migration):
migrations.AlterField(
model_name='sound',
name='bst_category',
field=models.CharField(blank=True, choices=[('m', 'Music'), ('m-sp', 'Solo percussion'), ('m-si', 'Solo instrument'), ('m-m', 'Multiple instruments'), ('m-other', 'Other (music)'), ('is', 'Instrument samples'), ('is-p', 'Percussion'), ('is-s', 'String'), ('is-w', 'Wind'), ('is-k', 'Piano / Keyboard instruments'), ('is-e', 'Synths / Electronic'), ('is-other', 'Instrument samples (other)'), ('sp', 'Speech'), ('sp-s', 'Solo speech'), ('sp-c', 'Conversation / Crowd'), ('sp-p', 'Processed / Synthetic'), ('sp-other', 'Other (speech)'), ('fx', 'Sound effects'), ('fx-o', 'Objects / House appliances'), ('fx-v', 'Vehicles'), ('fx-m', 'Other mechanisms, engines, machines'), ('fx-h', 'Human sounds and actions'), ('fx-a', 'Animals'), ('fx-n', 'Natural elements and explosions'), ('fx-ex', 'Experimental'), ('fx-el', 'Electronic / Design'), ('fx-other', 'Other (sound effects)'), ('ss', 'Soundscapes'), ('ss-n', 'Nature'), ('ss-i', 'Indoors'), ('ss-u', 'Urban'), ('ss-s', 'Synthetic / Artificial'), ('ss-other', 'Other (soundscapes)')], default=None, max_length=8, null=True),
field=models.CharField(blank=True, choices=[('m', 'Music'), ('m-sp', 'Solo percussion'), ('m-si', 'Solo instrument'), ('m-m', 'Multiple instruments'), ('m-other', 'Other'), ('is', 'Instrument samples'), ('is-p', 'Percussion'), ('is-s', 'String'), ('is-w', 'Wind'), ('is-k', 'Piano / Keyboard instruments'), ('is-e', 'Synths / Electronic'), ('is-other', 'Other'), ('sp', 'Speech'), ('sp-s', 'Solo speech'), ('sp-c', 'Conversation / Crowd'), ('sp-p', 'Processed / Synthetic'), ('sp-other', 'Other'), ('fx', 'Sound effects'), ('fx-o', 'Objects / House appliances'), ('fx-v', 'Vehicles'), ('fx-m', 'Other mechanisms, engines, machines'), ('fx-h', 'Human sounds and actions'), ('fx-a', 'Animals'), ('fx-n', 'Natural elements and explosions'), ('fx-ex', 'Experimental'), ('fx-el', 'Electronic / Design'), ('fx-other', 'Other'), ('ss', 'Soundscapes'), ('ss-n', 'Nature'), ('ss-i', 'Indoors'), ('ss-u', 'Urban'), ('ss-s', 'Synthetic / Artificial'), ('ss-other', 'Other')], default=None, max_length=8, null=True),
),
]
11 changes: 11 additions & 0 deletions sounds/templatetags/bst_category.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from django import template

register = template.Library()

@register.filter
def get_top_level_bst_category(value):
"""
Extract the top level category from the given value.
The top level category is the part before the '-' in value.
"""
return value.split('-')[0] if '-' in value else value
3 changes: 2 additions & 1 deletion sounds/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -663,7 +663,8 @@ def update_edited_sound(sound, data):
'sounds_per_round': forms_per_round,
'last_latlong': request.user.profile.get_last_latlong(),
'total_sounds_to_describe': len_original_describe_edit_sounds,
'next': request.GET.get('next', '')
'next': request.GET.get('next', ''),
'bst_taxonomy': settings.BROAD_SOUND_TAXONOMY
}

if request.method == "POST" and all_forms_validated_ok:
Expand Down
124 changes: 124 additions & 0 deletions templates/molecules/bst_category_form_field.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
{% load bst_category %}

<div class="bst-category-field">

{{ form.bst_category.errors }}
<div><label>Category</label></div>
{{ form.bst_category.as_hidden }}

<div class="top-buttons v-spacing-top-2">
{% for value, label in form.fields.bst_category.choices %}
{% if "-" not in value %}
<button type="button" class="btn no-hover {% if value == form.bst_category.value|get_top_level_bst_category %}btn-primary{% else %}btn-inverse{% endif %} cell_tooltip_left" data_value="{{ value }}">
{{ label }}
{% for item in bst_taxonomy %}
{% if item.category_code == value %}
<span class="tooltiptext">{{ item.description }}</span>
{% endif %}
{% endfor %}
</button>
{% endif %}
{% endfor %}
</div>

<div class="subcategory-buttons v-spacing-top-2 display-none">
<div><label>Subcategory</label></div>
<div class="row v-spacing-top-2">
{% for value, label in form.fields.bst_category.choices %}
{% if "-" in value %}
<button type="button" class="btn no-hover {% if value == form.bst_category.value %}btn-secondary{% else %}btn-inverse{% endif %} btn-subcategory cell_tooltip_left" top_level="{{ value|get_top_level_bst_category }}" data_value="{{ value }}">
{{ label }}
{% for item in bst_taxonomy %}
{% if item.category_code == value %}
<span class="tooltiptext">{{ item.description }}</span>
{% endif %}
{% endfor %}
</button>
{% endif %}
{% endfor %}
</div>
</div>
<div class="v-spacing-top-4">
<span class="helptext">{{ form.bst_category.help_text|safe }}</span>
</div>
</div>

<script>
document.addEventListener("DOMContentLoaded", function () {

const categoryFieldContainers = document.querySelectorAll(".bst-category-field");
categoryFieldContainers.forEach(container => {
const hiddenField = container.querySelectorAll("input[type=hidden]")[0];
const topButtons = container.querySelectorAll(".top-buttons .btn");
const subcategoryButtons = container.querySelectorAll(".btn-subcategory");
const subcategoryContainer = container.querySelector(".subcategory-buttons");

const updateSubcategoriesList = () => {
if (hiddenField.value === "") {
subcategoryContainer.classList.add("display-none");
return;
} else {
// Display subcategories that match the selected top-level category
// Triggered when a selection is made or updated.
const correspondingTopLevelValue = hiddenField.value.split("-")[0]; // Extract top-level value, if not already.
console.log(correspondingTopLevelValue);
if(correspondingTopLevelValue) {
subcategoryContainer.classList.remove("display-none");

subcategoryButtons.forEach(subBtn => {
const topLevelValue = subBtn.getAttribute("top_level");
const isTrue = topLevelValue === correspondingTopLevelValue;
// console.log("Is condition true?", isTrue);
subBtn.style.display = topLevelValue === correspondingTopLevelValue ? "inline-block" : "none";
});
}
}
}

// Event listener for top-level category buttons
topButtons.forEach(topBtn => {
topBtn.addEventListener("click", function () {
const selectedValue = this.getAttribute("data_value");

// Update hidden input value
hiddenField.value = selectedValue;

// Highlight the selected top-level category button
topButtons.forEach(btn => {
btn.classList.remove("btn-primary")
btn.classList.add("btn-inverse")
btn.setAttribute("aria-selected", "false")
})
this.classList.remove("btn-inverse")
this.classList.add("btn-primary")
this.setAttribute("aria-selected", "true")

updateSubcategoriesList();
});
});

// Event listener for subcategory buttons
subcategoryButtons.forEach(subBtn => {
subBtn.addEventListener("click", function () {
const subcategoryValue = this.getAttribute("data_value");

// Update hidden input value if subcategory is clicked
hiddenField.value = subcategoryValue;

// Highlight the selected subcategory button
subcategoryButtons.forEach(btn => {
btn.classList.remove("btn-secondary")
btn.classList.add("btn-inverse")
btn.setAttribute("aria-selected", "false")
})
this.classList.remove("btn-inverse")
this.classList.add("btn-secondary")
btn.setAttribute("aria-selected", "true");
});
});

updateSubcategoriesList();
});

});
</script>
4 changes: 1 addition & 3 deletions templates/sounds/edit_and_describe.html
Original file line number Diff line number Diff line change
Expand Up @@ -71,9 +71,7 @@ <h5 class="text-light-grey v-spacing-2">Basic information</h5>
{{ form.name }}
</div>
<div>
{{ form.bst_category.errors }}
{{ form.bst_category.label_tag }}
{{ form.bst_category }}
{% include "molecules/bst_category_form_field.html" %}
</div>
<div class="v-spacing-top-3">
{% include "molecules/tags_form_field.html" %}
Expand Down

0 comments on commit 1b35d58

Please sign in to comment.