问题
I'm trying to insert a 3x3 table into a google doc and then text into the table cells using c#. I came across this thread which helped me get the table added and at least get some text in one of the cells.
The answer in that thread said to add 4 to the startindex of the newly created table. I did that and all of my text was just added to the 2nd cell of the first row.
You can see from my code below that in the for loop I'm hoping to populate each cell with some test text. So, I'm not sure why all the text is being put into the one cell.
var docId = "mydocid";
List<Request> requests = new List<Request>
{
new Request()
{
InsertTable = new InsertTableRequest()
{
EndOfSegmentLocation = new EndOfSegmentLocation
{
SegmentId = ""
},
Columns = 3,
Rows = 3
}
}
};
BatchUpdateDocumentRequest body = new BatchUpdateDocumentRequest {Requests = requests};
service.Documents.BatchUpdate(body, docId).Execute();
var doc = service.Documents.Get(docId).Execute();
var index = doc.Body.Content.FirstOrDefault(x => x.Table != null).StartIndex + 4;
requests = new List<Request>();
for (var i = 0; i < 3; i++)
{
index++;
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = "test 1",
Location = new Location()
{
Index = index
}
}
});
index++;
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = "test 2",
Location = new Location()
{
Index = index
}
}
});
index++;
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = "test 3",
Location = new Location()
{
Index = index
}
}
});
}
body = new BatchUpdateDocumentRequest { Requests = requests };
service.Documents.BatchUpdate(body, docId).Execute();
Edit: After testing some more I realized I hadn't originally noticed that the text in the one cell ended up being this - tttttttttest 3est 2est 1est 3est 2est 1est 3est 2est 1 So, it looks like the index isn't necessarily being used to say which cell to write the content to, but some type of substring function. So, clearly I'm not understanding how to iterate through each row and cell to insert text with the index property.
As requested, here is the conversion of the request body object to json.
{
"requests": [{
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 60,
"segmentId": null,
"ETag": null
},
"text": "test 1",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 61,
"segmentId": null,
"ETag": null
},
"text": "test 2",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 62,
"segmentId": null,
"ETag": null
},
"text": "test 3",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 63,
"segmentId": null,
"ETag": null
},
"text": "test 1",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 64,
"segmentId": null,
"ETag": null
},
"text": "test 2",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 65,
"segmentId": null,
"ETag": null
},
"text": "test 3",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 66,
"segmentId": null,
"ETag": null
},
"text": "test 1",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 67,
"segmentId": null,
"ETag": null
},
"text": "test 2",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 68,
"segmentId": null,
"ETag": null
},
"text": "test 3",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}],
"writeControl": null,
"ETag": null
}
Edit after Tanaike's suggested answer.
So here's an updated version of the code.
public class AddendumRow
{
public string Title {get;set;}
public string Value {get;set;}
public string Description {get;set;}
}
var tableRows = new List<AddendumRow>()
{
new AddendumRow(){Title = "Row 1 Title", Value = "Row 1 Value", Description = "Row 1 Description" },
new AddendumRow(){Title = "Row 2 Title", Value = "Row 2 Value", Description = "Row 2 Description" },
new AddendumRow(){Title = "Row 3 Title", Value = "Row 3 Value", Description = "Row 3 Description" }
};
List<Request> requests = new List<Request>
{
new Request()
{
InsertTable = new InsertTableRequest()
{
EndOfSegmentLocation = new EndOfSegmentLocation
{
SegmentId = ""
},
Columns = 3,
Rows = tableRows.Count
}
}
};
BatchUpdateDocumentRequest body = new BatchUpdateDocumentRequest {Requests = requests};
service.Documents.BatchUpdate(body, docId).Execute();
var doc = service.Documents.Get(docId).Execute();
var index = doc.Body.Content.FirstOrDefault(x => x.Table != null).StartIndex + 3;
requests = new List<Request>();
foreach (var row in tableRows){
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = row.Title,
Location = new Location()
{
Index = index
}
}
});
index += 2;
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = row.Value,
Location = new Location()
{
Index = index
}
}
});
index += 2;
requests.Add(new Request()
{
InsertText = new InsertTextRequest()
{
Text = row.Description,
Location = new Location()
{
Index = index
}
}
});
index += 3;
}
body = new BatchUpdateDocumentRequest { Requests = requests };
var json = JsonConvert.SerializeObject(requests);
When I run that code, which I believe matches your example, it throws all of the content into the first row's first cell. And the content of that cell is...
RoRoRowRoRoRowRoRoRow 3 Descriptionw 3 Valuew 3 Title 2 Descriptionw 2 Valuew 2 Title 1 Descriptionw 1 Valuew 1 Title
You can see that it appears to be using the index as some sort of substring method for inserting the text inside existing text instead of moving to the next cell.
The resulting json of this line - var json = JsonConvert.SerializeObject(requests); is below. From what I can see it pretty much matches your example, but just has a lot of additional properties.
[{
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 58,
"segmentId": null,
"ETag": null
},
"text": "Row 1 Title",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 60,
"segmentId": null,
"ETag": null
},
"text": "Row 1 Value",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 62,
"segmentId": null,
"ETag": null
},
"text": "Row 1 Description",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 65,
"segmentId": null,
"ETag": null
},
"text": "Row 2 Title",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 67,
"segmentId": null,
"ETag": null
},
"text": "Row 2 Value",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 69,
"segmentId": null,
"ETag": null
},
"text": "Row 2 Description",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 72,
"segmentId": null,
"ETag": null
},
"text": "Row 3 Title",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 74,
"segmentId": null,
"ETag": null
},
"text": "Row 3 Value",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}, {
"createNamedRange": null,
"createParagraphBullets": null,
"deleteContentRange": null,
"deleteNamedRange": null,
"deleteParagraphBullets": null,
"deletePositionedObject": null,
"deleteTableColumn": null,
"deleteTableRow": null,
"insertInlineImage": null,
"insertPageBreak": null,
"insertTable": null,
"insertTableColumn": null,
"insertTableRow": null,
"insertText": {
"endOfSegmentLocation": null,
"location": {
"index": 76,
"segmentId": null,
"ETag": null
},
"text": "Row 3 Description",
"ETag": null
},
"replaceAllText": null,
"updateParagraphStyle": null,
"updateTableColumnProperties": null,
"updateTableRowStyle": null,
"updateTextStyle": null,
"ETag": null
}]
回答1:
- You want to append new table which has 3 rows and 3 columns to Google Document.
- You want to put the values to all cells.
I could understand like this. If my understanding is correct, how about this modification?
Modification points:
In your case, the values are put to new table. In this case, each value can be put to the start index of each cell.
From your request body, I supposes that this modified request is the following situation.
- New table, which has 3 rows and 3 columns, is appended to Google Document. And all cells of the table are empty.
- Values are put to all cells.
startIndex
(body.content[].startIndex
) of the appended table is57
.In this case,
startIndex
(body.content[].table.tableRows[0].tableCells[0].content[0].startIndex
) of row 1 and column 1 is '60'. AndstartIndex
of other cells are as follows.- From above image, it is found that the offsets for the cells of the column and row are
2
and3
, respectively.
- From above image, it is found that the offsets for the cells of the column and row are
When the values are put to all cells using the method of batchUpdate by one API call, there is one important point.
- For example, when a value of "sample" is put to the cell of row 1 and column 1 (
startIndex
is60
.),startIndex
of the cell of row 1 and column 2 becomes60 + 6 + 2 = 68
. The values of6
and2
are the length of the stringsample
and the offset for the next cell, respectively. - In your script, the offset is
1
. By this, all values are put in one cell. - As a simple method for putting values to the empty cells, in the case of the table which has 3 rows and 3 columns, it creates the request body by putting the values from the cell of row 3 and column 3 in the reverse order.
- For example, when a value of "sample" is put to the cell of row 1 and column 1 (
When above points are reflected to your request body, it becomes as follows.
Modified request body:
{"requests":[
{"insertText":{"location":{"index":78},"text":"c3"}},
{"insertText":{"location":{"index":76},"text":"b3"}},
{"insertText":{"location":{"index":74},"text":"a3"}},
{"insertText":{"location":{"index":71},"text":"c2"}},
{"insertText":{"location":{"index":69},"text":"b2"}},
{"insertText":{"location":{"index":67},"text":"a2"}},
{"insertText":{"location":{"index":64},"text":"c1"}},
{"insertText":{"location":{"index":62},"text":"b1"}},
{"insertText":{"location":{"index":60},"text":"a1"}}
]}
Result:
When above request body is used for the new table that startIndex
of table is 57
, the following result can be obtained. If you use above request body, please be careful the values of index
.
References:
- Method: documents.batchUpdate
- Inserting or deleting table rows
来源:https://stackoverflow.com/questions/56876436/how-to-add-content-to-google-doc-table-cell-in-c-sharp