Provide form for user to select export options

This commit is contained in:
Oliver Walters 2020-02-11 21:43:17 +11:00
parent eecc435c02
commit 434d084371
7 changed files with 88 additions and 15 deletions

View File

@ -52,6 +52,10 @@
font-size: 12px;
}
.glyphicon-right {
float: right;
}
.starred-part {
color: #ffbb00;
}

View File

@ -133,7 +133,14 @@ function loadBomTable(table, options) {
title: 'Part',
sortable: true,
formatter: function(value, row, index, field) {
return imageHoverIcon(row.sub_part_detail.image_url) + renderLink(row.sub_part_detail.full_name, row.sub_part_detail.url);
var html = imageHoverIcon(row.sub_part_detail.image_url) + renderLink(row.sub_part_detail.full_name, row.sub_part_detail.url);
// Display an extra icon if this part is an assembly
if (row.sub_part_detail.assembly) {
html += "<a href='" + row.sub_part_detail.url + "bom'><span class='glyphicon-right glyphicon glyphicon-th-list'></span></a>";
}
return html;
}
}
);

View File

@ -6,6 +6,7 @@ Django Forms for interacting with Part objects
from __future__ import unicode_literals
from InvenTree.forms import HelperForm
from InvenTree.helpers import GetExportFormats
from mptt.fields import TreeNodeChoiceField
from django import forms
@ -28,6 +29,26 @@ class PartImageForm(HelperForm):
]
class BomExportForm(forms.Form):
""" Simple form to let user set BOM export options,
before exporting a BOM (bill of materials) file.
"""
file_format = forms.ChoiceField(label=_("File Format"), help_text=_("Select output file format"))
cascading = forms.BooleanField(label=_("Cascading"), required=False, initial=False, help_text=_("Download cascading / multi-level BOM"))
def get_choices(self):
""" BOM export format choices """
return [(x, x.upper()) for x in GetExportFormats()]
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.fields['file_format'].choices = self.get_choices()
class BomValidateForm(HelperForm):
""" Simple confirmation form for BOM validation.
User is presented with a single checkbox input,

View File

@ -65,6 +65,8 @@ class PartBriefSerializer(InvenTreeModelSerializer):
'available_stock',
'image_url',
'active',
'assembly',
'virtual',
]

View File

@ -44,16 +44,7 @@
{% if part.is_bom_valid == False %}
<button class='btn btn-default' id='validate-bom' type='button'><span class='glyphicon glyphicon-check'></span></button>
{% endif %}
<div class='btn-group' role='group'>
<div class='dropdown'>
<button title='Export BOM' class='btn btn-default dropdown-toggle' data-toggle='dropdown' type='button'><span class='glyphicon glyphicon-download-alt'></span></button>
<ul class='dropdown-menu'>
<li><a href='#' class='download-bom' format='csv'>CSV</a></li>
<li><a href='#' class='download-bom' format='xlsx'>XLSX</a></li>
<li><a href='#' class='download-bom' format='json'>JSON</a></li>
</ul>
</div>
</div>
<button title='Export BOM' class='btn btn-default' id='download-bom' type='button'><span class='glyphicon glyphicon-download-alt'></span></button>
{% endif %}
</div>
@ -119,8 +110,14 @@
location.href = "{% url 'part-bom' part.id %}?edit=1";
});
$(".download-bom").click(function () {
location.href = "{% url 'bom-export' part.id %}?format=" + $(this).attr('format');
$("#download-bom").click(function () {
launchModalForm("{% url 'bom-export' part.id %}",
{
success: function(response) {
location.href = response.url;
},
}
);
});
{% endif %}

View File

@ -33,7 +33,8 @@ part_parameter_urls = [
part_detail_urls = [
url(r'^edit/?', views.PartEdit.as_view(), name='part-edit'),
url(r'^delete/?', views.PartDelete.as_view(), name='part-delete'),
url(r'^bom-export/?', views.BomDownload.as_view(), name='bom-export'),
url(r'^bom-export/?', views.BomExport.as_view(), name='bom-export'),
url(r'^bom-download/?', views.BomDownload.as_view(), name='bom-download'),
url(r'^validate-bom/', views.BomValidate.as_view(), name='bom-validate'),
url(r'^duplicate/', views.PartDuplicate.as_view(), name='part-duplicate'),
url(r'^make-variant/', views.MakePartVariant.as_view(), name='make-part-variant'),

View File

@ -1332,7 +1332,7 @@ class BomDownload(AjaxView):
part = get_object_or_404(Part, pk=self.kwargs['pk'])
export_format = request.GET.get('format', 'csv')
export_format = request.GET.get('file_format', 'csv')
if not IsValidBOMFormat(export_format):
export_format = 'csv'
@ -1345,6 +1345,47 @@ class BomDownload(AjaxView):
}
class BomExport(AjaxView):
""" Provide a simple form to allow the user to select BOM download options.
"""
model = Part
form_class = part_forms.BomExportForm
ajax_form_title = _("Export Bill of Materials")
def get(self, request, *args, **kwargs):
return self.renderJsonResponse(request, self.form_class())
def post(self, request, *args, **kwargs):
# Extract POSTed form data
fmt = request.POST.get('file_format', 'csv').lower()
cascade = str2bool(request.POST.get('cascading', False))
try:
part = Part.objects.get(pk=self.kwargs['pk'])
except:
part = None
# Format a URL to redirect to
if part:
url = reverse('bom-download', kwargs={'pk': part.pk})
else:
url = ''
url += '?file_format=' + fmt
url += '&cascade=' + str(cascade)
print("URL:", url)
data = {
'form_valid': part is not None,
'url': url,
}
return self.renderJsonResponse(request, self.form_class(), data=data)
class PartDelete(AjaxDeleteView):
""" View to delete a Part object """