google apps script TextBox value not passed to e.p

2019-02-19 22:38发布

问题:

On the code below I am defining a TextBox with name and id. The button handler works fine but I am not been able to get the value entered on the TextBox. The msgBox shows up but the e.parameter.matchValue shows as undefined.

On other part of the app I have the same logic but with a ListBox and it works fine.

What am I doing wrong?

function chooseColumnValueToMatch() {
  var app = UiApp.createApplication().setHeight(150).setWidth(250);
  var ss = SpreadsheetApp.getActiveSpreadsheet();

  var columnName = ScriptProperties.getProperty("columnNameToMatch");

  var h1Line = app.createHTML("<h2>Value to match "+columnName+":</h2>");
  var textPara = app.createHTML("<p>Type the VALUE that the <b>"+columnName+"</b> column must match EXACTLY to send the message.</p>");
  var selectionHandler = app.createServerHandler('chooseColumnValueToMatchSelectionHandler');
  var valueInputBox = app.createTextBox()
      .setTitle("Match value for "+columnName)
      .setName("matchValue")
      .setId("matchValue");
  var submitBtn = app.createButton("Submit", selectionHandler);

  app.add(h1Line)
    .add(textPara)
    .add(valueInputBox)
    .add(submitBtn);
  ss.show(app);
}
function chooseColumnValueToMatchSelectionHandler(e){
  var app = UiApp.getActiveApplication();
  var columnName = ScriptProperties.getProperty("columnNameToMatch");

  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var msg = e.parameter.matchValue;

  Browser.msgBox("Value to match "+columnName+" column is:", msg, Browser.Buttons.OK);

  return app;
}

回答1:

It seems that you forgot to add a callbackElement to your handler

you could try like this :

selectionHandler.addCallbackElement(valueInputBox)

right after the submitBtn definition



回答2:

You have to use the ServerHandler.addCallbackElement method. The following code demonstrates it. The method call "tells" GAS internals that the value of the widget pointed as the parameter should be passed to the handler.

If you have multiple widgets, which should be handled by the handler, then, instead of calling the addCallbackElement with every widget, is possible to place all controls to a panel and point only the panel as the addCallbackElement method parameter. The code in the point 4.4 of this tutorial shows this way.

function doGet(e) {
  var app = UiApp.createApplication();
  var valueInputBox = app.createTextBox()
      .setTitle("Match value for XXX")
      .setName("matchValue")
      .setId("matchValue");
  var selectionHandler = app.createServerHandler('chooseColumnValueToMatchSelectionHandler');
  selectionHandler.addCallbackElement(valueInputBox);
  var submitBtn = app.createButton("Submit", selectionHandler);
  var output = app.createLabel().setId("output"); 
  app.add(valueInputBox).add(submitBtn).add(output);  
  return app;
}

function chooseColumnValueToMatchSelectionHandler(e){
  var app = UiApp.getActiveApplication();
  var output = app.getElementById("output");

  var msg = e.parameter.matchValue;

  output.setText("Value to match XXXX column is: " + msg);

  return app;
}