diff --git a/bitbake/lib/toaster/toastergui/static/css/default.css b/bitbake/lib/toaster/toastergui/static/css/default.css index 8e60fd8b56..6194c97a0f 100644 --- a/bitbake/lib/toaster/toastergui/static/css/default.css +++ b/bitbake/lib/toaster/toastergui/static/css/default.css @@ -131,6 +131,10 @@ select { width: auto; } /* make tables Chrome-happy (me, not so much) */ #otable { table-layout: fixed; word-wrap: break-word; } +/* styles for the new build button */ +.new-build .btn-primary { padding: 4px 30px; } +#view-all-projects { display: block; } + /* Configuration styles */ .icon-trash { color: #B94A48; font-size: 16px; padding-left: 2px; } .icon-trash:hover { color: #943A38; text-decoration: none; cursor: pointer; } diff --git a/bitbake/lib/toaster/toastergui/static/js/base.js b/bitbake/lib/toaster/toastergui/static/js/base.js new file mode 100644 index 0000000000..864130def9 --- /dev/null +++ b/bitbake/lib/toaster/toastergui/static/js/base.js @@ -0,0 +1,125 @@ + + +function basePageInit (ctx) { + + var newBuildButton = $("#new-build-button"); + /* Hide the button if we're on the project,newproject or importlyaer page */ + if (ctx.currentUrl.search('newproject|project/\\d/$|importlayer/$') > 0){ + newBuildButton.hide(); + return; + } + + + newBuildButton.show().removeAttr("disabled"); + + _checkProjectBuildable() + _setupNewBuildButton(); + + + function _checkProjectBuildable(){ + libtoaster.getProjectInfo(ctx.projectInfoUrl, ctx.projectId, + function(data){ + if (data.machine.name == undefined || data.layers.length == 0) { + /* we can't build anything with out a machine and some layers */ + $("#new-build-button #targets-form").hide(); + $("#new-build-button .alert").show(); + } else { + $("#new-build-button #targets-form").show(); + $("#new-build-button .alert").hide(); + } + }, null); + } + + function _setupNewBuildButton() { + /* Setup New build button */ + var newBuildProjectInput = $("#new-build-button #project-name-input"); + var newBuildTargetBuildBtn = $("#new-build-button #build-button"); + var newBuildTargetInput = $("#new-build-button #build-target-input"); + var newBuildProjectSaveBtn = $("#new-build-button #save-project-button"); + var selectedTarget; + var selectedProject; + + /* If we don't have a current project then present the set project + * form. + */ + if (ctx.projectId == undefined) { + $('#change-project-form').show(); + $('#project .icon-pencil').hide(); + } + + libtoaster.makeTypeahead(newBuildTargetInput, ctx.xhrDataTypeaheadUrl, { type : "targets", project_id: ctx.projectId }, function(item){ + /* successfully selected a target */ + selectedTarget = item; + }); + + + libtoaster.makeTypeahead(newBuildProjectInput, ctx.xhrDataTypeaheadUrl, { type : "projects" }, function(item){ + /* successfully selected a project */ + newBuildProjectSaveBtn.removeAttr("disabled"); + selectedProject = item; + }); + + /* Any typing in the input apart from enter key is going to invalidate + * the value that has been set by selecting a suggestion from the typeahead + */ + newBuildProjectInput.keyup(function(event) { + if (event.keyCode == 13) + return; + newBuildProjectSaveBtn.attr("disabled", "disabled"); + }); + + newBuildTargetInput.keyup(function() { + if ($(this).val().length == 0) + newBuildTargetBuildBtn.attr("disabled", "disabled"); + else + newBuildTargetBuildBtn.removeAttr("disabled"); + }); + + newBuildTargetBuildBtn.click(function() { + if (!newBuildTargetInput.val()) + return; + + /* fire and forget */ + libtoaster.startABuild(ctx.projectBuildUrl, ctx.projectId, selectedTarget.name, null, null); + window.location.replace(ctx.projectPageUrl+ctx.projectId); + }); + + newBuildProjectSaveBtn.click(function() { + ctx.projectId = selectedProject.id + /* Update the typeahead project_id paramater */ + _checkProjectBuildable(); + newBuildTargetInput.data('typeahead').options.xhrParams.project_id = ctx.projectId; + newBuildTargetInput.val(""); + + $("#new-build-button #project a").text(selectedProject.name).attr('href', ctx.projectPageUrl+ctx.projectId); + $("#new-build-button .alert a").attr('href', ctx.projectPageUrl+ctx.projectId); + + + $("#change-project-form").slideUp({ 'complete' : function() { + $("#new-build-button #project").show(); + }}); + }); + + $('#new-build-button #project .icon-pencil').click(function() { + newBuildProjectSaveBtn.attr("disabled", "disabled"); + newBuildProjectInput.val($("#new-build-button #project a").text()); + $(this).parent().hide(); + $("#change-project-form").slideDown(); + }); + + $("#new-build-button #cancel-change-project").click(function() { + $("#change-project-form").hide(function(){ + $('#new-build-button #project').show(); + }); + + newBuildProjectInput.val(""); + newBuildProjectSaveBtn.attr("disabled", "disabled"); + }); + + /* Keep the dropdown open even unless we click outside the dropdown area */ + $(".new-build").click (function(event) { + event.stopPropagation(); + }); + }; + +} diff --git a/bitbake/lib/toaster/toastergui/templates/base.html b/bitbake/lib/toaster/toastergui/templates/base.html index 1b9edfd7b7..87746bfc8c 100644 --- a/bitbake/lib/toaster/toastergui/templates/base.html +++ b/bitbake/lib/toaster/toastergui/templates/base.html @@ -8,6 +8,7 @@ + + +{%if MANAGED %} + +{% endif %} @@ -34,15 +53,55 @@
diff --git a/bitbake/lib/toaster/toastergui/urls.py b/bitbake/lib/toaster/toastergui/urls.py index bae7103091..b60f7614af 100644 --- a/bitbake/lib/toaster/toastergui/urls.py +++ b/bitbake/lib/toaster/toastergui/urls.py @@ -80,10 +80,13 @@ urlpatterns = patterns('toastergui.views', url(r'^machines/$', 'machines', name='machines'), url(r'^projects/$', 'projects', name='all-projects'), + + url(r'^project/$', 'project', name='project'), url(r'^project/(?P