diff --git a/client/javascripts/picky.min.js b/client/javascripts/picky.min.js index c4679c7a..199c8616 100644 --- a/client/javascripts/picky.min.js +++ b/client/javascripts/picky.min.js @@ -1,19 +1,19 @@ Array.prototype.index=function(a){for(var b=0,i=this.length;b0&&h<=5&&q.fadeTo("fast",0.5).fadeTo("fast", -1)},c=function(h){if(h.isEmpty())return"none";if(h.total>i&&h.allocations.length>1)return"support";return"ok"},o=function(h){s.attr("class","dashboard "+h)};this.insert=function(h){f.val(h);f.select()};this.fullResultsCallback=function(h){o(c(h));if(h.isEmpty()){j();u(0);y.show();e()}else if(h.total>i&&h.allocations.length>1){j();e();n.show(h);u(h.total)}else if(h.offset==0){j();u(h.total);d.render(h);w.show();e();f.focus()}else{var v=$(x).position().top;r.remove();d.render(h);$("body").animate({scrollTop:v- -12},500)}};this.liveResultsCallback=function(h){o(c(h));u(h.total)};this.allocationChosen=function(h){h=h.data.query;a.insert(h);a.allocationChosen(h)};this.addinationClicked=function(h){a.addinationClicked(m(),h)};(function(){f.keyup(function(h){if(m()==""){p();a.searchTextCleared()}else{a.searchTextEntered(m(),h);e()}});q.click(function(){m()==""||a.searchButtonClicked(m())});k.click(function(){m()==""||a.searchButtonClicked(m())});g.click(function(){p("");a.clearButtonClicked();f.focus()})})(); -f.focus()};var PickyBackend=function(a){var b=function(i,f,g){var k=g||{};k=$.extend({query:i},g);$.getJSON(a,k,function(q){f&&f(new PickyData(q))})};this.search=function(i,f,g,k){b(i,function(q){f&&f(k,q)},g)}},LiveBackend=function(a){var b=a.live||alert("A live backend path must be provided."),i=new PickyBackend(b);this.search=function(f,g,k,q){q=q||{};latestRequestTimestamp=new Date;q.live=latestRequestTimestamp;k=$.extend({ids:a.liveResults||0,offset:0},k);i.search(f,function(s,x){if(!s.live||s.live==latestRequestTimestamp)g&& -g(x)},k,q)}},FullBackend=function(a){var b=a.full||alert("A full backend path must be provided."),i=new PickyBackend(b);this.search=function(f,g,k,q){q=q||{};latestRequestTimestamp=new Date;q.full=latestRequestTimestamp;k=$.extend({ids:a.fullResults||20,offset:0},k);i.search(f,function(s,x){if(!s.full||s.full==latestRequestTimestamp)g&&g(x)},k,q)}};var PickyController=function(a){var b=new PickyView(this,a),i=a.backends,f=a.beforeInsert||function(){},g=a.before||function(){},k=a.success||function(){},q=a.after||function(){},s=a.liveRendered||false,x=a.liveSearchInterval||180,w,y=function(c){return(c=c&&c.match(/q=([^&]+)/))&&decodeURIComponent(c[1]).replace(/\+/g," ").replace(/#/g,"")||""};this.extractQuery=y;var r=function(){var c=window.History&&window.History.getState();return y(c&&c.url)};this.lastFullQuery=r;var n=function(c,o,h,v){o=g(o, -v)||o;w=[c,o,h,v];var z=o;if(z!=r()){z="?q="+escape(z).replace(/\*/g,"%2A");window.History&&window.History.getState()&&window.History.pushState&&window.History.pushState(null,null,z)}(c=i[c])&&c.search(o,h,v)};this.resend=function(){w&&n.apply(this,w)};var d=function(c,o){c=k(c,o)||c;b.fullResultsCallback(c);q(c,o)},e=function(c,o){clearInterval(p);n("full",c,d,o||{})};a=function(c,o){c=k(c,o)||c;b.liveResultsCallback(c);q(c,o)};var j=s?d:a,p,m=function(){var c=b.text();n("live",c,j,{});clearInterval(p)}; -p=setInterval(m,x);clearInterval(p);var u=function(c,o,h){c=f(c)||c;b.insert(c);h&&e(c,o)};this.insert=u;this.clearButtonClicked=function(){clearInterval(p)};this.searchTextCleared=function(){clearInterval(p)};this.searchTextEntered=function(c,o){if($.inArray(o.keyCode,[0,8,13,32,46,48,49,50,51,52,53,54,55,56,57,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90])>-1)if(o.keyCode==13)e(c);else{clearInterval(p);p=setInterval(m,x)}};this.searchButtonClicked=function(c){e(c)}; -this.allocationChosen=function(c){e(c)};this.addinationClicked=function(c,o){e(c,{offset:o.data.offset})};window.History&&window.History.Adapter.bind(window,"statechange",function(){var c=window.History.getState();(c=y(c.url))&&c!=(w.length>1&&w[1])&&u(c,{},true)})};var Localization={},PickyI18n={},PickyClient=function(a){PickyI18n.locale=$("html").attr("lang").split("-")[0]||"en";a.locale=a.locale||PickyI18n.locale;Localization.qualifiers=a.qualifiers||{};Localization.explanations=a.explanations||{};Localization.choices=a.choices||{};Localization.explanation_delimiters={de:"und",fr:"et",it:"e",en:"and",ch:"und"};var b=a.backends;if(b){b.live||alert("Both a full and live backend must be provided.");b.full||alert("Both a full and live backend must be provided.")}else a.backends= -{live:new LiveBackend(a),full:new FullBackend(a)};b=a.enclosingSelector||"#picky";a.input=$(a.inputSelector||b+" input.query");a.reset=$(a.resetSelector||b+" div.reset");a.button=$(a.buttonSelector||b+" input.search_button");a.counter=$(a.counterSelector||b+" div.status");a.dashboard=$(a.dashboardSelector||b+" .dashboard");a.results=$(a.resultsSelector||b+" div.results");a.noResults=$(a.noResultsSelector||b+" .no_results");a.moreSelector=a.moreSelector||b+" div.results div.addination:last";a.allocations= -$(a.allocationsSelector||b+" .allocations");a.shownAllocations=a.allocations.find(".shown");a.showMoreAllocations=a.allocations.find(".more");a.hiddenAllocations=a.allocations.find(".hidden");a.maxSuggestions=a.maxSuggestions||3;a.results=$(a.resultsSelector||b+" div.results");a.resultsDivider=a.resultsDivider||"";a.noAsterisks=a.noAsterisks||[];a.wrapResults=a.wrapResults||'
    ';var i=a.controller&&new a.controller(a)||new PickyController(a);var f=this.insert=function(g,k,q){i.insert(g, -k||{},q||true)};this.resend=i.resend;this.insertFromURL=function(g){if(g&&g!="")f(g);else(g=i.lastFullQuery())&&f(g)}};var PickyAddination=function(a,b){this.remove=function(){b.find(".addination").remove()};this.render=function(i){var f=i.total,g,k=i.renderedAmount();g=i.offset+k;k=g+k;i=i.total;if(i"+t("results.addination.more")+"");f.bind("click",{offset:g.offset},a.addinationClicked);return f}else return""}};var PickyResultsRenderer=function(a,b){var i=b.locale,f=b.results,g=b.resultsDivider,k=b.wrapResults,q=b.noAsterisks,s=function(n){var d=n[n.length-1];if(d===undefined)return[];n=n.slice(0,n.length-1);if(n==[])n=[n];if(!q.include(d[0]))if(d[1].match(/[^\*~]$/))d[1]+="*";n.push(d);return n};this.asteriskifyLastToken=s;var x=function(n){for(var d=Localization.explanations&&Localization.explanations[i]||{},e=[],j,p=0,m=n.length;p$1"),d].join(" ")};this.strongify=w;var y=function(n,d){var e=Localization.explanation_delimiters[i],j="",p=[],m=[];x(s(d)).each(function(u,c){var o=c[0],h=c[1];if(j==""||o==j){h=h.replace(/[\w,]+:(.+)/,"$1");p.push(h);j=o}else{var v=w(j,p.join(" "));p=[];p.push(h);j=o;m.push(v)}});m.push(w(j,p.join(" ")));m=m.join(" "+e+" ");return m=''+n+" "+m+""}; -this.explain=y;var r=function(n,d){var e='
    ';e+=y(d.type,d.combination);if(n.offset>0)e+='';e+="
    ";return e};this.renderHeader=r;this.render=function(n){n.allocations.each(function(d,e){if(e.entries.length>0){f.append(r(n,e)).append(e.entries.join(g));f.children("li").wrapAll(k)}});f.append(a.render(n))}};function AllocationRenderer(a,b){function i(d){var e={},j={},p=[],m;m=0;for(l=d.length;m=0;m--)d.remove(p[m]);return d}function f(d){return $.map(d,function(e,j){return"%"+(j+1)+"$s"}).join(" ")}function g(d){if(d.length==0)return"";var e=d=i(d);e.sort(function(v,z){return v[0]=0;d--){v=e[d];if(v.length>0)break}v=v[v.length-1];n.include(v[0])||(v[1]+="...");return $.map(e,function(z){return g(z)})}function q(d){var e=[],j,p;for(p in d){j=d[p][0];j=x[j]||j;e[p]=j+":"+d[p][2]}return e.join(" ")}var s=b.locale,x=Localization.qualifiers&&Localization.qualifiers[s]||{},w=Localization.explanations&&Localization.explanations[s]||{},y=b.groups||[],r=Localization.choices&&Localization.choices[s]||{};this.explanation=this.query=this.text="";var n=["street_number", -"zipcode"];this.contract=i;this.rendered=g;this.groupify=k;this.querify=q;this.render=function(d){var e=d.combination,j=d.count;d=q(e);e=k(e).join(" ");e=$('
  1. '+e+'
    '+j+"
  2. ");e.bind("click",{query:d},a);return e}};var PickyAllocationsCloud=function(a,b){var i=b.allocations,f=b.shownAllocations,g=b.showMoreAllocations,k=b.hiddenAllocations,q=b.maxSuggestions,s=function(){i.hide()},x=new AllocationRenderer(function(r){s();a.allocationChosen(r)},b),w=function(r){var n=[];r.each(function(d,e){n.push(x.render(e))});return n},y=function(r){if(r.length==0)return i.hide();f.empty();g.hide();k.empty().hide();if(r.length>q){$.each(r.slice(0,q-1),function(n,d){f.append(d)});$.each(r.slice(q-1),function(n,d){k.append(d)}); -g.show()}else $.each(r,function(n,d){f.append(d)});return i.show()};g.click(function(){g.hide();k.show()});this.hide=s;this.show=function(r){y(w(r.allocations));i.show()}}; +"en",i=a.split(".").concat(b),f=dictionary,e=0,k=i.length;e0&&h<=5&&q.fadeTo("fast",0.5).fadeTo("fast", +1)},c=function(h){if(h.isEmpty())return"none";if(h.total>i&&h.allocations.length>1)return"support";return"ok"},o=function(h){s.attr("class","dashboard "+h)};this.insert=function(h){f.val(h);f.select()};this.fullResultsCallback=function(h){o(c(h));if(h.isEmpty()){j();u(0);y.show();d()}else if(h.total>i&&h.allocations.length>1){j();d();p.show(h);u(h.total)}else if(h.offset==0){j();u(h.total);g.render(v,h);v.show();d();f.focus()}else{var w=$(x).position().top;r.remove();g.render(v,h);$("body").animate({scrollTop:w- +12},500)}};this.liveResultsCallback=function(h){o(c(h));u(h.total)};this.allocationChosen=function(h){h=h.data.query;a.insert(h);a.allocationChosen(h)};this.addinationClicked=function(h){a.addinationClicked(n(),h)};(function(){f.keyup(function(h){if(n()==""){m();a.searchTextCleared()}else{a.searchTextEntered(n(),h);d()}});q.click(function(){n()==""||a.searchButtonClicked(n())});k.click(function(){n()==""||a.searchButtonClicked(n())});e.click(function(){m("");a.clearButtonClicked();f.focus()})})(); +f.focus()};var PickyBackend=function(a){var b=function(i,f,e){var k=e||{};k=$.extend({query:i},e);$.getJSON(a,k,function(q){f&&f(new PickyData(q))})};this.search=function(i,f,e,k){b(i,function(q){f&&f(k,q)},e)}},LiveBackend=function(a){var b=a.live||alert("A live backend path must be provided."),i=new PickyBackend(b);this.search=function(f,e,k,q){q=q||{};latestRequestTimestamp=new Date;q.live=latestRequestTimestamp;k=$.extend({ids:a.liveResults||0,offset:0},k);i.search(f,function(s,x){if(!s.live||s.live==latestRequestTimestamp)e&& +e(x)},k,q)}},FullBackend=function(a){var b=a.full||alert("A full backend path must be provided."),i=new PickyBackend(b);this.search=function(f,e,k,q){q=q||{};latestRequestTimestamp=new Date;q.full=latestRequestTimestamp;k=$.extend({ids:a.fullResults||20,offset:0},k);i.search(f,function(s,x){if(!s.full||s.full==latestRequestTimestamp)e&&e(x)},k,q)}};var PickyController=function(a){var b=new PickyView(this,a),i=a.backends,f=a.beforeInsert||function(){},e=a.before||function(){},k=a.success||function(){},q=a.after||function(){},s=a.liveRendered||false,x=a.liveSearchInterval||180,v,y=function(c){return(c=c&&c.match(/q=([^&]+)/))&&decodeURIComponent(c[1]).replace(/\+/g," ").replace(/#/g,"")||""};this.extractQuery=y;var r=function(){var c=window.History&&window.History.getState();return y(c&&c.url)};this.lastFullQuery=r;var p=function(c,o,h,w){o=e(o, +w)||o;v=[c,o,h,w];var z=o;if(z!=r()){z="?q="+escape(z).replace(/\*/g,"%2A");window.History&&window.History.getState()&&window.History.pushState&&window.History.pushState(null,null,z)}(c=i[c])&&c.search(o,h,w)};this.resend=function(){v&&p.apply(this,v)};var g=function(c,o){c=k(c,o)||c;b.fullResultsCallback(c);q(c,o)},d=function(c,o){clearInterval(m);p("full",c,g,o||{})};a=function(c,o){c=k(c,o)||c;b.liveResultsCallback(c);q(c,o)};var j=s?g:a,m,n=function(){var c=b.text();p("live",c,j,{});clearInterval(m)}; +m=setInterval(n,x);clearInterval(m);var u=function(c,o,h){c=f(c)||c;b.insert(c);h&&d(c,o)};this.insert=u;this.clearButtonClicked=function(){clearInterval(m)};this.searchTextCleared=function(){clearInterval(m)};this.searchTextEntered=function(c,o){if($.inArray(o.keyCode,[0,8,13,32,46,48,49,50,51,52,53,54,55,56,57,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90])>-1)if(o.keyCode==13)d(c);else{clearInterval(m);m=setInterval(n,x)}};this.searchButtonClicked=function(c){d(c)}; +this.allocationChosen=function(c){d(c)};this.addinationClicked=function(c,o){d(c,{offset:o.data.offset})};window.History&&window.History.Adapter.bind(window,"statechange",function(){var c=window.History.getState();(c=y(c.url))&&c!=(v.length>1&&v[1])&&u(c,{},true)})};var PickyI18n={},PickyClient=function(a){PickyI18n.locale=$("html").attr("lang").split("-")[0]||"en";a.locale=a.locale||PickyI18n.locale;a.qualifiers=a.qualifiers||{};a.explanations=a.explanations||{};a.choices=a.choices||{};a.explanation_delimiters={ch:"und",de:"und",en:"and",fr:"et",it:"e"};var b=a.backends;if(b){b.live||alert("Both a full and live backend must be provided.");b.full||alert("Both a full and live backend must be provided.")}else a.backends={live:new LiveBackend(a),full:new FullBackend(a)}; +b=a.enclosingSelector||"#picky";a.input=$(a.inputSelector||b+" input.query");a.reset=$(a.resetSelector||b+" div.reset");a.button=$(a.buttonSelector||b+" input.search_button");a.counter=$(a.counterSelector||b+" div.status");a.dashboard=$(a.dashboardSelector||b+" .dashboard");a.results=$(a.resultsSelector||b+" div.results");a.noResults=$(a.noResultsSelector||b+" .no_results");a.moreSelector=a.moreSelector||b+" div.results div.addination:last";a.allocations=$(a.allocationsSelector||b+" .allocations"); +a.shownAllocations=a.allocations.find(".shown");a.showMoreAllocations=a.allocations.find(".more");a.hiddenAllocations=a.allocations.find(".hidden");a.maxSuggestions=a.maxSuggestions||3;a.results=$(a.resultsSelector||b+" div.results");a.resultsDivider=a.resultsDivider||"";a.nonPartial=a.nonPartial||[];a.wrapResults=a.wrapResults||'
      ';var i=a.controller&&new a.controller(a)||new PickyController(a);var f=this.insert=function(e,k,q){i.insert(e,k||{},q||true)};this.resend=i.resend; +this.insertFromURL=function(e){if(e&&e!="")f(e);else(e=i.lastFullQuery())&&f(e)}};var PickyAddination=function(a,b){this.remove=function(){b.find(".addination").remove()};this.render=function(i){var f=i.total,e,k=i.renderedAmount();e=i.offset+k;k=e+k;i=i.total;if(i"+t("results.addination.more")+"");f.bind("click",{offset:e.offset},a.addinationClicked);return f}else return""}};var PickyResultsRenderer=function(a,b){var i=b.locale,f=b.resultsDivider,e=b.wrapResults,k=b.nonPartial,q=function(r){var p=r[r.length-1];if(p===undefined)return[];r=r.slice(0,r.length-1);if(r==[])r=[r];if(!k.include(p[0]))if(p[1].match(/[^\*~]$/))p[1]+="*";r.push(p);return r};this.asteriskifyLastToken=q;var s=function(r){for(var p=Localization.explanations&&Localization.explanations[i]||{},g=[],d,j=0,m=r.length;j$1"),p].join(" ")};this.strongify=x;var v=function(r,p){var g=Localization.explanation_delimiters[i],d="",j=[],m=[];s(q(p)).each(function(n,u){var c=u[0],o=u[1];if(d==""||c==d){o=o.replace(/[\w,]+:(.+)/,"$1");j.push(o);d=c}else{var h=x(d,j.join(" "));j=[];j.push(o);d=c;m.push(h)}});m.push(x(d,j.join(" ")));m=m.join(" "+g+" ");return m=''+r+" "+m+""}; +this.explain=v;var y=function(r,p){var g='
      ';g+=v(p.type,p.combination);if(r.offset>0)g+='';g+="
      ";return g};this.renderHeader=y;this.render=function(r,p){p.allocations.each(function(g,d){if(d.entries.length>0){r.append(y(p,d)).append(d.entries.join(f));r.children("li").wrapAll(e)}});r.append(a.render(p))}};function AllocationRenderer(a,b){function i(g){var d={},j={},m=[],n;n=0;for(l=g.length;n=0;n--)g.remove(m[n]);return g}function f(g){var d=[];g.each(function(j){d.push("%"+(j+1)+"$s")});return d.join(" ")}function e(g){if(g.length==0)return"";var d=g=i(g);d.sort(function(h,w){return h[0]=0;g--){w=d[g];if(w.length>0)break}w=w[w.length-1];p.include(w[0])||(w[1]+="...");var z=[];d.each(function(A,B){z.push(e(B))});return z}function q(g){return k(g).join(" ")}var s=b.locale,x=b.qualifiers&&b.qualifiers[s]||{},v=b.explanations&&b.explanations[s]||{},y=b.groups||[],r=b.choices&&b.choices[s]||{},p=b.nonPartial||[];this.explanation=this.query=this.text="";this.contract=i;this.makeUpMissingFormat=f;this.rendered=e;this.groupify=k;this.querify=function(g){var d=[],j,m;for(m in g){j= +g[m][0];j=x[j]||j;d[m]=j+":"+g[m][2]}return d.join(" ")};this.suggestify=q;this.render=function(g){return q(g.combination)}};var PickyAllocationsCloud=function(a,b){var i=b.allocations,f=b.shownAllocations,e=b.showMoreAllocations,k=b.hiddenAllocations,q=b.maxSuggestions,s=function(){i.hide()},x=function(p){s();a.allocationChosen(p)},v=new AllocationRenderer(b),y=function(p){var g=[];p.each(function(d,j){var m=v.render(j),n=v.querify(j.combination);m=$('
    1. '+m+'
      '+j.count+"
    2. ");m.bind("click",{query:n},x);g.push(m)});return g},r=function(p){if(p.length==0)return i.hide(); +f.empty();e.hide();k.empty().hide();if(p.length>q){$.each(p.slice(0,q-1),function(g,d){f.append(d)});$.each(p.slice(q-1),function(g,d){k.append(d)});e.show()}else $.each(p,function(g,d){f.append(d)});return i.show()};e.click(function(){e.hide();k.show()});this.hide=s;this.show=function(p){r(y(p.allocations));i.show()}}; diff --git a/client/javascripts/picky.source.js.tar b/client/javascripts/picky.source.js.tar index f3c63c59..708bbe4f 100644 Binary files a/client/javascripts/picky.source.js.tar and b/client/javascripts/picky.source.js.tar differ diff --git a/client/javascripts/source/picky.allocation_renderer.js b/client/javascripts/source/picky.allocation_renderer.js index 53443d7d..cf24a0b5 100644 --- a/client/javascripts/source/picky.allocation_renderer.js +++ b/client/javascripts/source/picky.allocation_renderer.js @@ -3,12 +3,13 @@ function AllocationRenderer(allocationChosenCallback, config) { var locale = config.locale; - var qualifiers = Localization.qualifiers && Localization.qualifiers[locale] || {}; - var explanations = Localization.explanations && Localization.explanations[locale] || {}; - var explanation_delimiter = Localization.explanation_delimiters[locale]; - - var choiceGroups = config.groups || []; - var choices = Localization.choices && Localization.choices[locale] || {}; + // TODO Maybe make dynamic. + // + var qualifiers = config.qualifiers && config.qualifiers[locale] || {}; + var explanations = config.explanations && config.explanations[locale] || {}; + var choiceGroups = config.groups || []; + var choices = config.choices && config.choices[locale] || {}; + var nonPartial = config['nonPartial'] || []; // Those are of interest to the public. // @@ -16,10 +17,6 @@ function AllocationRenderer(allocationChosenCallback, config) { this.query = ''; this.explanation = ''; - // TODO parametrize. - // - var no_ellipses = ['street_number', 'zipcode']; - // Contracts the originals of the zipped. // function contract(zipped) { @@ -46,6 +43,7 @@ function AllocationRenderer(allocationChosenCallback, config) { for (i = remove.length-1; i >= 0; i--) { zipped.remove(remove[i]); } + return zipped; }; this.contract = contract; @@ -53,11 +51,17 @@ function AllocationRenderer(allocationChosenCallback, config) { // Renders the given combinations according to the // choice formatting defined in the config. // - function makeUpMissingFormat(key) { - return $.map(key, function(element, i) { - return '%' + (i+1) + '$s'; - }).join(' '); + function makeUpMissingFormat(keys) { + var result = []; + keys.each(function(i, _) { + result.push('%' + (i+1) + '$s'); + }); + return result.join(' '); }; + this.makeUpMissingFormat = makeUpMissingFormat; + + // + // function rendered(zipped) { // Return an empty string if there are no combinations. // @@ -72,25 +76,25 @@ function AllocationRenderer(allocationChosenCallback, config) { // Now that it's sorted, get the right string. // - var key = []; + var keys = []; for (var i = 0, l = key_ary.length; i < l; i++) { - key.push(key_ary[i][0]); + keys.push(key_ary[i][0]); }; // Get the right formatting or make up a simple one. // // var result = choices[key] || (choices[key] = makeUpMissingFormat(key)); - var single = key.length == 1; + var single = keys.length == 1; // Get the formatting to be replaced. // - var formatting = choices[key] || (choices[key] = makeUpMissingFormat(key)); + var formatting = choices[keys.join(',')] || (choices[keys] = makeUpMissingFormat(keys)); // If someone uses the simple format, change into complex format. // - if ($.type(formatting) === "string") { - choices[key] = { format: formatting }; - formatting = choices[key]; + if (typeof formatting === "string") { + choices[keys] = { format: formatting }; + formatting = choices[keys]; }; var j = 1; @@ -98,7 +102,7 @@ function AllocationRenderer(allocationChosenCallback, config) { // Replace each word into the formatting string. // - $.each(zipped, function(i, original_token) { + zipped.each(function(i, original_token) { var category = original_token[0]; var word = original_token[2]; @@ -110,15 +114,10 @@ function AllocationRenderer(allocationChosenCallback, config) { return result; } - var regexp = new RegExp("%" + j + "\\$s", "g"); + var regexp = new RegExp("%" + (i+1) + "\\$s", "g"); result = result.replace(regexp, word); - - j += 1; - - return j; }); - return result; }; this.rendered = rendered; @@ -180,13 +179,16 @@ function AllocationRenderer(allocationChosenCallback, config) { // And append ellipses. // - if (!no_ellipses.include(last_part[0])) { last_part[1] += '...'; } // TODO * + if (!nonPartial.include(last_part[0])) { last_part[1] += '...'; } // Render each group and return the resulting rendered array. // - return $.map(groups, function(group) { - return rendered(group); + var result = []; + groups.each(function(i, group) { + result.push(rendered(group)); }); + + return result; }; this.groupify = groupify; @@ -195,11 +197,13 @@ function AllocationRenderer(allocationChosenCallback, config) { function querify(zipped) { var query_parts = []; var qualifier; + for (var i in zipped) { qualifier = zipped[i][0]; qualifier = qualifiers[qualifier] || qualifier; // Use the returned qualifier if none is given. query_parts[i] = qualifier + ':' + zipped[i][2]; }; + return query_parts.join(' '); }; this.querify = querify; @@ -209,37 +213,10 @@ function AllocationRenderer(allocationChosenCallback, config) { function suggestify(zipped) { return groupify(zipped).join(' '); }; - - - // Generates the text and the link. - // - var generate = function() { - this.query = querify(combination); - this.text = suggestify(combination); - - return self; - }; - - // TODO Extract. - // - var listItem = function(text, count) { - return $('
    3. ' + text + '
      ' + count + '
    4. '); - }; + this.suggestify = suggestify; var render = function(allocation) { - - var combination = allocation.combination; - var type = allocation.type; - var count = allocation.count; - - var query = querify(combination); - - var item = listItem(suggestify(combination), count); - - // TODO Move this outwards? - // - item.bind('click', { query: query }, allocationChosenCallback); - return item; + return suggestify(allocation.combination); }; this.render = render; diff --git a/client/javascripts/source/picky.allocations_cloud.js b/client/javascripts/source/picky.allocations_cloud.js index 01acb14d..adbba66c 100644 --- a/client/javascripts/source/picky.allocations_cloud.js +++ b/client/javascripts/source/picky.allocations_cloud.js @@ -26,24 +26,34 @@ var PickyAllocationsCloud = function(view, config) { // // - var allocationChosen = function(event) { + var allocationChosenCallback = function(event) { hide(); view.allocationChosen(event); }; - var allocationRenderer = new AllocationRenderer(allocationChosen, config); + var allocationRenderer = new AllocationRenderer(config); + // How an allocation renders as a list item. + // + var listItem = function(text, count) { + return $('
    5. ' + text + '
      ' + count + '
    6. '); + }; + + // + // var createAllocationList = function(allocations) { var shown = []; + allocations.each(function(i, allocation) { - shown.push(allocationRenderer.render(allocation)); + var rendered = allocationRenderer.render(allocation); + var query = allocationRenderer.querify(allocation.combination); - // TODO Combine. - // allocationRenderer.generate(); - // var listItem = renderListItem(allocationRenderer); - - // shown.push(listItem); + rendered = listItem(rendered, allocation.count); + rendered.bind('click', { query: query }, allocationChosenCallback); + + shown.push(rendered); }); + return shown; }; diff --git a/client/javascripts/source/picky.client.js b/client/javascripts/source/picky.client.js index f0642d2a..2a28146c 100644 --- a/client/javascripts/source/picky.client.js +++ b/client/javascripts/source/picky.client.js @@ -1,4 +1,3 @@ -var Localization = {}; var PickyI18n = { }; // The client handles parameters and @@ -24,25 +23,31 @@ var PickyClient = function(config) { // // This needs to correspond to the parsing in the search engine. // - Localization.qualifiers = config.qualifiers || {}; + config['qualifiers'] = config.qualifiers || {}; // This is used to explain the preceding word in the suggestion text. // // e.g. with locale it: // ['title', 'ulysses', 'Ulysses'] => 'Ulysses (titolo)' // - Localization.explanations = config.explanations || {}; + config['explanations'] = config.explanations || {}; // This is used to expain more complex combinations of categories // in the choices. // // e.g. with locale en:{'author,title': '%1$s, who wrote %2$s'} // - Localization.choices = config.choices || {}; + config['choices'] = config.choices || {}; // Delimiters for connecting explanations. // - Localization.explanation_delimiters = { de:'und', fr:'et', it:'e', en:'and', ch:'und' }; + config['explanation_delimiters'] = { + ch:'und', + de:'und', + en:'and', + fr:'et', + it:'e' + }; // Either you pass it a backends hash with full and live, // or you pass it full and live (urls), which will then @@ -85,9 +90,9 @@ var PickyClient = function(config) { // Results rendering. // config['results'] = $(config['resultsSelector'] || (enclosingSelector + ' div.results')); - config['resultsDivider'] = config['resultsDivider'] || ''; - config['noAsterisks'] = config['noAsterisks'] || []; // e.g. ['category1', 'category2'] - config['wrapResults'] = config['wrapResults'] || '
        '; + config['resultsDivider'] = config['resultsDivider'] || ''; + config['nonPartial'] = config['nonPartial'] || []; // e.g. ['category1', 'category2'] + config['wrapResults'] = config['wrapResults'] || '
          '; // The central Picky controller. // diff --git a/client/javascripts/source/picky.results_renderer.js b/client/javascripts/source/picky.results_renderer.js index 429fbf71..8e682320 100644 --- a/client/javascripts/source/picky.results_renderer.js +++ b/client/javascripts/source/picky.results_renderer.js @@ -2,10 +2,9 @@ var PickyResultsRenderer = function(addination, config) { var locale = config.locale; - var results = config['results']; var resultsDivider = config['resultsDivider']; var allocationWrapper = config['wrapResults']; - var noAsterisks = config['noAsterisks']; + var nonPartial = config['nonPartial']; // Adds asterisks to the last token. // @@ -14,7 +13,7 @@ var PickyResultsRenderer = function(addination, config) { if (last_part === undefined) { return []; } var parts = combinations.slice(0, combinations.length-1); if (parts == []) { parts = [parts]; } - if (!noAsterisks.include(last_part[0])) { + if (!nonPartial.include(last_part[0])) { // Replace with * unless there is already one or a tilde. // if (last_part[1].match(/[^\*~]$/)) { last_part[1] += '*'; } @@ -120,7 +119,7 @@ var PickyResultsRenderer = function(addination, config) { // Render results with the data. // - this.render = function(data) { + this.render = function(results, data) { data.allocations.each(function(i, allocation) { // Only render if there is something to render. // TODO Move into methods. diff --git a/client/javascripts/source/picky.view.js b/client/javascripts/source/picky.view.js index 59f3f353..fa7f6c7a 100644 --- a/client/javascripts/source/picky.view.js +++ b/client/javascripts/source/picky.view.js @@ -117,7 +117,7 @@ var PickyView = function(picky_controller, config) { var showResults = function(data) { clean(); updateResultCounter(data.total); - resultsRenderer.render(data); + resultsRenderer.render(results, data); results.show(); showClearButton(); }; @@ -130,7 +130,7 @@ var PickyView = function(picky_controller, config) { var position = $(moreSelector).position().top; addination.remove(); // TODO Where should this be? - resultsRenderer.render(data); + resultsRenderer.render(results, data); scrollTo(position); }; diff --git a/client/javascripts/spec/picky.allocation_renderer.spec.js b/client/javascripts/spec/picky.allocation_renderer.spec.js index b4a5c6dd..fc090573 100644 --- a/client/javascripts/spec/picky.allocation_renderer.spec.js +++ b/client/javascripts/spec/picky.allocation_renderer.spec.js @@ -4,12 +4,157 @@ describe( function() { renderer = new AllocationRenderer(function() { // - }, {}); + }, { + locale: 'en', + choices: { + en:{ + 'title': { + format: "%1$s", + filter: function(text) { return text.toUpperCase(); }, + ignoreSingle: false + }, + 'author': { + format: "%1$s", + filter: function(text) { return text.toLowerCase(); }, + ignoreSingle: true + }, + 'author,title': '%1$s, who wrote %2$s', + } + } + }); }, function() { - describe("makeUpMissingFormat", function() { - it("should be tasty", function() { - expect(renderer.makeUpMissingFormat('someKey')).toMatch(''); + describe("makeUpMissingFormat", null, function() { + it("is correct", function() { + return renderer.makeUpMissingFormat(['title']) == '%1$s'; + }); + it("is correct", function() { + return renderer.makeUpMissingFormat(['author', 'title']) == '%1$s %2$s'; + }); + it("is correct", function() { + return renderer.makeUpMissingFormat(['author', 'title', 'something']) == '%1$s %2$s %3$s'; + }); + }); + describe("contract", null, function() { + it("is correct", function() { + return renderer.contract([ + ['cat1', 'Orig1', 'parsed1'] + ]).compare([ + ['cat1', 'Orig1', 'parsed1'] + ]); + }); + it("is correct", function() { + return renderer.contract([ + ['cat2', 'Orig1', 'parsed1'], + ['cat1', 'Orig2', 'parsed2'], + ['cat2', 'Orig3', 'parsed3'] + ]).compare([ + ['cat2', 'Orig1 Orig3', 'parsed1'], // TODO Is just parsed1 ok? Do we care? + ['cat1', 'Orig2', 'parsed2'] + ]); + }); + it("is correct", function() { + return renderer.contract([ + ['cat2', 'Orig1', 'parsed1'], + ['cat1', 'Orig2', 'parsed2'], + ['cat2', 'Orig3', 'parsed3'], + ['cat1', 'Orig4', 'parsed4'] + ]).compare([ + ['cat2', 'Orig1 Orig3', 'parsed1'], // TODO Is just parsed1 ok? Do we care? + ['cat1', 'Orig2 Orig4', 'parsed2'] + ]); + }); + }); + describe("rendered", null, function() { + it("is correct", function() { + return renderer.rendered([['cat1', 'Orig1 Orig2', 'parsed1']]) == "parsed1 (cat1)"; + }); + it("is correct", function() { + return renderer.rendered([ + ['cat1', 'Orig1 Orig2', 'parsed1'], + ['cat2', 'Orig3 Orig4', 'parsed2'] + ]) == "parsed1 parsed2"; + }); + it("is correct", function() { + return renderer.rendered([ + ['title', 'Title1', 'title1'] + ]) == "TITLE1 (title)"; + }); + it("is correct", function() { + return renderer.rendered([ + ['title', 'Title1 Title2', 'title1 title2'] + ]) == "TITLE1 TITLE2 (title)"; + }); + it("is correct", function() { + return renderer.rendered([ + ['author', 'Author1', 'author1'] + ]) == "author1"; + }); + it("is correct", function() { + return renderer.rendered([ + ['author', 'Author1 Author2', 'author1 author2'] + ]) == "author1 author2"; + }); + it("is correct", function() { + return renderer.rendered([ + ['title', 'Title1', 'title1'], + ['author', 'Author1', 'author1'] + ]) == "author1, who wrote title1"; + }); + it("is correct", function() { + return renderer.rendered([ + ['title', 'Title1', 'title:title1'], + ['author', 'Author1', 'author:author1'] + ]) == "author1, who wrote title1"; + }); + }); + + describe("querify", null, function() { + it("is correct", function() { + return renderer.querify([ + ['cat1', 'Orig1', 'parsed1'] + ]) == "cat1:parsed1"; + }); + it("is correct", function() { + return renderer.querify([ + ['cat1', 'Orig1', 'parsed1'], + ['cat2', 'Orig2', 'parsed2'] + ]) == "cat1:parsed1 cat2:parsed2"; + }); + it("is correct", function() { + return renderer.querify([ + ['cat1', 'Orig1 Orig3', 'parsed1 parsed3'], + ['cat2', 'Orig2', 'parsed2'] + ]) == "cat1:parsed1 cat2:parsed2"; + }); + }); + describe("suggestify", null, function() { + it("is correct", function() { + return renderer.suggestify([ + ['cat1', 'Orig1', 'parsed1'] + ]) == "parsed1 (cat1)"; + }); + it("is correct", function() { + return renderer.suggestify([ + ['cat1', 'Orig1', 'parsed1'], + ['cat2', 'Orig2', 'parsed2'] + ]) == "parsed1 parsed2"; + }); + it("is correct", function() { + return renderer.suggestify([ + ['cat1', 'Orig1 Orig3', 'parsed1 parsed3'], + ['cat2', 'Orig2', 'parsed2'] + ]) == "parsed1 parsed3 parsed2"; + }); + it("is correct", function() { + return renderer.suggestify([ + ['title', 'Orig1', 'parsed1'] + ]) == "PARSED1 (title)"; + }); + it("is correct", function() { + return renderer.suggestify([ + ['author', 'Orig1', 'parsed1'] + ]) == "parsed1"; }); }); } diff --git a/client/javascripts/spec/picky.allocations.spec.js b/client/javascripts/spec/picky.allocations.spec.js index 78efd77c..eae2bdcb 100644 --- a/client/javascripts/spec/picky.allocations.spec.js +++ b/client/javascripts/spec/picky.allocations.spec.js @@ -19,7 +19,7 @@ describe( null, function() { it("is correct", function() { - var result = true; + var result = true; allocations.each(function() { result = false; // It should not be called. }); diff --git a/client/javascripts/spec/picky.results_renderer.spec.js b/client/javascripts/spec/picky.results_renderer.spec.js index 912189d7..f739b663 100644 --- a/client/javascripts/spec/picky.results_renderer.spec.js +++ b/client/javascripts/spec/picky.results_renderer.spec.js @@ -2,11 +2,24 @@ var renderer; describe( "Mocked controller", function() { + var append = ""; + var results = { + append: function(string) { + append += string; + }, + str: function() { + return append; + } + } + renderer = new PickyResultsRenderer( - null, + { + render: function() { return "the_addination"; } + }, { locale: 'en', - noAsterisks: ['noAsterisksCategory'] + nonPartial: ['nonPartialCategory'], + results: results } ); }, @@ -16,6 +29,9 @@ describe( it("is correct", function() { return renderer.asteriskifyLastToken([]).compare([]); }); + it("is correct", function() { + return renderer.asteriskifyLastToken([['nonPartialCategory', 'Orig1', 'parsed1']]).compare([['nonPartialCategory', 'Orig1', 'parsed1']]); + }); it("is correct", function() { return renderer.asteriskifyLastToken([['cat1', 'Orig1', 'parsed1']]).compare([['cat1', 'Orig1*', 'parsed1']]); }); @@ -98,7 +114,7 @@ describe( it("is correct", function() { return renderer.renderHeader( { offset: 0 }, - { + { type: 'type1', combination: [['cat1', 'Orig1', 'parsed1']] } @@ -107,7 +123,7 @@ describe( it("is correct", function() { return renderer.renderHeader( { offset: 0 }, - { + { type: 'type1', combination: [ ['cat1', 'Orig1', 'parsed1'], @@ -118,5 +134,18 @@ describe( }); } ); + // describe("render", null, + // function() { + // it("is correct", function() { + // return renderer.render( + // new PickyData({ + // offset: 0, + // allocations: [ + // ['type1', 3.14, 123, [['cat1', 'Orig1', 'parsed1']]] + // ] + // })) == '
          type1 done by Orig1*
          '; + // }); + // } + // ); } ); diff --git a/client/javascripts/specs b/client/javascripts/specs index 48cca8a1..a8309399 100755 --- a/client/javascripts/specs +++ b/client/javascripts/specs @@ -1,8 +1,3 @@ -# js -f spec_helper.js \ -# -f source/picky.translations.js \ -# -f source/picky.allocation_renderer.js \ -# spec/picky.allocation_renderer.spec.js - js -f spec_helper.js \ -f source/picky.extensions.js \ spec/picky.extensions.spec.js @@ -24,9 +19,15 @@ js -f spec_helper.js \ js -f spec_helper.js \ -f source/picky.extensions.js \ + -f source/picky.data.js \ -f source/picky.results_renderer.js \ spec/picky.results_renderer.spec.js +js -f spec_helper.js \ + -f source/picky.extensions.js \ + -f source/picky.allocation_renderer.js \ + spec/picky.allocation_renderer.spec.js + # js -f spec_helper.js \ # -f source/picky.client.js \ # spec/picky.client.spec.js diff --git a/client/test_project/javascripts/picky.allocation_renderer.js b/client/test_project/javascripts/picky.allocation_renderer.js index 53443d7d..cf24a0b5 100644 --- a/client/test_project/javascripts/picky.allocation_renderer.js +++ b/client/test_project/javascripts/picky.allocation_renderer.js @@ -3,12 +3,13 @@ function AllocationRenderer(allocationChosenCallback, config) { var locale = config.locale; - var qualifiers = Localization.qualifiers && Localization.qualifiers[locale] || {}; - var explanations = Localization.explanations && Localization.explanations[locale] || {}; - var explanation_delimiter = Localization.explanation_delimiters[locale]; - - var choiceGroups = config.groups || []; - var choices = Localization.choices && Localization.choices[locale] || {}; + // TODO Maybe make dynamic. + // + var qualifiers = config.qualifiers && config.qualifiers[locale] || {}; + var explanations = config.explanations && config.explanations[locale] || {}; + var choiceGroups = config.groups || []; + var choices = config.choices && config.choices[locale] || {}; + var nonPartial = config['nonPartial'] || []; // Those are of interest to the public. // @@ -16,10 +17,6 @@ function AllocationRenderer(allocationChosenCallback, config) { this.query = ''; this.explanation = ''; - // TODO parametrize. - // - var no_ellipses = ['street_number', 'zipcode']; - // Contracts the originals of the zipped. // function contract(zipped) { @@ -46,6 +43,7 @@ function AllocationRenderer(allocationChosenCallback, config) { for (i = remove.length-1; i >= 0; i--) { zipped.remove(remove[i]); } + return zipped; }; this.contract = contract; @@ -53,11 +51,17 @@ function AllocationRenderer(allocationChosenCallback, config) { // Renders the given combinations according to the // choice formatting defined in the config. // - function makeUpMissingFormat(key) { - return $.map(key, function(element, i) { - return '%' + (i+1) + '$s'; - }).join(' '); + function makeUpMissingFormat(keys) { + var result = []; + keys.each(function(i, _) { + result.push('%' + (i+1) + '$s'); + }); + return result.join(' '); }; + this.makeUpMissingFormat = makeUpMissingFormat; + + // + // function rendered(zipped) { // Return an empty string if there are no combinations. // @@ -72,25 +76,25 @@ function AllocationRenderer(allocationChosenCallback, config) { // Now that it's sorted, get the right string. // - var key = []; + var keys = []; for (var i = 0, l = key_ary.length; i < l; i++) { - key.push(key_ary[i][0]); + keys.push(key_ary[i][0]); }; // Get the right formatting or make up a simple one. // // var result = choices[key] || (choices[key] = makeUpMissingFormat(key)); - var single = key.length == 1; + var single = keys.length == 1; // Get the formatting to be replaced. // - var formatting = choices[key] || (choices[key] = makeUpMissingFormat(key)); + var formatting = choices[keys.join(',')] || (choices[keys] = makeUpMissingFormat(keys)); // If someone uses the simple format, change into complex format. // - if ($.type(formatting) === "string") { - choices[key] = { format: formatting }; - formatting = choices[key]; + if (typeof formatting === "string") { + choices[keys] = { format: formatting }; + formatting = choices[keys]; }; var j = 1; @@ -98,7 +102,7 @@ function AllocationRenderer(allocationChosenCallback, config) { // Replace each word into the formatting string. // - $.each(zipped, function(i, original_token) { + zipped.each(function(i, original_token) { var category = original_token[0]; var word = original_token[2]; @@ -110,15 +114,10 @@ function AllocationRenderer(allocationChosenCallback, config) { return result; } - var regexp = new RegExp("%" + j + "\\$s", "g"); + var regexp = new RegExp("%" + (i+1) + "\\$s", "g"); result = result.replace(regexp, word); - - j += 1; - - return j; }); - return result; }; this.rendered = rendered; @@ -180,13 +179,16 @@ function AllocationRenderer(allocationChosenCallback, config) { // And append ellipses. // - if (!no_ellipses.include(last_part[0])) { last_part[1] += '...'; } // TODO * + if (!nonPartial.include(last_part[0])) { last_part[1] += '...'; } // Render each group and return the resulting rendered array. // - return $.map(groups, function(group) { - return rendered(group); + var result = []; + groups.each(function(i, group) { + result.push(rendered(group)); }); + + return result; }; this.groupify = groupify; @@ -195,11 +197,13 @@ function AllocationRenderer(allocationChosenCallback, config) { function querify(zipped) { var query_parts = []; var qualifier; + for (var i in zipped) { qualifier = zipped[i][0]; qualifier = qualifiers[qualifier] || qualifier; // Use the returned qualifier if none is given. query_parts[i] = qualifier + ':' + zipped[i][2]; }; + return query_parts.join(' '); }; this.querify = querify; @@ -209,37 +213,10 @@ function AllocationRenderer(allocationChosenCallback, config) { function suggestify(zipped) { return groupify(zipped).join(' '); }; - - - // Generates the text and the link. - // - var generate = function() { - this.query = querify(combination); - this.text = suggestify(combination); - - return self; - }; - - // TODO Extract. - // - var listItem = function(text, count) { - return $('
        1. ' + text + '
          ' + count + '
        2. '); - }; + this.suggestify = suggestify; var render = function(allocation) { - - var combination = allocation.combination; - var type = allocation.type; - var count = allocation.count; - - var query = querify(combination); - - var item = listItem(suggestify(combination), count); - - // TODO Move this outwards? - // - item.bind('click', { query: query }, allocationChosenCallback); - return item; + return suggestify(allocation.combination); }; this.render = render; diff --git a/client/test_project/javascripts/picky.allocations_cloud.js b/client/test_project/javascripts/picky.allocations_cloud.js index 01acb14d..adbba66c 100644 --- a/client/test_project/javascripts/picky.allocations_cloud.js +++ b/client/test_project/javascripts/picky.allocations_cloud.js @@ -26,24 +26,34 @@ var PickyAllocationsCloud = function(view, config) { // // - var allocationChosen = function(event) { + var allocationChosenCallback = function(event) { hide(); view.allocationChosen(event); }; - var allocationRenderer = new AllocationRenderer(allocationChosen, config); + var allocationRenderer = new AllocationRenderer(config); + // How an allocation renders as a list item. + // + var listItem = function(text, count) { + return $('
        3. ' + text + '
          ' + count + '
        4. '); + }; + + // + // var createAllocationList = function(allocations) { var shown = []; + allocations.each(function(i, allocation) { - shown.push(allocationRenderer.render(allocation)); + var rendered = allocationRenderer.render(allocation); + var query = allocationRenderer.querify(allocation.combination); - // TODO Combine. - // allocationRenderer.generate(); - // var listItem = renderListItem(allocationRenderer); - - // shown.push(listItem); + rendered = listItem(rendered, allocation.count); + rendered.bind('click', { query: query }, allocationChosenCallback); + + shown.push(rendered); }); + return shown; }; diff --git a/client/test_project/javascripts/picky.client.js b/client/test_project/javascripts/picky.client.js index f0642d2a..2a28146c 100644 --- a/client/test_project/javascripts/picky.client.js +++ b/client/test_project/javascripts/picky.client.js @@ -1,4 +1,3 @@ -var Localization = {}; var PickyI18n = { }; // The client handles parameters and @@ -24,25 +23,31 @@ var PickyClient = function(config) { // // This needs to correspond to the parsing in the search engine. // - Localization.qualifiers = config.qualifiers || {}; + config['qualifiers'] = config.qualifiers || {}; // This is used to explain the preceding word in the suggestion text. // // e.g. with locale it: // ['title', 'ulysses', 'Ulysses'] => 'Ulysses (titolo)' // - Localization.explanations = config.explanations || {}; + config['explanations'] = config.explanations || {}; // This is used to expain more complex combinations of categories // in the choices. // // e.g. with locale en:{'author,title': '%1$s, who wrote %2$s'} // - Localization.choices = config.choices || {}; + config['choices'] = config.choices || {}; // Delimiters for connecting explanations. // - Localization.explanation_delimiters = { de:'und', fr:'et', it:'e', en:'and', ch:'und' }; + config['explanation_delimiters'] = { + ch:'und', + de:'und', + en:'and', + fr:'et', + it:'e' + }; // Either you pass it a backends hash with full and live, // or you pass it full and live (urls), which will then @@ -85,9 +90,9 @@ var PickyClient = function(config) { // Results rendering. // config['results'] = $(config['resultsSelector'] || (enclosingSelector + ' div.results')); - config['resultsDivider'] = config['resultsDivider'] || ''; - config['noAsterisks'] = config['noAsterisks'] || []; // e.g. ['category1', 'category2'] - config['wrapResults'] = config['wrapResults'] || '
            '; + config['resultsDivider'] = config['resultsDivider'] || ''; + config['nonPartial'] = config['nonPartial'] || []; // e.g. ['category1', 'category2'] + config['wrapResults'] = config['wrapResults'] || '
              '; // The central Picky controller. // diff --git a/client/test_project/javascripts/picky.results_renderer.js b/client/test_project/javascripts/picky.results_renderer.js index 429fbf71..8e682320 100644 --- a/client/test_project/javascripts/picky.results_renderer.js +++ b/client/test_project/javascripts/picky.results_renderer.js @@ -2,10 +2,9 @@ var PickyResultsRenderer = function(addination, config) { var locale = config.locale; - var results = config['results']; var resultsDivider = config['resultsDivider']; var allocationWrapper = config['wrapResults']; - var noAsterisks = config['noAsterisks']; + var nonPartial = config['nonPartial']; // Adds asterisks to the last token. // @@ -14,7 +13,7 @@ var PickyResultsRenderer = function(addination, config) { if (last_part === undefined) { return []; } var parts = combinations.slice(0, combinations.length-1); if (parts == []) { parts = [parts]; } - if (!noAsterisks.include(last_part[0])) { + if (!nonPartial.include(last_part[0])) { // Replace with * unless there is already one or a tilde. // if (last_part[1].match(/[^\*~]$/)) { last_part[1] += '*'; } @@ -120,7 +119,7 @@ var PickyResultsRenderer = function(addination, config) { // Render results with the data. // - this.render = function(data) { + this.render = function(results, data) { data.allocations.each(function(i, allocation) { // Only render if there is something to render. // TODO Move into methods. diff --git a/client/test_project/javascripts/picky.view.js b/client/test_project/javascripts/picky.view.js index 59f3f353..fa7f6c7a 100644 --- a/client/test_project/javascripts/picky.view.js +++ b/client/test_project/javascripts/picky.view.js @@ -117,7 +117,7 @@ var PickyView = function(picky_controller, config) { var showResults = function(data) { clean(); updateResultCounter(data.total); - resultsRenderer.render(data); + resultsRenderer.render(results, data); results.show(); showClearButton(); }; @@ -130,7 +130,7 @@ var PickyView = function(picky_controller, config) { var position = $(moreSelector).position().top; addination.remove(); // TODO Where should this be? - resultsRenderer.render(data); + resultsRenderer.render(results, data); scrollTo(position); }; diff --git a/generators/prototypes/client/sinatra/javascripts/picky.min.js b/generators/prototypes/client/sinatra/javascripts/picky.min.js index c4679c7a..199c8616 100644 --- a/generators/prototypes/client/sinatra/javascripts/picky.min.js +++ b/generators/prototypes/client/sinatra/javascripts/picky.min.js @@ -1,19 +1,19 @@ Array.prototype.index=function(a){for(var b=0,i=this.length;b0&&h<=5&&q.fadeTo("fast",0.5).fadeTo("fast", -1)},c=function(h){if(h.isEmpty())return"none";if(h.total>i&&h.allocations.length>1)return"support";return"ok"},o=function(h){s.attr("class","dashboard "+h)};this.insert=function(h){f.val(h);f.select()};this.fullResultsCallback=function(h){o(c(h));if(h.isEmpty()){j();u(0);y.show();e()}else if(h.total>i&&h.allocations.length>1){j();e();n.show(h);u(h.total)}else if(h.offset==0){j();u(h.total);d.render(h);w.show();e();f.focus()}else{var v=$(x).position().top;r.remove();d.render(h);$("body").animate({scrollTop:v- -12},500)}};this.liveResultsCallback=function(h){o(c(h));u(h.total)};this.allocationChosen=function(h){h=h.data.query;a.insert(h);a.allocationChosen(h)};this.addinationClicked=function(h){a.addinationClicked(m(),h)};(function(){f.keyup(function(h){if(m()==""){p();a.searchTextCleared()}else{a.searchTextEntered(m(),h);e()}});q.click(function(){m()==""||a.searchButtonClicked(m())});k.click(function(){m()==""||a.searchButtonClicked(m())});g.click(function(){p("");a.clearButtonClicked();f.focus()})})(); -f.focus()};var PickyBackend=function(a){var b=function(i,f,g){var k=g||{};k=$.extend({query:i},g);$.getJSON(a,k,function(q){f&&f(new PickyData(q))})};this.search=function(i,f,g,k){b(i,function(q){f&&f(k,q)},g)}},LiveBackend=function(a){var b=a.live||alert("A live backend path must be provided."),i=new PickyBackend(b);this.search=function(f,g,k,q){q=q||{};latestRequestTimestamp=new Date;q.live=latestRequestTimestamp;k=$.extend({ids:a.liveResults||0,offset:0},k);i.search(f,function(s,x){if(!s.live||s.live==latestRequestTimestamp)g&& -g(x)},k,q)}},FullBackend=function(a){var b=a.full||alert("A full backend path must be provided."),i=new PickyBackend(b);this.search=function(f,g,k,q){q=q||{};latestRequestTimestamp=new Date;q.full=latestRequestTimestamp;k=$.extend({ids:a.fullResults||20,offset:0},k);i.search(f,function(s,x){if(!s.full||s.full==latestRequestTimestamp)g&&g(x)},k,q)}};var PickyController=function(a){var b=new PickyView(this,a),i=a.backends,f=a.beforeInsert||function(){},g=a.before||function(){},k=a.success||function(){},q=a.after||function(){},s=a.liveRendered||false,x=a.liveSearchInterval||180,w,y=function(c){return(c=c&&c.match(/q=([^&]+)/))&&decodeURIComponent(c[1]).replace(/\+/g," ").replace(/#/g,"")||""};this.extractQuery=y;var r=function(){var c=window.History&&window.History.getState();return y(c&&c.url)};this.lastFullQuery=r;var n=function(c,o,h,v){o=g(o, -v)||o;w=[c,o,h,v];var z=o;if(z!=r()){z="?q="+escape(z).replace(/\*/g,"%2A");window.History&&window.History.getState()&&window.History.pushState&&window.History.pushState(null,null,z)}(c=i[c])&&c.search(o,h,v)};this.resend=function(){w&&n.apply(this,w)};var d=function(c,o){c=k(c,o)||c;b.fullResultsCallback(c);q(c,o)},e=function(c,o){clearInterval(p);n("full",c,d,o||{})};a=function(c,o){c=k(c,o)||c;b.liveResultsCallback(c);q(c,o)};var j=s?d:a,p,m=function(){var c=b.text();n("live",c,j,{});clearInterval(p)}; -p=setInterval(m,x);clearInterval(p);var u=function(c,o,h){c=f(c)||c;b.insert(c);h&&e(c,o)};this.insert=u;this.clearButtonClicked=function(){clearInterval(p)};this.searchTextCleared=function(){clearInterval(p)};this.searchTextEntered=function(c,o){if($.inArray(o.keyCode,[0,8,13,32,46,48,49,50,51,52,53,54,55,56,57,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90])>-1)if(o.keyCode==13)e(c);else{clearInterval(p);p=setInterval(m,x)}};this.searchButtonClicked=function(c){e(c)}; -this.allocationChosen=function(c){e(c)};this.addinationClicked=function(c,o){e(c,{offset:o.data.offset})};window.History&&window.History.Adapter.bind(window,"statechange",function(){var c=window.History.getState();(c=y(c.url))&&c!=(w.length>1&&w[1])&&u(c,{},true)})};var Localization={},PickyI18n={},PickyClient=function(a){PickyI18n.locale=$("html").attr("lang").split("-")[0]||"en";a.locale=a.locale||PickyI18n.locale;Localization.qualifiers=a.qualifiers||{};Localization.explanations=a.explanations||{};Localization.choices=a.choices||{};Localization.explanation_delimiters={de:"und",fr:"et",it:"e",en:"and",ch:"und"};var b=a.backends;if(b){b.live||alert("Both a full and live backend must be provided.");b.full||alert("Both a full and live backend must be provided.")}else a.backends= -{live:new LiveBackend(a),full:new FullBackend(a)};b=a.enclosingSelector||"#picky";a.input=$(a.inputSelector||b+" input.query");a.reset=$(a.resetSelector||b+" div.reset");a.button=$(a.buttonSelector||b+" input.search_button");a.counter=$(a.counterSelector||b+" div.status");a.dashboard=$(a.dashboardSelector||b+" .dashboard");a.results=$(a.resultsSelector||b+" div.results");a.noResults=$(a.noResultsSelector||b+" .no_results");a.moreSelector=a.moreSelector||b+" div.results div.addination:last";a.allocations= -$(a.allocationsSelector||b+" .allocations");a.shownAllocations=a.allocations.find(".shown");a.showMoreAllocations=a.allocations.find(".more");a.hiddenAllocations=a.allocations.find(".hidden");a.maxSuggestions=a.maxSuggestions||3;a.results=$(a.resultsSelector||b+" div.results");a.resultsDivider=a.resultsDivider||"";a.noAsterisks=a.noAsterisks||[];a.wrapResults=a.wrapResults||'
                ';var i=a.controller&&new a.controller(a)||new PickyController(a);var f=this.insert=function(g,k,q){i.insert(g, -k||{},q||true)};this.resend=i.resend;this.insertFromURL=function(g){if(g&&g!="")f(g);else(g=i.lastFullQuery())&&f(g)}};var PickyAddination=function(a,b){this.remove=function(){b.find(".addination").remove()};this.render=function(i){var f=i.total,g,k=i.renderedAmount();g=i.offset+k;k=g+k;i=i.total;if(i"+t("results.addination.more")+"");f.bind("click",{offset:g.offset},a.addinationClicked);return f}else return""}};var PickyResultsRenderer=function(a,b){var i=b.locale,f=b.results,g=b.resultsDivider,k=b.wrapResults,q=b.noAsterisks,s=function(n){var d=n[n.length-1];if(d===undefined)return[];n=n.slice(0,n.length-1);if(n==[])n=[n];if(!q.include(d[0]))if(d[1].match(/[^\*~]$/))d[1]+="*";n.push(d);return n};this.asteriskifyLastToken=s;var x=function(n){for(var d=Localization.explanations&&Localization.explanations[i]||{},e=[],j,p=0,m=n.length;p$1"),d].join(" ")};this.strongify=w;var y=function(n,d){var e=Localization.explanation_delimiters[i],j="",p=[],m=[];x(s(d)).each(function(u,c){var o=c[0],h=c[1];if(j==""||o==j){h=h.replace(/[\w,]+:(.+)/,"$1");p.push(h);j=o}else{var v=w(j,p.join(" "));p=[];p.push(h);j=o;m.push(v)}});m.push(w(j,p.join(" ")));m=m.join(" "+e+" ");return m=''+n+" "+m+""}; -this.explain=y;var r=function(n,d){var e='
                ';e+=y(d.type,d.combination);if(n.offset>0)e+='';e+="
                ";return e};this.renderHeader=r;this.render=function(n){n.allocations.each(function(d,e){if(e.entries.length>0){f.append(r(n,e)).append(e.entries.join(g));f.children("li").wrapAll(k)}});f.append(a.render(n))}};function AllocationRenderer(a,b){function i(d){var e={},j={},p=[],m;m=0;for(l=d.length;m=0;m--)d.remove(p[m]);return d}function f(d){return $.map(d,function(e,j){return"%"+(j+1)+"$s"}).join(" ")}function g(d){if(d.length==0)return"";var e=d=i(d);e.sort(function(v,z){return v[0]=0;d--){v=e[d];if(v.length>0)break}v=v[v.length-1];n.include(v[0])||(v[1]+="...");return $.map(e,function(z){return g(z)})}function q(d){var e=[],j,p;for(p in d){j=d[p][0];j=x[j]||j;e[p]=j+":"+d[p][2]}return e.join(" ")}var s=b.locale,x=Localization.qualifiers&&Localization.qualifiers[s]||{},w=Localization.explanations&&Localization.explanations[s]||{},y=b.groups||[],r=Localization.choices&&Localization.choices[s]||{};this.explanation=this.query=this.text="";var n=["street_number", -"zipcode"];this.contract=i;this.rendered=g;this.groupify=k;this.querify=q;this.render=function(d){var e=d.combination,j=d.count;d=q(e);e=k(e).join(" ");e=$('
              1. '+e+'
                '+j+"
              2. ");e.bind("click",{query:d},a);return e}};var PickyAllocationsCloud=function(a,b){var i=b.allocations,f=b.shownAllocations,g=b.showMoreAllocations,k=b.hiddenAllocations,q=b.maxSuggestions,s=function(){i.hide()},x=new AllocationRenderer(function(r){s();a.allocationChosen(r)},b),w=function(r){var n=[];r.each(function(d,e){n.push(x.render(e))});return n},y=function(r){if(r.length==0)return i.hide();f.empty();g.hide();k.empty().hide();if(r.length>q){$.each(r.slice(0,q-1),function(n,d){f.append(d)});$.each(r.slice(q-1),function(n,d){k.append(d)}); -g.show()}else $.each(r,function(n,d){f.append(d)});return i.show()};g.click(function(){g.hide();k.show()});this.hide=s;this.show=function(r){y(w(r.allocations));i.show()}}; +"en",i=a.split(".").concat(b),f=dictionary,e=0,k=i.length;e0&&h<=5&&q.fadeTo("fast",0.5).fadeTo("fast", +1)},c=function(h){if(h.isEmpty())return"none";if(h.total>i&&h.allocations.length>1)return"support";return"ok"},o=function(h){s.attr("class","dashboard "+h)};this.insert=function(h){f.val(h);f.select()};this.fullResultsCallback=function(h){o(c(h));if(h.isEmpty()){j();u(0);y.show();d()}else if(h.total>i&&h.allocations.length>1){j();d();p.show(h);u(h.total)}else if(h.offset==0){j();u(h.total);g.render(v,h);v.show();d();f.focus()}else{var w=$(x).position().top;r.remove();g.render(v,h);$("body").animate({scrollTop:w- +12},500)}};this.liveResultsCallback=function(h){o(c(h));u(h.total)};this.allocationChosen=function(h){h=h.data.query;a.insert(h);a.allocationChosen(h)};this.addinationClicked=function(h){a.addinationClicked(n(),h)};(function(){f.keyup(function(h){if(n()==""){m();a.searchTextCleared()}else{a.searchTextEntered(n(),h);d()}});q.click(function(){n()==""||a.searchButtonClicked(n())});k.click(function(){n()==""||a.searchButtonClicked(n())});e.click(function(){m("");a.clearButtonClicked();f.focus()})})(); +f.focus()};var PickyBackend=function(a){var b=function(i,f,e){var k=e||{};k=$.extend({query:i},e);$.getJSON(a,k,function(q){f&&f(new PickyData(q))})};this.search=function(i,f,e,k){b(i,function(q){f&&f(k,q)},e)}},LiveBackend=function(a){var b=a.live||alert("A live backend path must be provided."),i=new PickyBackend(b);this.search=function(f,e,k,q){q=q||{};latestRequestTimestamp=new Date;q.live=latestRequestTimestamp;k=$.extend({ids:a.liveResults||0,offset:0},k);i.search(f,function(s,x){if(!s.live||s.live==latestRequestTimestamp)e&& +e(x)},k,q)}},FullBackend=function(a){var b=a.full||alert("A full backend path must be provided."),i=new PickyBackend(b);this.search=function(f,e,k,q){q=q||{};latestRequestTimestamp=new Date;q.full=latestRequestTimestamp;k=$.extend({ids:a.fullResults||20,offset:0},k);i.search(f,function(s,x){if(!s.full||s.full==latestRequestTimestamp)e&&e(x)},k,q)}};var PickyController=function(a){var b=new PickyView(this,a),i=a.backends,f=a.beforeInsert||function(){},e=a.before||function(){},k=a.success||function(){},q=a.after||function(){},s=a.liveRendered||false,x=a.liveSearchInterval||180,v,y=function(c){return(c=c&&c.match(/q=([^&]+)/))&&decodeURIComponent(c[1]).replace(/\+/g," ").replace(/#/g,"")||""};this.extractQuery=y;var r=function(){var c=window.History&&window.History.getState();return y(c&&c.url)};this.lastFullQuery=r;var p=function(c,o,h,w){o=e(o, +w)||o;v=[c,o,h,w];var z=o;if(z!=r()){z="?q="+escape(z).replace(/\*/g,"%2A");window.History&&window.History.getState()&&window.History.pushState&&window.History.pushState(null,null,z)}(c=i[c])&&c.search(o,h,w)};this.resend=function(){v&&p.apply(this,v)};var g=function(c,o){c=k(c,o)||c;b.fullResultsCallback(c);q(c,o)},d=function(c,o){clearInterval(m);p("full",c,g,o||{})};a=function(c,o){c=k(c,o)||c;b.liveResultsCallback(c);q(c,o)};var j=s?g:a,m,n=function(){var c=b.text();p("live",c,j,{});clearInterval(m)}; +m=setInterval(n,x);clearInterval(m);var u=function(c,o,h){c=f(c)||c;b.insert(c);h&&d(c,o)};this.insert=u;this.clearButtonClicked=function(){clearInterval(m)};this.searchTextCleared=function(){clearInterval(m)};this.searchTextEntered=function(c,o){if($.inArray(o.keyCode,[0,8,13,32,46,48,49,50,51,52,53,54,55,56,57,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90])>-1)if(o.keyCode==13)d(c);else{clearInterval(m);m=setInterval(n,x)}};this.searchButtonClicked=function(c){d(c)}; +this.allocationChosen=function(c){d(c)};this.addinationClicked=function(c,o){d(c,{offset:o.data.offset})};window.History&&window.History.Adapter.bind(window,"statechange",function(){var c=window.History.getState();(c=y(c.url))&&c!=(v.length>1&&v[1])&&u(c,{},true)})};var PickyI18n={},PickyClient=function(a){PickyI18n.locale=$("html").attr("lang").split("-")[0]||"en";a.locale=a.locale||PickyI18n.locale;a.qualifiers=a.qualifiers||{};a.explanations=a.explanations||{};a.choices=a.choices||{};a.explanation_delimiters={ch:"und",de:"und",en:"and",fr:"et",it:"e"};var b=a.backends;if(b){b.live||alert("Both a full and live backend must be provided.");b.full||alert("Both a full and live backend must be provided.")}else a.backends={live:new LiveBackend(a),full:new FullBackend(a)}; +b=a.enclosingSelector||"#picky";a.input=$(a.inputSelector||b+" input.query");a.reset=$(a.resetSelector||b+" div.reset");a.button=$(a.buttonSelector||b+" input.search_button");a.counter=$(a.counterSelector||b+" div.status");a.dashboard=$(a.dashboardSelector||b+" .dashboard");a.results=$(a.resultsSelector||b+" div.results");a.noResults=$(a.noResultsSelector||b+" .no_results");a.moreSelector=a.moreSelector||b+" div.results div.addination:last";a.allocations=$(a.allocationsSelector||b+" .allocations"); +a.shownAllocations=a.allocations.find(".shown");a.showMoreAllocations=a.allocations.find(".more");a.hiddenAllocations=a.allocations.find(".hidden");a.maxSuggestions=a.maxSuggestions||3;a.results=$(a.resultsSelector||b+" div.results");a.resultsDivider=a.resultsDivider||"";a.nonPartial=a.nonPartial||[];a.wrapResults=a.wrapResults||'
                  ';var i=a.controller&&new a.controller(a)||new PickyController(a);var f=this.insert=function(e,k,q){i.insert(e,k||{},q||true)};this.resend=i.resend; +this.insertFromURL=function(e){if(e&&e!="")f(e);else(e=i.lastFullQuery())&&f(e)}};var PickyAddination=function(a,b){this.remove=function(){b.find(".addination").remove()};this.render=function(i){var f=i.total,e,k=i.renderedAmount();e=i.offset+k;k=e+k;i=i.total;if(i"+t("results.addination.more")+"");f.bind("click",{offset:e.offset},a.addinationClicked);return f}else return""}};var PickyResultsRenderer=function(a,b){var i=b.locale,f=b.resultsDivider,e=b.wrapResults,k=b.nonPartial,q=function(r){var p=r[r.length-1];if(p===undefined)return[];r=r.slice(0,r.length-1);if(r==[])r=[r];if(!k.include(p[0]))if(p[1].match(/[^\*~]$/))p[1]+="*";r.push(p);return r};this.asteriskifyLastToken=q;var s=function(r){for(var p=Localization.explanations&&Localization.explanations[i]||{},g=[],d,j=0,m=r.length;j$1"),p].join(" ")};this.strongify=x;var v=function(r,p){var g=Localization.explanation_delimiters[i],d="",j=[],m=[];s(q(p)).each(function(n,u){var c=u[0],o=u[1];if(d==""||c==d){o=o.replace(/[\w,]+:(.+)/,"$1");j.push(o);d=c}else{var h=x(d,j.join(" "));j=[];j.push(o);d=c;m.push(h)}});m.push(x(d,j.join(" ")));m=m.join(" "+g+" ");return m=''+r+" "+m+""}; +this.explain=v;var y=function(r,p){var g='
                  ';g+=v(p.type,p.combination);if(r.offset>0)g+='';g+="
                  ";return g};this.renderHeader=y;this.render=function(r,p){p.allocations.each(function(g,d){if(d.entries.length>0){r.append(y(p,d)).append(d.entries.join(f));r.children("li").wrapAll(e)}});r.append(a.render(p))}};function AllocationRenderer(a,b){function i(g){var d={},j={},m=[],n;n=0;for(l=g.length;n=0;n--)g.remove(m[n]);return g}function f(g){var d=[];g.each(function(j){d.push("%"+(j+1)+"$s")});return d.join(" ")}function e(g){if(g.length==0)return"";var d=g=i(g);d.sort(function(h,w){return h[0]=0;g--){w=d[g];if(w.length>0)break}w=w[w.length-1];p.include(w[0])||(w[1]+="...");var z=[];d.each(function(A,B){z.push(e(B))});return z}function q(g){return k(g).join(" ")}var s=b.locale,x=b.qualifiers&&b.qualifiers[s]||{},v=b.explanations&&b.explanations[s]||{},y=b.groups||[],r=b.choices&&b.choices[s]||{},p=b.nonPartial||[];this.explanation=this.query=this.text="";this.contract=i;this.makeUpMissingFormat=f;this.rendered=e;this.groupify=k;this.querify=function(g){var d=[],j,m;for(m in g){j= +g[m][0];j=x[j]||j;d[m]=j+":"+g[m][2]}return d.join(" ")};this.suggestify=q;this.render=function(g){return q(g.combination)}};var PickyAllocationsCloud=function(a,b){var i=b.allocations,f=b.shownAllocations,e=b.showMoreAllocations,k=b.hiddenAllocations,q=b.maxSuggestions,s=function(){i.hide()},x=function(p){s();a.allocationChosen(p)},v=new AllocationRenderer(b),y=function(p){var g=[];p.each(function(d,j){var m=v.render(j),n=v.querify(j.combination);m=$('
                1. '+m+'
                  '+j.count+"
                2. ");m.bind("click",{query:n},x);g.push(m)});return g},r=function(p){if(p.length==0)return i.hide(); +f.empty();e.hide();k.empty().hide();if(p.length>q){$.each(p.slice(0,q-1),function(g,d){f.append(d)});$.each(p.slice(q-1),function(g,d){k.append(d)});e.show()}else $.each(p,function(g,d){f.append(d)});return i.show()};e.click(function(){e.hide();k.show()});this.hide=s;this.show=function(p){r(y(p.allocations));i.show()}};