Added command Transpose Cells in Rows into Columns (Issue 82).
git-svn-id: http://google-refine.googlecode.com/svn/trunk@1147 7d457c2a-affb-35e4-300a-418c747d4874
This commit is contained in:
parent
7d4125654e
commit
8f071ede31
@ -74,6 +74,7 @@ public class GridworksServlet extends Butterfly {
|
|||||||
{"fill-down", "com.google.gridworks.commands.cell.FillDownCommand"},
|
{"fill-down", "com.google.gridworks.commands.cell.FillDownCommand"},
|
||||||
{"blank-down", "com.google.gridworks.commands.cell.BlankDownCommand"},
|
{"blank-down", "com.google.gridworks.commands.cell.BlankDownCommand"},
|
||||||
{"transpose-columns-into-rows", "com.google.gridworks.commands.cell.TransposeColumnsIntoRowsCommand"},
|
{"transpose-columns-into-rows", "com.google.gridworks.commands.cell.TransposeColumnsIntoRowsCommand"},
|
||||||
|
{"transpose-rows-into-columns", "com.google.gridworks.commands.cell.TransposeRowsIntoColumnsCommand"},
|
||||||
|
|
||||||
{"add-column", "com.google.gridworks.commands.column.AddColumnCommand"},
|
{"add-column", "com.google.gridworks.commands.column.AddColumnCommand"},
|
||||||
{"remove-column", "com.google.gridworks.commands.column.RemoveColumnCommand"},
|
{"remove-column", "com.google.gridworks.commands.column.RemoveColumnCommand"},
|
||||||
|
@ -0,0 +1,37 @@
|
|||||||
|
package com.google.gridworks.commands.cell;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
import javax.servlet.ServletException;
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import com.google.gridworks.commands.Command;
|
||||||
|
import com.google.gridworks.model.AbstractOperation;
|
||||||
|
import com.google.gridworks.model.Project;
|
||||||
|
import com.google.gridworks.operations.cell.TransposeRowsIntoColumnsOperation;
|
||||||
|
import com.google.gridworks.process.Process;
|
||||||
|
|
||||||
|
public class TransposeRowsIntoColumnsCommand extends Command {
|
||||||
|
@Override
|
||||||
|
public void doPost(HttpServletRequest request, HttpServletResponse response)
|
||||||
|
throws ServletException, IOException {
|
||||||
|
|
||||||
|
try {
|
||||||
|
Project project = getProject(request);
|
||||||
|
|
||||||
|
String columnName = request.getParameter("columnName");
|
||||||
|
int rowCount = Integer.parseInt(request.getParameter("rowCount"));
|
||||||
|
|
||||||
|
AbstractOperation op = new TransposeRowsIntoColumnsOperation(
|
||||||
|
columnName, rowCount);
|
||||||
|
|
||||||
|
Process process = op.createProcess(project, new Properties());
|
||||||
|
|
||||||
|
performProcessAndRespond(request, response, project, process);
|
||||||
|
} catch (Exception e) {
|
||||||
|
respondException(response, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -14,6 +14,7 @@ import com.google.gridworks.operations.cell.MultiValuedCellJoinOperation;
|
|||||||
import com.google.gridworks.operations.cell.MultiValuedCellSplitOperation;
|
import com.google.gridworks.operations.cell.MultiValuedCellSplitOperation;
|
||||||
import com.google.gridworks.operations.cell.TextTransformOperation;
|
import com.google.gridworks.operations.cell.TextTransformOperation;
|
||||||
import com.google.gridworks.operations.cell.TransposeColumnsIntoRowsOperation;
|
import com.google.gridworks.operations.cell.TransposeColumnsIntoRowsOperation;
|
||||||
|
import com.google.gridworks.operations.cell.TransposeRowsIntoColumnsOperation;
|
||||||
import com.google.gridworks.operations.column.ColumnAdditionOperation;
|
import com.google.gridworks.operations.column.ColumnAdditionOperation;
|
||||||
import com.google.gridworks.operations.column.ColumnMoveOperation;
|
import com.google.gridworks.operations.column.ColumnMoveOperation;
|
||||||
import com.google.gridworks.operations.column.ColumnRemovalOperation;
|
import com.google.gridworks.operations.column.ColumnRemovalOperation;
|
||||||
@ -54,6 +55,7 @@ public abstract class OperationRegistry {
|
|||||||
register("multivalued-cell-split", MultiValuedCellSplitOperation.class);
|
register("multivalued-cell-split", MultiValuedCellSplitOperation.class);
|
||||||
register("fill-down", FillDownOperation.class);
|
register("fill-down", FillDownOperation.class);
|
||||||
register("transpose-columns-into-rows", TransposeColumnsIntoRowsOperation.class);
|
register("transpose-columns-into-rows", TransposeColumnsIntoRowsOperation.class);
|
||||||
|
register("transpose-rows-into-columns", TransposeRowsIntoColumnsOperation.class);
|
||||||
|
|
||||||
register("column-addition", ColumnAdditionOperation.class);
|
register("column-addition", ColumnAdditionOperation.class);
|
||||||
register("column-removal", ColumnRemovalOperation.class);
|
register("column-removal", ColumnRemovalOperation.class);
|
||||||
|
@ -0,0 +1,125 @@
|
|||||||
|
package com.google.gridworks.operations.cell;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
import org.json.JSONException;
|
||||||
|
import org.json.JSONObject;
|
||||||
|
import org.json.JSONWriter;
|
||||||
|
|
||||||
|
import com.google.gridworks.history.HistoryEntry;
|
||||||
|
import com.google.gridworks.model.AbstractOperation;
|
||||||
|
import com.google.gridworks.model.Cell;
|
||||||
|
import com.google.gridworks.model.Column;
|
||||||
|
import com.google.gridworks.model.Project;
|
||||||
|
import com.google.gridworks.model.Row;
|
||||||
|
import com.google.gridworks.model.changes.MassRowColumnChange;
|
||||||
|
import com.google.gridworks.operations.OperationRegistry;
|
||||||
|
|
||||||
|
public class TransposeRowsIntoColumnsOperation extends AbstractOperation {
|
||||||
|
final protected String _columnName;
|
||||||
|
final protected int _rowCount;
|
||||||
|
|
||||||
|
static public AbstractOperation reconstruct(Project project, JSONObject obj) throws Exception {
|
||||||
|
return new TransposeRowsIntoColumnsOperation(
|
||||||
|
obj.getString("columnName"),
|
||||||
|
obj.getInt("rowCount")
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public TransposeRowsIntoColumnsOperation(
|
||||||
|
String columnName,
|
||||||
|
int rowCount
|
||||||
|
) {
|
||||||
|
_columnName = columnName;
|
||||||
|
_rowCount = rowCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void write(JSONWriter writer, Properties options)
|
||||||
|
throws JSONException {
|
||||||
|
|
||||||
|
writer.object();
|
||||||
|
writer.key("op"); writer.value(OperationRegistry.s_opClassToName.get(this.getClass()));
|
||||||
|
writer.key("description"); writer.value("Transpose every " + _rowCount + " cells in column " + _columnName + " into separate columns");
|
||||||
|
writer.key("columnName"); writer.value(_columnName);
|
||||||
|
writer.key("rowCount"); writer.value(_rowCount);
|
||||||
|
writer.endObject();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected String getBriefDescription(Project project) {
|
||||||
|
return "Transpose every " + _rowCount + " cells in column " + _columnName + " into separate columns";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected HistoryEntry createHistoryEntry(Project project, long historyEntryID) throws Exception {
|
||||||
|
List<Column> newColumns = new ArrayList<Column>();
|
||||||
|
List<Column> oldColumns = project.columnModel.columns;
|
||||||
|
|
||||||
|
int columnIndex = project.columnModel.getColumnIndexByName(_columnName);
|
||||||
|
int columnCount = oldColumns.size();
|
||||||
|
|
||||||
|
newColumns.addAll(oldColumns.subList(0, columnIndex));
|
||||||
|
|
||||||
|
for (int i = 0; i < columnCount; i++) {
|
||||||
|
Column column = oldColumns.get(i);
|
||||||
|
|
||||||
|
if (i == columnIndex) {
|
||||||
|
int newIndex = 1;
|
||||||
|
for (int n = 0; n < _rowCount; n++) {
|
||||||
|
String columnName = _columnName + " " + newIndex++;
|
||||||
|
while (project.columnModel.getColumnByName(columnName) != null) {
|
||||||
|
columnName = _columnName + " " + newIndex++;
|
||||||
|
}
|
||||||
|
|
||||||
|
newColumns.add(new Column(i + n, columnName));
|
||||||
|
}
|
||||||
|
} else if (i < columnIndex) {
|
||||||
|
newColumns.add(new Column(i, column.getName()));
|
||||||
|
} else {
|
||||||
|
newColumns.add(new Column(i + _rowCount - 1, column.getName()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
List<Row> oldRows = project.rows;
|
||||||
|
List<Row> newRows = new ArrayList<Row>(oldRows.size() / _rowCount);
|
||||||
|
for (int r = 0; r < oldRows.size(); r += _rowCount) {
|
||||||
|
Row firstNewRow = new Row(newColumns.size());
|
||||||
|
|
||||||
|
for (int r2 = 0; r2 < _rowCount && r + r2 < oldRows.size(); r2++) {
|
||||||
|
Row oldRow = oldRows.get(r + r2);
|
||||||
|
Row newRow = r2 == 0 ? firstNewRow : new Row(newColumns.size());
|
||||||
|
boolean hasData = r2 == 0;
|
||||||
|
|
||||||
|
for (int c = 0; c < oldColumns.size(); c++) {
|
||||||
|
Column column = oldColumns.get(c);
|
||||||
|
Cell cell = oldRow.getCell(column.getCellIndex());
|
||||||
|
|
||||||
|
if (cell != null && cell.value != null) {
|
||||||
|
if (c == columnIndex) {
|
||||||
|
firstNewRow.setCell(columnIndex + r2, cell);
|
||||||
|
} else if (c < columnIndex) {
|
||||||
|
newRow.setCell(c, cell);
|
||||||
|
hasData = true;
|
||||||
|
} else {
|
||||||
|
newRow.setCell(c + _rowCount - 1, cell);
|
||||||
|
hasData = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (hasData) {
|
||||||
|
newRows.add(newRow);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return new HistoryEntry(
|
||||||
|
historyEntryID,
|
||||||
|
project,
|
||||||
|
getBriefDescription(null),
|
||||||
|
this,
|
||||||
|
new MassRowColumnChange(newColumns, newRows)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -352,6 +352,10 @@ DataTableColumnHeaderUI.prototype._createMenuForColumnHeader = function(elmt) {
|
|||||||
{
|
{
|
||||||
label: "Cells Across Columns into Rows",
|
label: "Cells Across Columns into Rows",
|
||||||
click: function() { self._doTransposeColumnsIntoRows(); }
|
click: function() { self._doTransposeColumnsIntoRows(); }
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Cells in Rows into Columns",
|
||||||
|
click: function() { self._doTransposeRowsIntoColumns(); }
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
@ -1232,6 +1236,33 @@ DataTableColumnHeaderUI.prototype._doTransposeColumnsIntoRows = function() {
|
|||||||
elmts.fromColumnSelect.bind("change", populateToColumn);
|
elmts.fromColumnSelect.bind("change", populateToColumn);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
DataTableColumnHeaderUI.prototype._doTransposeRowsIntoColumns = function() {
|
||||||
|
var rowCount = window.prompt("How many rows to transpose?", "2");
|
||||||
|
if (rowCount != null) {
|
||||||
|
try {
|
||||||
|
rowCount = parseInt(rowCount);
|
||||||
|
} catch (e) {
|
||||||
|
// ignore
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isNaN(rowCount) || rowCount < 2) {
|
||||||
|
alert("Expected an integer at least 2.");
|
||||||
|
} else {
|
||||||
|
var config = {
|
||||||
|
columnName: this._column.name,
|
||||||
|
rowCount: rowCount
|
||||||
|
};
|
||||||
|
|
||||||
|
Gridworks.postProcess(
|
||||||
|
"transpose-rows-into-columns",
|
||||||
|
config,
|
||||||
|
null,
|
||||||
|
{ modelsChanged: true }
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
DataTableColumnHeaderUI.prototype._showSortingCriterion = function(criterion, hasOtherCriteria) {
|
DataTableColumnHeaderUI.prototype._showSortingCriterion = function(criterion, hasOtherCriteria) {
|
||||||
var self = this;
|
var self = this;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user