Skip to content

Commit

Permalink
fixes for read only and enabled columns;
Browse files Browse the repository at this point in the history
add auto detect to bindings
  • Loading branch information
johnspackman committed Jan 23, 2024
1 parent aa5a1b7 commit 7316b7d
Show file tree
Hide file tree
Showing 4 changed files with 202 additions and 9 deletions.
37 changes: 35 additions & 2 deletions source/class/qxl/datagrid/DataGrid.js
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,16 @@ qx.Class.define("qxl.datagrid.DataGrid", {
*/
scrollbar: {
group: ["scrollbarX", "scrollbarY"]
},

/**
* Whether the grid is read only (even if the data grid does not yet support editing, this is
* still relevant because it is available to the columns and )
*/
readOnly: {
init: false,
check: "Boolean",
event: "changeReadOnly"
}
},

Expand Down Expand Up @@ -190,6 +200,7 @@ qx.Class.define("qxl.datagrid.DataGrid", {
headerWidgetFactory() {
return new qxl.datagrid.ui.factory.HeaderWidgetFactory(this.getColumns());
},

header() {
return new qxl.datagrid.ui.HeaderRows(this.__sizeCalculator, this.getQxObject("headerWidgetFactory"), this.getDataSource());
}
Expand Down Expand Up @@ -227,17 +238,39 @@ qx.Class.define("qxl.datagrid.DataGrid", {
*/
_applyColumns(value, oldValue) {
if (oldValue) {
oldValue.removeListener("change", this.scheduleLayoutUpdate, this);
oldValue.removeListener("change", this.__onColumnsChange, this);
for (let column of oldValue) {
column.setDataGrid(null);
}
}
if (value) {
value.addListener("change", this.scheduleLayoutUpdate, this);
for (let column of value) {
column.setDataGrid(this);
}
value.addListener("change", this.__onColumnsChange, this);
}
this.__sizeCalculator.setColumns(value);
this.getQxObject("headerWidgetFactory").setColumns(value);
this.getQxObject("paneWidgetFactory").setColumns(value);
this.updateWidgets();
},

/**
* Event handler for changes in the columns array
*
* @param {qx.event.type.Data} evt
*/
__onColumnsChange(evt) {
let data = evt.getData();
if (data.type == "remove") {
data.column.setDataGrid(null);
}
if (data.type == "add") {
data.column.setDataGrid(this);
}
this.scheduleLayoutUpdate();
},

/**
* Apply for `dataSource`
*/
Expand Down
18 changes: 16 additions & 2 deletions source/class/qxl/datagrid/binding/Bindings.js
Original file line number Diff line number Diff line change
Expand Up @@ -65,14 +65,28 @@ qx.Class.define("qxl.datagrid.binding.Bindings", {
__bindingData: null,

/**
* Adds a binding or listener binding ID.
*
* Set `bindingType` to "binding" if this is a binding to a property, or "listener" if it's for a listener
* added with "addListener". If no value then it will be auto detected
*
* @param {qx.core.Object} model the object with a binding
* @param {*} bindingId the binding ID to release
* @param {String?"binding"} bindingType The type of the binding. Either "binding" or "listener". Defaults to binding. Set to "binding " if this is a binding to a property, or "listener" if it's for a listener added with "addListener".
* @param {String?} bindingType The type of the binding. Either "binding" or "listener". Defaults to auto detect.
*/
add(model, bindingId, bindingType) {
if (bindingType === undefined) {
bindingType = "binding";
if (typeof bindingId == "string") {
bindingType = "listener";
} else {
bindingType = "binding";
}
} else if (qx.core.Environment.get("qx.debug")) {
if (bindingType === "listener") {
this.assertTrue(typeof bindingId == "string", "Invalid binding type " + bindingType + " for bindingId " + bindingId);
} else {
this.assertTrue(typeof bindingId != "string", "Invalid binding type " + bindingType + " for bindingId " + JSON.stringify(bindingId));
}
}
this.__bindingData.push({
model,
Expand Down
136 changes: 131 additions & 5 deletions source/class/qxl/datagrid/column/Column.js
Original file line number Diff line number Diff line change
Expand Up @@ -91,17 +91,103 @@ qx.Class.define("qxl.datagrid.column.Column", {
event: "changeReadOnly"
},

/** Whether the column is enabled (this is controlled by the data grid) */
enabled: {
init: true,
check: "Boolean",
apply: "_applyEnabled",
event: "changeEnabled"
},

bindingOptions: {
init: () => undefined
}
},

events: {
/** Fired when the column details change */
change: "qx.event.type.Data",
headerTap: "qx.event.type.Event"

/** Fired when the user taps on a header cell */
headerTap: "qx.event.type.Event",

/** Fired when the effectivelyEnabled needs to be checked, data is a {Boolean} */
changeEffectivelyEnabled: "qx.event.type.Data",

/** Fired when the effectivelyReadOnly needs to be checked, data is a {Boolean} */
changeEffectivelyReadOnly: "qx.event.type.Data"
},

members: {
__datagrid: null,

/**
* Called the the DataGrid when the column is added. Do NOT call this manually.
*
* @param {qxl.datagrid.DataGrid} datagrid
*/
setDataGrid(datagrid) {
if (this.__datagrid === datagrid) {
return;
}
if (qx.core.Environment.get("qx.debug")) {
this.assertInstance(datagrid, qxl.datagrid.DataGrid);
this.assertTrue(!this.__datagrid, "DataGrid already set");
}
if (this.__datagrid) {
this.__datagrid.removeListener("changeEnabled", this.__onDataGridChangeEnabled, this);
this.__datagrid.removeListener("changeReadOnly", this.__onDataGridChangeReadOnly, this);
}
this.__datagrid = datagrid;
if (datagrid) {
datagrid.addListener("changeEnabled", this.__onDataGridChangeEnabled, this);
datagrid.addListener("changeReadOnly", this.__onDataGridChangeReadOnly, this);
}
this.fireDataEvent("changeEffectivelyEnabled", this.isEffectivelyEnabled());
this.fireDataEvent("changeEffectivelyReadOnly", this.isEffectivelyEnabled());
},

/**
* Returns the datagrid, if any
*
* @returns {qxl.datagrid.DataGrid}
*/
getDataGrid() {
return this.__datagrid;
},

/**
* Event handler for when the datagrid changes `enabled`
*/
__onDataGridChangeEnabled(evt) {
this.fireDataEvent("changeEffectivelyEnabled", this.isEffectivelyEnabled());
},

/**
* Event handler for when the datagrid changes `readOnly`
*/
__onDataGridChangeReadOnly(evt) {
this.fireDataEvent("changeEffectivelyReadOnly", this.isEffectivelyEnabled());
},

/**
* Detects whether the column is read only, taking into account the datagrid
*
* @returns {Boolean}
*/
isEffectivelyReadOnly() {
return this.getReadOnly() || !this.getEnabled() || this.__datagrid?.isReadOnly() || !this.__datagrid?.isEnabled();
},

/**
* Detects whether the column is enabled, taking into account the datagrid
*
* @returns {Boolean}
*/
isEffectivelyEnabled() {
return !this.getEnabled() || this.__datagrid?.isEnabled();
},

/**
* Called to implement the binding
*
Expand All @@ -112,13 +198,48 @@ qx.Class.define("qxl.datagrid.column.Column", {
*/
bindWidget(widget, model, factory) {
let path = this.getPath();
let bindings = new qxl.datagrid.binding.Bindings(model);
if (path) {
if (model) {
let bindingId = model.bind(path, widget, "value", this.getBindingOptions()(widget, model));
return new qxl.datagrid.binding.Bindings(model, bindingId);
bindings.add(model, bindingId);
}
}
return new qxl.datagrid.binding.Bindings(model);
if (typeof widget.setReadOnly == "function") {
const update = () => {
widget.setReadOnly(this.isEffectivelyReadOnly());
widget.setEnabled(this.isEffectivelyEnabled());
};

bindings.add(
this,
this.addListener("changeEffectivelyReadOnly", () => update()),
"listener"
);
bindings.add(
this,
this.addListener("changeEffectivelyEnabled", () => update()),
"listener"
);
update();
} else {
const update = () => {
widget.setEnabled(this.isEffectivelyEnabled() && !this.isEffectivelyReadOnly());
};

bindings.add(
this,
this.addListener("changeEffectivelyReadOnly", () => update()),
"listener"
);
bindings.add(
this,
this.addListener("changeEffectivelyEnabled", () => update()),
"listener"
);
update();
}
return bindings;
},

/**
Expand Down Expand Up @@ -152,8 +273,13 @@ qx.Class.define("qxl.datagrid.column.Column", {
_applyFlex(value) {},

/**
* Apply for `readOnly` property`
* Apply for `readOnly` property
*/
_applyReadOnly(value) {},

/**
* Apply for `enabled` property
*/
_applyReadOnly(value) {}
_applyEnabled(value) {}
}
});
20 changes: 20 additions & 0 deletions source/class/qxl/datagrid/column/toolbar/CellWidget.js
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,11 @@ qx.Class.define("qxl.datagrid.column.toolbar.CellWidget", {
}
},

/**
* Adds a button factory
*
* @param {qxl.datagrid.column.toolbar.Factory} factory
*/
_addButton(factory) {
let button = factory.createButton();
button.addListener("execute", () => {
Expand All @@ -71,6 +76,11 @@ qx.Class.define("qxl.datagrid.column.toolbar.CellWidget", {
this._add(button);
},

/**
* Removes a button factory
*
* @param {qxl.datagrid.column.toolbar.Factory} factory
*/
_removeButton(factory) {
let current = this.__buttonsByFactoryHash[factory.toHashCode()];
if (current) {
Expand All @@ -80,6 +90,16 @@ qx.Class.define("qxl.datagrid.column.toolbar.CellWidget", {
}
},

/**
* @Override
*/
_applyEnabled(value, oldValue) {
for (let btn of Object.values(this.__buttonsByFactoryHash)) {
btn.setEnabled(value);
}
return super._applyEnabled(value, oldValue);
},

/**
* Event handler for changes to the buttons array
*
Expand Down

0 comments on commit 7316b7d

Please sign in to comment.