Added support for starring rows.
git-svn-id: http://google-refine.googlecode.com/svn/trunk@129 7d457c2a-affb-35e4-300a-418c747d4874
This commit is contained in:
parent
92806cea7e
commit
ec1604e815
BIN
src/graphics/star-flag-map.psd
Normal file
BIN
src/graphics/star-flag-map.psd
Normal file
Binary file not shown.
BIN
src/graphics/star.psd
Normal file
BIN
src/graphics/star.psd
Normal file
Binary file not shown.
@ -16,6 +16,8 @@ import org.json.JSONTokener;
|
|||||||
|
|
||||||
import com.metaweb.gridworks.commands.Command;
|
import com.metaweb.gridworks.commands.Command;
|
||||||
import com.metaweb.gridworks.commands.edit.AddColumnCommand;
|
import com.metaweb.gridworks.commands.edit.AddColumnCommand;
|
||||||
|
import com.metaweb.gridworks.commands.edit.AnnotateOneRowCommand;
|
||||||
|
import com.metaweb.gridworks.commands.edit.AnnotateRowsCommand;
|
||||||
import com.metaweb.gridworks.commands.edit.ApplyOperationsCommand;
|
import com.metaweb.gridworks.commands.edit.ApplyOperationsCommand;
|
||||||
import com.metaweb.gridworks.commands.edit.CreateProjectCommand;
|
import com.metaweb.gridworks.commands.edit.CreateProjectCommand;
|
||||||
import com.metaweb.gridworks.commands.edit.DoTextTransformCommand;
|
import com.metaweb.gridworks.commands.edit.DoTextTransformCommand;
|
||||||
@ -82,6 +84,9 @@ public class GridworksServlet extends HttpServlet {
|
|||||||
_commands.put("recon-judge-one-cell", new ReconJudgeOneCellCommand());
|
_commands.put("recon-judge-one-cell", new ReconJudgeOneCellCommand());
|
||||||
_commands.put("recon-judge-similar-cells", new ReconJudgeSimilarCellsCommand());
|
_commands.put("recon-judge-similar-cells", new ReconJudgeSimilarCellsCommand());
|
||||||
|
|
||||||
|
_commands.put("annotate-one-row", new AnnotateOneRowCommand());
|
||||||
|
_commands.put("annotate-rows", new AnnotateRowsCommand());
|
||||||
|
|
||||||
_commands.put("save-protograph", new SaveProtographCommand());
|
_commands.put("save-protograph", new SaveProtographCommand());
|
||||||
|
|
||||||
_commands.put("preview-expression", new PreviewExpressionCommand());
|
_commands.put("preview-expression", new PreviewExpressionCommand());
|
||||||
|
@ -0,0 +1,85 @@
|
|||||||
|
package com.metaweb.gridworks.commands.edit;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.servlet.ServletException;
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.json.JSONWriter;
|
||||||
|
|
||||||
|
import com.metaweb.gridworks.commands.Command;
|
||||||
|
import com.metaweb.gridworks.history.HistoryEntry;
|
||||||
|
import com.metaweb.gridworks.model.Project;
|
||||||
|
import com.metaweb.gridworks.model.changes.RowStarChange;
|
||||||
|
import com.metaweb.gridworks.process.QuickHistoryEntryProcess;
|
||||||
|
|
||||||
|
public class AnnotateOneRowCommand extends Command {
|
||||||
|
@Override
|
||||||
|
public void doPost(HttpServletRequest request, HttpServletResponse response)
|
||||||
|
throws ServletException, IOException {
|
||||||
|
|
||||||
|
response.setCharacterEncoding("UTF-8");
|
||||||
|
response.setHeader("Content-Type", "application/json");
|
||||||
|
|
||||||
|
try {
|
||||||
|
Project project = getProject(request);
|
||||||
|
|
||||||
|
int rowIndex = Integer.parseInt(request.getParameter("row"));
|
||||||
|
|
||||||
|
String starredString = request.getParameter("starred");
|
||||||
|
if (starredString != null) {
|
||||||
|
boolean starred = "true".endsWith(starredString);
|
||||||
|
String description = starred ? "Star row " + rowIndex : "Unstar row " + rowIndex;
|
||||||
|
|
||||||
|
StarOneRowProcess process = new StarOneRowProcess(
|
||||||
|
project,
|
||||||
|
description,
|
||||||
|
rowIndex,
|
||||||
|
starred
|
||||||
|
);
|
||||||
|
|
||||||
|
boolean done = project.processManager.queueProcess(process);
|
||||||
|
if (done) {
|
||||||
|
JSONWriter writer = new JSONWriter(response.getWriter());
|
||||||
|
|
||||||
|
writer.object();
|
||||||
|
writer.key("code"); writer.value("ok");
|
||||||
|
writer.endObject();
|
||||||
|
} else {
|
||||||
|
respond(response, "{ \"code\" : \"pending\" }");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
respond(response, "{ \"code\" : \"error\", \"message\" : \"invalid command parameters\" }");
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
respondException(response, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected class StarOneRowProcess extends QuickHistoryEntryProcess {
|
||||||
|
final int rowIndex;
|
||||||
|
final boolean starred;
|
||||||
|
|
||||||
|
StarOneRowProcess(
|
||||||
|
Project project,
|
||||||
|
String briefDescription,
|
||||||
|
int rowIndex,
|
||||||
|
boolean starred
|
||||||
|
) {
|
||||||
|
super(project, briefDescription);
|
||||||
|
|
||||||
|
this.rowIndex = rowIndex;
|
||||||
|
this.starred = starred;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected HistoryEntry createHistoryEntry() throws Exception {
|
||||||
|
return new HistoryEntry(
|
||||||
|
_project,
|
||||||
|
starred ? "Star row " + rowIndex : "Unstar row " + rowIndex,
|
||||||
|
null,
|
||||||
|
new RowStarChange(rowIndex, starred)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,25 @@
|
|||||||
|
package com.metaweb.gridworks.commands.edit;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
|
||||||
|
import org.json.JSONObject;
|
||||||
|
|
||||||
|
import com.metaweb.gridworks.commands.EngineDependentCommand;
|
||||||
|
import com.metaweb.gridworks.model.AbstractOperation;
|
||||||
|
import com.metaweb.gridworks.operations.RowStarOperation;
|
||||||
|
|
||||||
|
public class AnnotateRowsCommand extends EngineDependentCommand {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected AbstractOperation createOperation(HttpServletRequest request,
|
||||||
|
JSONObject engineConfig) throws Exception {
|
||||||
|
|
||||||
|
String starredString = request.getParameter("starred");
|
||||||
|
if (starredString != null) {
|
||||||
|
boolean starred = "true".endsWith(starredString);
|
||||||
|
|
||||||
|
return new RowStarOperation(engineConfig, starred);
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,42 @@
|
|||||||
|
package com.metaweb.gridworks.model.changes;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import com.metaweb.gridworks.history.Change;
|
||||||
|
import com.metaweb.gridworks.model.Project;
|
||||||
|
|
||||||
|
public class MassChange implements Change {
|
||||||
|
private static final long serialVersionUID = -3926239320561407450L;
|
||||||
|
|
||||||
|
final protected List<? extends Change> _changes;
|
||||||
|
final protected boolean _updateRowContextDependencies;
|
||||||
|
|
||||||
|
public MassChange(List<? extends Change> changes, boolean updateRowContextDependencies) {
|
||||||
|
_changes = changes;
|
||||||
|
_updateRowContextDependencies = updateRowContextDependencies;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void apply(Project project) {
|
||||||
|
synchronized (project) {
|
||||||
|
for (Change change : _changes) {
|
||||||
|
change.apply(project);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_updateRowContextDependencies) {
|
||||||
|
project.recomputeRowContextDependencies();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void revert(Project project) {
|
||||||
|
synchronized (project) {
|
||||||
|
for (Change change : _changes) {
|
||||||
|
change.revert(project);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_updateRowContextDependencies) {
|
||||||
|
project.recomputeRowContextDependencies();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,31 @@
|
|||||||
|
package com.metaweb.gridworks.model.changes;
|
||||||
|
|
||||||
|
import com.metaweb.gridworks.history.Change;
|
||||||
|
import com.metaweb.gridworks.model.Project;
|
||||||
|
import com.metaweb.gridworks.model.Row;
|
||||||
|
|
||||||
|
public class RowStarChange implements Change {
|
||||||
|
private static final long serialVersionUID = 7343472491567342093L;
|
||||||
|
|
||||||
|
final int rowIndex;
|
||||||
|
final boolean newStarred;
|
||||||
|
boolean oldStarred;
|
||||||
|
|
||||||
|
public RowStarChange(int rowIndex, boolean newStarred) {
|
||||||
|
this.rowIndex = rowIndex;
|
||||||
|
this.newStarred = newStarred;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void apply(Project project) {
|
||||||
|
Row row = project.rows.get(rowIndex);
|
||||||
|
|
||||||
|
oldStarred = row.starred;
|
||||||
|
row.starred = newStarred;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void revert(Project project) {
|
||||||
|
Row row = project.rows.get(rowIndex);
|
||||||
|
|
||||||
|
row.starred = oldStarred;
|
||||||
|
}
|
||||||
|
}
|
@ -31,6 +31,8 @@ public abstract class OperationRegistry {
|
|||||||
register("column-addition", ColumnAdditionOperation.class);
|
register("column-addition", ColumnAdditionOperation.class);
|
||||||
register("column-removal", ColumnRemovalOperation.class);
|
register("column-removal", ColumnRemovalOperation.class);
|
||||||
|
|
||||||
|
register("row-star", RowStarOperation.class);
|
||||||
|
|
||||||
register("save-protograph", SaveProtographOperation.class);
|
register("save-protograph", SaveProtographOperation.class);
|
||||||
register("text-transform", TextTransformOperation.class);
|
register("text-transform", TextTransformOperation.class);
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,92 @@
|
|||||||
|
package com.metaweb.gridworks.operations;
|
||||||
|
|
||||||
|
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.metaweb.gridworks.browsing.Engine;
|
||||||
|
import com.metaweb.gridworks.browsing.FilteredRows;
|
||||||
|
import com.metaweb.gridworks.browsing.RowVisitor;
|
||||||
|
import com.metaweb.gridworks.history.Change;
|
||||||
|
import com.metaweb.gridworks.history.HistoryEntry;
|
||||||
|
import com.metaweb.gridworks.model.AbstractOperation;
|
||||||
|
import com.metaweb.gridworks.model.Project;
|
||||||
|
import com.metaweb.gridworks.model.Row;
|
||||||
|
import com.metaweb.gridworks.model.changes.MassChange;
|
||||||
|
import com.metaweb.gridworks.model.changes.RowStarChange;
|
||||||
|
|
||||||
|
public class RowStarOperation extends EngineDependentOperation {
|
||||||
|
private static final long serialVersionUID = 7047630960948704761L;
|
||||||
|
|
||||||
|
final protected boolean _starred;
|
||||||
|
|
||||||
|
static public AbstractOperation reconstruct(Project project, JSONObject obj) throws Exception {
|
||||||
|
JSONObject engineConfig = obj.getJSONObject("engineConfig");
|
||||||
|
boolean starred = obj.getBoolean("starred");
|
||||||
|
|
||||||
|
return new RowStarOperation(
|
||||||
|
engineConfig,
|
||||||
|
starred
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RowStarOperation(JSONObject engineConfig, boolean starred) {
|
||||||
|
super(engineConfig);
|
||||||
|
_starred = starred;
|
||||||
|
}
|
||||||
|
|
||||||
|
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(getBriefDescription());
|
||||||
|
writer.key("engineConfig"); writer.value(getEngineConfig());
|
||||||
|
writer.key("starred"); writer.value(_starred);
|
||||||
|
writer.endObject();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected String getBriefDescription() {
|
||||||
|
return (_starred ? "Star rows" : "Unstar rows");
|
||||||
|
}
|
||||||
|
|
||||||
|
protected HistoryEntry createHistoryEntry(Project project) throws Exception {
|
||||||
|
Engine engine = createEngine(project);
|
||||||
|
|
||||||
|
List<Change> changes = new ArrayList<Change>(project.rows.size());
|
||||||
|
|
||||||
|
FilteredRows filteredRows = engine.getAllFilteredRows(false);
|
||||||
|
filteredRows.accept(project, createRowVisitor(project, changes));
|
||||||
|
|
||||||
|
return new HistoryEntry(
|
||||||
|
project,
|
||||||
|
(_starred ? "Star" : "Unstar") + " " + changes.size() + " rows",
|
||||||
|
this,
|
||||||
|
new MassChange(changes, false)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected RowVisitor createRowVisitor(Project project, List<Change> changes) throws Exception {
|
||||||
|
return new RowVisitor() {
|
||||||
|
List<Change> changes;
|
||||||
|
|
||||||
|
public RowVisitor init(List<Change> changes) {
|
||||||
|
this.changes = changes;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean visit(Project project, int rowIndex, Row row, boolean contextual) {
|
||||||
|
if (row.starred != _starred) {
|
||||||
|
RowStarChange change = new RowStarChange(rowIndex, _starred);
|
||||||
|
|
||||||
|
changes.add(change);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}.init(changes);
|
||||||
|
}
|
||||||
|
}
|
BIN
src/main/webapp/images/star-flag-map.png
Normal file
BIN
src/main/webapp/images/star-flag-map.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 778 B |
BIN
src/main/webapp/images/star.png
Normal file
BIN
src/main/webapp/images/star.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 465 B |
@ -101,7 +101,8 @@ DataTableView.prototype.render = function() {
|
|||||||
var renderColumnKeys = function(keys) {
|
var renderColumnKeys = function(keys) {
|
||||||
if (keys.length > 0) {
|
if (keys.length > 0) {
|
||||||
var tr = table.insertRow(table.rows.length);
|
var tr = table.insertRow(table.rows.length);
|
||||||
tr.insertCell(0); // row index
|
tr.insertCell(0); // star
|
||||||
|
tr.insertCell(1); // row index
|
||||||
|
|
||||||
for (var c = 0; c < columns.length; c++) {
|
for (var c = 0; c < columns.length; c++) {
|
||||||
var td = tr.insertCell(tr.cells.length);
|
var td = tr.insertCell(tr.cells.length);
|
||||||
@ -120,7 +121,8 @@ DataTableView.prototype.render = function() {
|
|||||||
|
|
||||||
if (groups.length > 0) {
|
if (groups.length > 0) {
|
||||||
var tr = table.insertRow(table.rows.length);
|
var tr = table.insertRow(table.rows.length);
|
||||||
tr.insertCell(0); // row index
|
tr.insertCell(0); // star
|
||||||
|
tr.insertCell(1); // row index
|
||||||
|
|
||||||
for (var c = 0; c < columns.length; c++) {
|
for (var c = 0; c < columns.length; c++) {
|
||||||
var foundGroup = false;
|
var foundGroup = false;
|
||||||
@ -167,9 +169,9 @@ DataTableView.prototype.render = function() {
|
|||||||
|
|
||||||
var trHead = table.insertRow(table.rows.length);
|
var trHead = table.insertRow(table.rows.length);
|
||||||
|
|
||||||
var td = trHead.insertCell(trHead.cells.length);
|
var tdHeadIndex = trHead.insertCell(trHead.cells.length);
|
||||||
$(td).addClass("column-header");
|
$(tdHeadIndex).attr("colspan", "2").addClass("column-header");
|
||||||
$('<img src="/images/menu-dropdown.png" />').addClass("column-header-menu").appendTo(td).click(function() {
|
$('<img src="/images/menu-dropdown.png" />').addClass("column-header-menu").appendTo(tdHeadIndex).click(function() {
|
||||||
self._createMenuForAllColumns(this);
|
self._createMenuForAllColumns(this);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -197,21 +199,42 @@ DataTableView.prototype.render = function() {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
var rows = theProject.rowModel.rows;
|
var rows = theProject.rowModel.rows;
|
||||||
var even = true;
|
var renderRow = function(tr, r, row, even) {
|
||||||
for (var r = 0; r < rows.length; r++) {
|
|
||||||
var row = rows[r];
|
|
||||||
var cells = row.cells;
|
var cells = row.cells;
|
||||||
|
|
||||||
var tr = table.insertRow(table.rows.length);
|
var tdStar = tr.insertCell(tr.cells.length);
|
||||||
|
var star = $('<a href="javascript:{}"> </a>')
|
||||||
|
.addClass(row.starred ? "data-table-star-on" : "data-table-star-off")
|
||||||
|
.appendTo(tdStar)
|
||||||
|
.click(function() {
|
||||||
|
var newStarred = !row.starred;
|
||||||
|
$.post(
|
||||||
|
"/command/annotate-one-row?" + $.param({ project: theProject.id, row: row.i, starred: newStarred }),
|
||||||
|
null,
|
||||||
|
function(o) {
|
||||||
|
if (o.code == "ok") {
|
||||||
|
row.starred = newStarred;
|
||||||
|
|
||||||
|
$(tr).empty();
|
||||||
|
|
||||||
|
renderRow(tr, r, row, even);
|
||||||
|
|
||||||
|
ui.historyWidget.update();
|
||||||
|
} else {
|
||||||
|
ui.processWidget.update();
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"json"
|
||||||
|
);
|
||||||
|
|
||||||
|
});
|
||||||
|
|
||||||
var td = tr.insertCell(tr.cells.length);
|
var tdIndex = tr.insertCell(tr.cells.length);
|
||||||
if ("j" in row) {
|
if ("j" in row) {
|
||||||
even = !even;
|
|
||||||
|
|
||||||
$(tr).addClass("record");
|
$(tr).addClass("record");
|
||||||
$('<div></div>').html((row.j + 1) + ".").appendTo(td);
|
$('<div></div>').html((row.j + 1) + ".").appendTo(tdIndex);
|
||||||
} else {
|
} else {
|
||||||
$('<div></div>').html(" ").appendTo(td);
|
$('<div></div>').html(" ").appendTo(tdIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
if ("contextual" in row && row.contextual) {
|
if ("contextual" in row && row.contextual) {
|
||||||
@ -230,6 +253,16 @@ DataTableView.prototype.render = function() {
|
|||||||
new DataTableCellUI(this, cell, row.i, column.cellIndex, td);
|
new DataTableCellUI(this, cell, row.i, column.cellIndex, td);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
var even = true;
|
||||||
|
for (var r = 0; r < rows.length; r++) {
|
||||||
|
var row = rows[r];
|
||||||
|
var tr = table.insertRow(table.rows.length);
|
||||||
|
if ("j" in row) {
|
||||||
|
even = !even;
|
||||||
|
}
|
||||||
|
renderRow(tr, r, row, even);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -287,6 +320,19 @@ DataTableView.prototype._createMenuForAllColumns = function(elmt) {
|
|||||||
}
|
}
|
||||||
self.render();
|
self.render();
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{},
|
||||||
|
{
|
||||||
|
label: "Star Rows",
|
||||||
|
click: function() {
|
||||||
|
self.doPostThenUpdate("annotate-rows", { "starred" : "true" }, false);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Unstar Rows",
|
||||||
|
click: function() {
|
||||||
|
self.doPostThenUpdate("annotate-rows", { "starred" : "false" }, false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
], elmt);
|
], elmt);
|
||||||
};
|
};
|
||||||
|
@ -42,6 +42,9 @@ table.column-header-layout td {
|
|||||||
}
|
}
|
||||||
|
|
||||||
img.column-header-menu {
|
img.column-header-menu {
|
||||||
|
position: relative;
|
||||||
|
top: -5px;
|
||||||
|
left: 5px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.viewPanel-summary {
|
.viewPanel-summary {
|
||||||
@ -117,3 +120,18 @@ a.data-table-recon-match-similar {
|
|||||||
a.data-table-recon-match-similar:hover {
|
a.data-table-recon-match-similar:hover {
|
||||||
background-position: 0px -17px;
|
background-position: 0px -17px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
a.data-table-star-on, a.data-table-star-off {
|
||||||
|
display: block;
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
background-image: url('../images/star-flag-map.png');
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
a.data-table-star-on {
|
||||||
|
background-position: 0px 0px;
|
||||||
|
}
|
||||||
|
a.data-table-star-off {
|
||||||
|
background-position: -17px 0px;
|
||||||
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user