0

我最近问了这个问题: 有一个列表框填充 myDrive 中的每个文件夹

我得到了答案(感谢 Serge insas 的帮助!)但我正试图将他所做的东西融入我当前的 UI。我已经制作了列表框,除了他制作的函数之外的所有内容,当我尝试将它移到我的 UI 时,“function folderSelect”在我运行脚本时给了我一个“e undefined”错误。我还需要确保当我在下拉菜单中选择该文件夹时,当文档生成时,它会将该文档保存在该文件夹中。(很抱歉,我问了这么多关于这一切的问题。我试着在我来这里之前自己做我需要做的事情,但是当我不知道自己在做什么时,这很难。)

当前项目的 PasteBin:http: //pastebin.com/GVSvfcqG

这是我到目前为止所拥有的:

 function getTemplates() {
      var doc = SpreadsheetApp.getActiveSpreadsheet();
      var app = UiApp.createApplication().setTitle('Generate from template');
      // Create a grid with 3 text boxes and corresponding labels
      var grid = app.createGrid(5, 2);
      grid.setWidget(0, 0, app.createLabel('Template name:'));
      var list = app.createListBox();
      list.setName('Templates');
      grid.setWidget(0, 1, list);
      var docs = DocsList.getFolder("Templates").getFilesByType("document");
      for (var i = 0; i < docs.length; i++) {
        list.addItem(docs[i].getName(),docs[i].getId());
      }
      grid.setWidget(1, 0, app.createLabel('Row:'));
      var row = app.createTextBox().setName('row');
      row.setValue(SpreadsheetApp.getActiveSpreadsheet().getActiveRange().getRow());
      grid.setWidget(1, 1, row);

    ///////////////////////////////This is what i am trying to implement into my UI//////////////////////////////////////////////
       var curFN = app.createTextBox().setText('MyDrive/').setName('curFN').setId('curFN').setWidth('400');
  //var curFID = app.createTextBox().setText('x').setName('curFID').setId('curFID').setWidth('400');
  var listFolder = app.createListBox().setName('list').setId('list').addItem('please select a folder','x');
  grid.setWidget(2, 0, app.createLabel('Choose Folder:'));
  grid.setWidget(2, 1, listFolder);
  var folders = DocsList.getRootFolder().getFolders();
  for (var i = 0; i < folders.length; i++) {
    list.addItem(folders[i].getName(),folders[i].getId())
  } 
  var handler = app.createServerHandler('folderSelect').addCallbackElement(grid);
  list.addChangeHandler(handler);

  var currentFN = e.parameter.curFN;
  var currentFID = e.parameter.list;
  //Logger.log(currentFID);
  var FolderList = app.getElementById('listFolder');
  var curFN = app.getElementById('curFN');
  //var curFID = app.getElementById('curFID');
  //if(currentFID=='x'){currentFID=DocsList.getRootFolder().getId() ; curFN.setText('MyDrive/')};
  var startFolder = DocsList.getFolderById(currentFID);
  var folders = startFolder.getFolders();
  FolderList.clear().addItem('no other subFolder','x').addItem('Go back to Root','x');
  if(folders.length>0){FolderList.clear(); FolderList.addItem('please select a subFolder','x')};
  for (var i = 0; i < folders.length; i++) {
   FolderList.addItem(folders[i].getName(),folders[i].getId())
  } 
  curFN.setText(currentFN+DocsList.getFolderById(currentFID).getName()+'/');
  if(currentFID==DocsList.getRootFolder().getId()){curFN.setText('MyDrive/')};
  curFID.setText(currentFID);

    /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

      var panel = app.createVerticalPanel();
      panel.add(grid);
      var button = app.createButton('Submit');
      var handler = app.createServerClickHandler('generateDocument');
      handler.addCallbackElement(grid);
      button.addClickHandler(handler);

      // Add the button to the panel and the panel to the application, then display the application app in the Spreadsheet doc
      panel.add(button);
      app.add(panel);
      doc.show(app);
    }

编辑:

感谢 Serge insas 的所有帮助,他修复了所有问题,并且运行良好,如果您需要以下内容,我想与大家分享:将电子表格文档的一行导出到工作文档中,将其放入一个特定的文件夹并创建该工作文档的 PDF。使模板使用 {A} {B} 等等,你想把你的信息。

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

/*
Template Generator By: Andre Fecteau - klutch2013@gmail.com
Original Code From: kiszal@gmail.com (Found in the template gallery by searching "Templates" It is the first One.
Major Help from: Serge Insas On Stack Overflow (He did most of the work.)
Link 1: https://stackoverflow.com/questions/18147798/e-undefined-google-script-error
Link 2: https://stackoverflow.com/questions/18132837/have-a-listbox-populate-with-every-folder-in-mydrive

How To Use: 
First: each column is designated in your Template by {Column Letter} for example for column A it would be {A}
Second: You can change this, but your Template must be in a folder called "Templates." This folder can be anywhere in your drive.
Third: Click "Generate Documents Here!" Then click "Export Row to Document"
Fourth: Type in the row you want to export. Chose your Folder Path. Click Submit. 
NOTE ON FOURTH STEP: If you want your number to skip the header row add a +1 to line 28. 
This would mean if you typed "2" in the row box it actually exports row 3. I took this out because it can get confusing at times.

NOTE: Line 67 you can edit the word "Templates" to whatever folder you saved your Template into.

Feel free to edit this code as you wish and for your needs. That is what I did with the original code.
So there is no reason I should restrict what others do with this code.
*/

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

function generateDocument(e) {
  var template = DocsList.getFileById(e.parameter.Templates);
  Logger.log(template.getName());
  var Sheet = SpreadsheetApp.getActiveSpreadsheet();
  var row = Number(e.parameter.row)//+1 ; // Remove the // in this line next to the +1 to skip headers
  Logger.log(row);
  var currentFID = e.parameter.curFID;
  Logger.log(currentFID);
  var myDocID = template.makeCopy(Sheet.getRange('B'+row).getValue()+' - '+Sheet.getRange('E'+row).getValue()+' - '+Sheet.getRange('D'+row).getValue()+' - '+Sheet.getRange('X'+row).getValue()).getId();
  var myDoc = DocumentApp.openById(myDocID);
  var copyBody = myDoc.getActiveSection();
  var Sheet = SpreadsheetApp.getActiveSpreadsheet();
  row--; // decrement row number to be in concordance with real row numbers in sheet
  var myRow = SpreadsheetApp.getActiveSpreadsheet().getRange(row+":"+row);
  for (var i=1;i<Sheet.getLastColumn()+1;i++){
    var myCell = myRow.getCell(1, i);
    copyBody.replaceText("{"+myCell.getA1Notation().replace(row,"")+"}", myCell.getValue());
  }

  myDoc.saveAndClose();
  var destFolder = DocsList.getFolderById(currentFID);
  Logger.log(myDocID);
  var doc = DocsList.getFileById(myDocID);// get the document again but using docsList this time...
  doc.addToFolder(destFolder);// add it to the desired folder
  doc.removeFromFolder(DocsList.getRootFolder());// I did it step by step to be more easy to follow
  var pdf = DocsList.getFileById(myDocID).getAs("application/pdf");
  destFolder.createFile(pdf);// this will create the pdf file in your folder
  var app = UiApp.getActiveApplication();
  app.close();
  return app;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

function getTemplates() {
  var doc = SpreadsheetApp.getActiveSpreadsheet();
  var app = UiApp.createApplication().setTitle('Generate from template');
  // Create a grid with 3 text boxes and corresponding labels
  var grid = app.createGrid(5, 2);
  grid.setWidget(0, 0, app.createLabel('Template name:'));
  var list = app.createListBox();
  list.setName('Templates');
  grid.setWidget(0, 1, list);
  var docs = DocsList.getFolder("Templates").getFilesByType("document"); //Change the word "Templates" to whatever folder you saved your template into
  for (var i = 0; i < docs.length; i++) {
    list.addItem(docs[i].getName(),docs[i].getId());
  }

  grid.setWidget(1, 0, app.createLabel('Row:'));
  var row = app.createTextBox().setName('row');
  row.setValue(SpreadsheetApp.getActiveSpreadsheet().getActiveRange().getRow());
  grid.setWidget(1, 1, row);
  var curFN = app.createTextBox().setText('MyDrive/').setName('curFN').setId('curFN').setWidth('400');
  var curFID = app.createTextBox().setText(DocsList.getRootFolder().getId()).setName('curFID').setId('curFID').setVisible(false);
  var listF = app.createListBox().setName('listF').setId('listF').addItem('Please Select Folder','x');
  grid.setText(2,0,'Type Path:').setWidget(2,1,curFN).setText(3,0,'OR').setText(4,0, 'Choose Path:').setWidget(4,1,listF).setWidget(3,1,curFID);
  var folders = DocsList.getRootFolder().getFolders();
  for (var i = 0; i < folders.length; i++) {
    listF.addItem(folders[i].getName(),folders[i].getId())
  } 

  var handlerF = app.createServerHandler('folderSelect').addCallbackElement(grid);
  listF.addChangeHandler(handlerF);
  var panel = app.createVerticalPanel();
  panel.add(grid);
  var button = app.createButton('Submit');
  var handler = app.createServerClickHandler('generateDocument');
  handler.addCallbackElement(grid);
  button.addClickHandler(handler);
  // Add the button to the panel and the panel to the application, then display the application app in the Spreadsheet doc
  panel.add(button);
  app.add(panel);
  doc.show(app);
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

function folderSelect(e){
  var app = UiApp.getActiveApplication();
  var currentFN = e.parameter.curFN;
  var currentFID = e.parameter.listF;
  Logger.log(currentFID);
  var listF = app.getElementById('listF');
  var curFN = app.getElementById('curFN');
  var curFID = app.getElementById('curFID');
  if(currentFID=='x'){currentFID=DocsList.getRootFolder().getId() ; curFN.setText('MyDrive/')};
  var startFolder = DocsList.getFolderById(currentFID);
  var folders = startFolder.getFolders();
  listF.clear().addItem('No More Sub Folders!','x').addItem('Go back to Root','x');
  if(folders.length>0){listF.clear(); listF.addItem('Select Sub Folder','x')};
  for (var i = 0; i < folders.length; i++) {
    listF.addItem(folders[i].getName(),folders[i].getId())
  } 

  curFN.setText(currentFN+DocsList.getFolderById(currentFID).getName()+'/');
  if(currentFID==DocsList.getRootFolder().getId()){curFN.setText('MyDrive/')};
  curFID.setText(currentFID);
  return app;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

function onOpen() {   
  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var menuEntries = [{name: "Export Row to Document", functionName: "getTemplates"}];  
  ss.addMenu("Generate Documents Here!", menuEntries);  

}

4

1 回答 1

1

您无法按照您的方式集成此代码...handler函数是在用户完成某个操作并callBackElement使用对象为该函数带来值时执行的函数e(e 用于事件信息)。

如果您尝试进入e.parameter主代码,它将尝试获取尚未定义的值并生成您得到的错误。

这是我的代码在您的代码中的正确实现,请仔细检查它以查看并了解它是如何工作的。

function getTemplates() {
  var doc = SpreadsheetApp.getActiveSpreadsheet();
  var app = UiApp.createApplication().setTitle('Generate from template');
  // Create a grid with 3 text boxes and corresponding labels
  var grid = app.createGrid(5, 2);
  grid.setWidget(0, 0, app.createLabel('Template name:'));
  var list = app.createListBox();
  list.setName('Templates');
  grid.setWidget(0, 1, list);
  var docs = DocsList.getFolder("Templates").getFilesByType("document");
  for (var i = 0; i < docs.length; i++) {
    list.addItem(docs[i].getName(),docs[i].getId());
  }
  grid.setWidget(1, 0, app.createLabel('Row:'));
  var row = app.createTextBox().setName('row');
  row.setValue(SpreadsheetApp.getActiveSpreadsheet().getActiveRange().getRow());
  grid.setWidget(1, 1, row);
  var curFN = app.createTextBox().setText('MyDrive/').setName('curFN').setId('curFN').setWidth('400');
  var curFID = app.createTextBox().setText('x').setName('curFID').setId('curFID').setVisible(false);
  var listF = app.createListBox().setName('listF').setId('listF').addItem('please select a folder','x');
  grid.setText(2,0,'Choose a folder in your drive').setWidget(2,1,curFN).setWidget(3,1,curFID).setWidget(4,1,listF);
  var folders = DocsList.getRootFolder().getFolders();
  for (var i = 0; i < folders.length; i++) {
    listF.addItem(folders[i].getName(),folders[i].getId())
  } 
  var handlerF = app.createServerHandler('folderSelect').addCallbackElement(grid);
  listF.addChangeHandler(handlerF);
  var panel = app.createVerticalPanel();
  panel.add(grid);
  var button = app.createButton('Submit');
  var handler = app.createServerClickHandler('generateDocument');
  handler.addCallbackElement(grid);
  button.addClickHandler(handler);
  // Add the button to the panel and the panel to the application, then display the application app in the Spreadsheet doc
  panel.add(button);
  app.add(panel);
  doc.show(app);
}

function folderSelect(e){
  var app = UiApp.getActiveApplication();
  var currentFN = e.parameter.curFN;
  var currentFID = e.parameter.listF;
  Logger.log(currentFID);
  var listF = app.getElementById('listF');
  var curFN = app.getElementById('curFN');
  var curFID = app.getElementById('curFID');
  if(currentFID=='x'){currentFID=DocsList.getRootFolder().getId() ; curFN.setText('MyDrive/')};
  var startFolder = DocsList.getFolderById(currentFID);
  var folders = startFolder.getFolders();
  listF.clear().addItem('no other subFolder','x').addItem('Go back to Root','x');
  if(folders.length>0){listF.clear(); listF.addItem('please select a subFolder','x')};
  for (var i = 0; i < folders.length; i++) {
    listF.addItem(folders[i].getName(),folders[i].getId())
  } 
  curFN.setText(currentFN+DocsList.getFolderById(currentFID).getName()+'/');
  if(currentFID==DocsList.getRootFolder().getId()){curFN.setText('MyDrive/')};
  curFID.setText(currentFID);
  return app;
}

编辑 :

根据您的评论,这里是将文档移动到所选文件夹并在同一文件夹中创建 pdf 文件的修改:

function generateDocument(e) {
  var template = DocsList.getFileById(e.parameter.Templates);
  var Sheet = SpreadsheetApp.getActiveSpreadsheet();
  var row = e.parameter.row
  var currentFID = e.parameter.listF;
  var myDocID = template.makeCopy(Sheet.getRange('B'+row).getValue()+' - '+Sheet.getRange('E'+row).getValue()+' - '+Sheet.getRange('D'+row).getValue()+' - '+Sheet.getRange('X'+row).getValue()).getId();
  var myDoc = DocumentApp.openById(myDocID);
  var copyBody = myDoc.getActiveSection();
  var Sheet = SpreadsheetApp.getActiveSpreadsheet();
  var myRow = SpreadsheetApp.getActiveSpreadsheet().getRange(row+":"+row);
  for (var i=1;i<Sheet.getLastColumn()+1;i++){
    var myCell = myRow.getCell(1, i);
    copyBody.replaceText("{"+myCell.getA1Notation().replace(row,"")+"}", myCell.getValue());
  }
  myDoc.saveAndClose();
  var destFolder = DocsList.getFolderById(currentFID);
  var doc = DocsList.getFileById(myDocID);// get the document again but using docsList this time...
  doc.addToFolder(destFolder);// add it to the desired folder
  doc.removeFromFolder(DocsList.getRootFolder());// I did it step by step to be more easy to follow
  var pdf = DocsList.getFileById(myDocID).getAs("application/pdf");
  destFolder.createFile(pdf);// this will create the pdf file in your folder
  var app = UiApp.getActiveApplication();
  app.close();
  return app;
}
于 2013-08-09T14:14:52.470 回答