diff --git a/www/js/Application.js b/www/js/Application.js index 05b2d11e..37862015 100755 --- a/www/js/Application.js +++ b/www/js/Application.js @@ -333,7 +333,16 @@ define(function (require) { // this.checkDBSchema(); }, + checkDBSchema: function () { + // verify we're on the latest DB schema (upgrade if necessary) + return projModel.checkSchema(); + }, + + // ----------- // Routes from AppRouter (router.js) + // ----------- + + // Home page (main view) home: function () { // First, look for projects in the project list that aren't complete; // this can happen if the user clicks the back button before completing the @@ -396,18 +405,13 @@ define(function (require) { } }); }, - - checkDBSchema: function () { - // verify we're on the latest DB schema (upgrade if necessary) - return projModel.checkSchema(); - }, - + // Set UI language view (language can also be set within project settings / edit project view > UI settings) setUILanguage: function () { langView = new HomeViews.UILanguageView(); langView.delegateEvents(); window.Application.main.show(langView); }, - + // Edit project view editProject: function (id) { // edit the selected project var proj = this.ProjectList.where({projectid: id}); @@ -415,7 +419,7 @@ define(function (require) { window.Application.main.show(new ProjectViews.EditProjectView({model: proj[0]})); } }, - + // Copy project view copyProject: function () { var proj = new projModel.Project(); copyProjectView = new ProjectViews.CopyProjectView({model: proj}); @@ -423,7 +427,7 @@ define(function (require) { this.ProjectList.add(proj); this.main.show(copyProjectView); }, - + // New Project view (wizard) newProject: function () { var proj = new projModel.Project(); newProjectView = new ProjectViews.NewProjectView({model: proj}); @@ -431,28 +435,23 @@ define(function (require) { this.ProjectList.add(proj); this.main.show(newProjectView); }, - + // KB editor view editKB: function (id) { console.log("editKB"); - // update the KB and source Phrase lists, then show the KB editor view - $.when(window.Application.kbList.fetch({reset: true, data: {projectid: id}})).done(function () { - var proj = window.Application.ProjectList.where({projectid: id}); - editTUView = new SearchViews.TUListView({model: proj[0]}); - editTUView.delegateEvents(); - window.Application.main.show(editTUView); - }); + // show the KB editor view (KB refresh happens inside the view's onShow()) + var proj = window.Application.ProjectList.where({projectid: id}); + editTUView = new SearchViews.TUListView({model: proj[0]}); + editTUView.delegateEvents(); + window.Application.main.show(editTUView); }, - + // New Target Unit view newTU: function() { console.log("newTU"); - // update the KB list, then show the view - $.when(window.Application.kbList.fetch({reset: true, data: {projectid: window.Application.currentProject.get("projectid")}})).done(function () { - newTransView = new SearchViews.NewTUView(); - newTransView.delegateEvents(); - window.Application.main.show(newTransView); - }); + newTransView = new SearchViews.NewTUView(); + newTransView.delegateEvents(); + window.Application.main.show(newTransView); }, - + // View / edit TU editTU: function (id) { console.log("editTU"); // update the KB list, then show the view @@ -472,7 +471,7 @@ define(function (require) { window.Application.main.show(showTransView); }); }, - + // Show translations (edit TU, but also includes the "current translation" / SP) showTranslations: function (id) { console.log("showTranslations"); // update the KB and source phrase list, then display the Translations screen with the currently-selected sourcephrase @@ -535,43 +534,7 @@ define(function (require) { }); }); }, - - // Another process has sent us a file via URL. Get the File handle and send it along to - // importFileFromURL (below). - processFileEntry: function (fileEntry) { - console.log("processFileEntry: enter"); - fileEntry.file(window.Application.importFileFromURL, window.Application.importFail); - }, - - processError: function (error) { - // log the error and continue processing - console.log("getDirectory error: " + error.code); - alert("error: " + error.code); - }, - - // This is similar to importBooks, EXCEPT that another process is sending a file to us to - // open/import (rather than the user picking a file out of a list). Call - // ImportDocumentView::importFile() to import the file. - importFileFromURL: function (file) { - console.log("importFile: enter"); - var proj = window.Application.currentProject; - if (proj !== null) { - // We have a project -- load the ImportDocumentView to do the work - importDocView = new DocumentViews.ImportDocumentView({model: proj}); - importDocView.isLoadingFromURL = true; - importDocView.delegateEvents(); - window.Application.main.show(importDocView); - // call ImportDocumentView::importFromURL() to import the file - importDocView.importFromURL(file, proj); - } else { - alert("No current project defined -- ignoring open() call"); - } - }, - - importFail: function () { - alert("Unable to open file."); - }, - + // import doc view importBooks: function (id) { console.log("importBooks"); // update the book and chapter lists, then show the import docs view @@ -583,7 +546,7 @@ define(function (require) { window.Application.main.show(importDocView); } }, - + // Export doc view exportBooks: function (id) { console.log("exportBooks"); var proj = window.Application.currentProject; @@ -595,7 +558,7 @@ define(function (require) { window.Application.main.show(exportDocView); } }, - + // Search / browse chapter view lookupChapter: function (id) { console.log("lookupChapter"); $.when(window.Application.ProjectList.fetch({reset: true, data: {name: ""}})).done(function () { @@ -610,7 +573,7 @@ define(function (require) { }); }); }, - + // Adapt View (the reason we're here) adaptChapter: function (id) { console.log("adaptChapter"); // refresh the models @@ -649,6 +612,44 @@ define(function (require) { } }); }); + }, + // ---- + // External document route helper methods: + // Another process has sent us a file via URL. + // ---- + // Helper method to get the File handle from the external process and send it along to + // importFileFromURL (below). + processFileEntry: function (fileEntry) { + console.log("processFileEntry: enter"); + fileEntry.file(window.Application.importFileFromURL, window.Application.importFail); + }, + // helper callback to process a getDirectory() error + processError: function (error) { + // log the error and continue processing + console.log("getDirectory error: " + error.code); + alert("error: " + error.code); + }, + // This is similar to importBooks, EXCEPT that another process is sending a file to us to + // open/import (rather than the user picking a file out of a list). Call + // ImportDocumentView::importFile() to import the file. + importFileFromURL: function (file) { + console.log("importFile: enter"); + var proj = window.Application.currentProject; + if (proj !== null) { + // We have a project -- load the ImportDocumentView to do the work + importDocView = new DocumentViews.ImportDocumentView({model: proj}); + importDocView.isLoadingFromURL = true; + importDocView.delegateEvents(); + window.Application.main.show(importDocView); + // call ImportDocumentView::importFromURL() to import the file + importDocView.importFromURL(file, proj); + } else { + alert("No current project defined -- ignoring open() call"); + } + }, + // Helper callback for processFileEntry() failure (above) + importFail: function () { + alert("Unable to open file."); } }); diff --git a/www/js/models/sql/targetunit.js b/www/js/models/sql/targetunit.js index 778b2ef1..6fea3d2a 100644 --- a/www/js/models/sql/targetunit.js +++ b/www/js/models/sql/targetunit.js @@ -127,6 +127,7 @@ define(function (require) { TargetUnitCollection = Backbone.Collection.extend({ model: TargetUnit, + page_size: 0, resetFromDB: function () { var i = 0, @@ -226,6 +227,34 @@ define(function (require) { return deferred.promise(); }, + // Return the count (only) of items in the targetunit table matching the specified projectid and isGloss setting, + // and optionally a source filter + getCount: function(options) { + var deferred = $.Deferred(); + var source = ""; + var retValue = null; + var sql = "SELECT COUNT(*) as tot from targetunit WHERE projectid='" + options.data.projectid + "' AND isGloss=" + options.data.isGloss; + if (options.data.hasOwnProperty('source')) { + source = options.data.source; + if (source.length > 0) { + sql += " AND source LIKE '%" + source + "%'" + } + } + sql += ";"; + window.Application.db.transaction(function (tx) { + tx.executeSql(sql, [], function (tx, res) { + retValue = res.rows.item(0).tot; + console.log("SELECT ok: " + retValue + " targetunit items"); + deferred.resolve(retValue); + }, function (tx, err) { + console.log("SELECT COUNT(*) error: " + err.message); + }); + }, function (e) { + deferred.reject(e); + }); + return deferred.promise(); + }, + // UPDATE an array of TargetUnit objects updateBatch: function (models) { var deferred = $.Deferred(); @@ -261,6 +290,7 @@ define(function (require) { var deferred = $.Deferred(); var len = 0; var i = 0; + var source = ""; var projectid = null; var retValue = null; var results = null; @@ -270,44 +300,58 @@ define(function (require) { options.success(data); }); } else if (options.data.hasOwnProperty('projectid')) { - projectid = options.data.projectid; - results = targetunits.filter(function (element) { - return element.attributes.projectid === projectid.toLowerCase(); - }); - if (results.length === 0) { - // not in collection -- retrieve them from the db (alphabetized) - window.Application.db.transaction(function (tx) { - tx.executeSql("SELECT * from targetunit WHERE projectid=? ORDER BY source;", [projectid], function (tx, res) { - var tmpString = ""; - for (i = 0, len = res.rows.length; i < len; ++i) { - // add the chapter - var tu = new TargetUnit(); - tu.off("change"); - tu.set(res.rows.item(i)); - // convert refstring back into an array object - tmpString = tu.get('refstring'); - tu.set('refstring', JSON.parse(tmpString)); - targetunits.push(tu); - tu.on("change", tu.save, tu); - } - console.log("SELECT ok: " + res.rows.length + " targetunit items"); - retValue = targetunits; - options.success(retValue); - deferred.resolve(retValue); - }); - }, function (e) { - options.error(); - deferred.reject(e); - }); - } else { - // results already in collection -- return them - options.success(results); - deferred.resolve(results); + // get data in a specified projectid + projectid = options.data.projectid; + targetunits.length = 0; // reset the collection + // build the sql statement + var sql = "SELECT * from targetunit WHERE projectid='" + projectid + "'"; + if (options.data.hasOwnProperty('isGloss')) { + sql += " AND isGloss=" + options.data.isGloss; + } + if (options.data.hasOwnProperty('source')) { + if (options.data.source.length > 0) { + sql += " AND source LIKE '%" + options.data.source + "%'"; + } + } + sql += " ORDER BY source"; + if (options.data.hasOwnProperty('limit')) { + sql += " LIMIT " + options.data.limit; + if (options.data.hasOwnProperty('offset')) { + sql += " OFFSET " + options.data.offset; + } } + sql += ";"; + // retrieve them from the db (ordered by source) + window.Application.db.transaction(function (tx) { + tx.executeSql(sql, [], function (tx, res) { + var tmpString = ""; + for (i = 0, len = res.rows.length; i < len; ++i) { + // add the chapter + var tu = new TargetUnit(); + tu.off("change"); + tu.set(res.rows.item(i)); + // convert refstring back into an array object + tmpString = tu.get('refstring'); + tu.set('refstring', JSON.parse(tmpString)); + targetunits.push(tu); + tu.on("change", tu.save, tu); + } + console.log("SELECT ok: " + res.rows.length + " targetunit items"); + retValue = targetunits; + options.success(retValue); + deferred.resolve(retValue); + }, function (tx, err) { + console.log("TargetUnit SELECT error: " + err.message); + }); + }, function (e) { + options.error(); + deferred.reject(e); + }); + // return the promise return deferred.promise(); } else if (options.data.hasOwnProperty('source')) { - var source = options.data.source; + source = options.data.source; results = targetunits.filter(function (element) { return element.attributes.source.toLowerCase().indexOf(source.toLowerCase()) > -1; }); diff --git a/www/js/views/SearchViews.js b/www/js/views/SearchViews.js index 057ef381..b00db4ee 100644 --- a/www/js/views/SearchViews.js +++ b/www/js/views/SearchViews.js @@ -34,7 +34,9 @@ define(function (require) { caseSource = [], caseTarget = [], refstrings = [], - PAGE_SIZE = 100, // arbitrary # of search results to display at once + PAGE_SIZE = 100, // arbitrary # of search results to display at once + nKBTotal = 0, + nFilteredTotal = 0, //////// // STATIC METHODS @@ -100,6 +102,33 @@ define(function (require) { } }, + // Helper method that returns the