Smart table's property initiallyVisibleFields + ODataModel - sapui5

I used SmartTable with the property initiallyVisibleFields. I bound ODataModel to it. The problem is when I want to show all fields of ODataModel, e.g. after I click on SmartTable's row and try to display it in the dialog. I just see fields from initiallyVisibleFields property. It looks like ODataModel is filtered with initiallyVisibleFields property.
I was thinking about JSONModel where I put copy of ODataModel before it is bind to SmartTable, but I am planning to use SmartFilterBar, so index of shown data in the table will be changed after filtering. So I can not simply pull data from JSONModel. I can still filter data from JSONModel based on the fields I get from
ODataModel filtered with initiallyVisibleFields but there I can still get different data, because there can be differences in the fields which are hidden.
Please, can you advice me how to solve this issue?
Thanks for any tips.
...
return Controller.extend("ABC.View1", {
oDialog: null,
onInit: function() {
var oModel, oView;
oModel = new ODataModel("/sap/opu/odata/sap/ABC/", {
useBatch: false
});
oView = this.getView();
oView.setModel(oModel);
this._createSmartTable();
},
_createSmartTable: function() {
var oSmartTable = new SmartTable('idSmartTable',{
entitySet: "ABCListSet",
tableType: "ResponsiveTable",
sStyleClass: "sapUiResponsiveContentPadding",
initiallyVisibleFields: "A,B,C,D",
showRowCount: false,
enableAutoBinding: true,
demandPopin: false,
useVariantManagement: false,
useExportToExcel: false,
useTablePersonalisation: true,
});
// Register event row click
var that = this;
var oTable = oSmartTable.getTable();
oSmartTable.attachDataReceived(function() {
var aItems = oTable.getItems();
if (aItems.length === 0) return;
$.each(aItems, function(oIndex, oItem) {
oItem.detachPress(that._createDialog);
oItem.setType("Active");
oItem.attachPress(that._createDialog);
});
});
var oVBox = new VBox();
oVBox.addItem(oSmartTable);
var oPage = this.getView().byId("idPage");
oPage.addContent(oVBox);
},
_createDialog: function(oEvent) {
//HERE I the oEvent has data filtered by initiallyVisibleFields property of Smarttable.
},
});
...

Do I understand you correctly that you want to show the complete entry in a dialog? The SmartTable uses $select statements to only load the fields of an entity that are also shown in the table. If you want to load all, I think you should add them in the requestAtLeast property.

Related

sap.m.table multi checkbox make it READ ONLY - On Condition + SAP UI5

This is my first post to Stack, appreciate the work you guys do, amazing.
I have a sap.m.table sap ui5 and i have 4 records
out of 4, 2 are selected by default, i want to disable the preselected once based on condition.
I have tried below code but its not working, any input please?
View
/results' }" **mode="MultiSelect"**
Controller logic
//--->disable the selected department checkboxes
var tbl = that.getView().byId('idImpactTable');
var header = tbl.$().find('thead');
var selectAllCb = header.find('.sapMCb');
selectAllCb.remove();
tbl.getItems().forEach(function(r) {
var obj = r.getBindingContext("impactModel").getObject();
var oStatus = obj.COMPLETED;
var cb = r.$().find('.sapMCb');
var oCb = sap.ui.getCore().byId(cb.attr('id'));
if (oStatus === "X") {
oCb.setSelected(true);
oCb.setEnabled(false);
} else {
oCb.setEnabled(false);
}
});
Multiselect Mode Table - Make selected check box read only
Last time I tried this I found it easiest to use the updateFinished event on the table, and then use an internal property of the column list item, like so:
onTableUpdateFinished: function (oEvent) {
oEvent.getSource().getItems().forEach(function (item) {
var data = item.getBindingContext().getObject();
item._oMultiSelectControl.setEnabled(!data.IsEnabled); //whatever your check is
});
}
You'll have to find a way to keep them disabled though when using the Select All checkbox at the top of the table. I ended up extending sap.m.Table to accomplish that, there might be easier ways...
My extension is like this
sap.ui.define([
"sap/m/Table"
], function(Control) {
return Control.extend("myapp.controls.MyTable", {
updateSelectAllCheckbox: function(oEvent) {
if (this._selectAllCheckBox && this.getMode() === "MultiSelect") {
var aItems = this.getItems();
var iSelectedItemCount = this.getSelectedItems().length;
var iSelectableItemCount = aItems.filter(function(oItem) {
//standard table does not check if the item is enabled
return oItem.getSelected() || oItem._oMultiSelectControl.getEnabled();
}).length;
// set state of the checkbox by comparing item length and selected item length
this._selectAllCheckBox.setSelected(aItems.length > 0 && iSelectedItemCount === iSelectableItemCount);
}
}
});
});
And just the standard renderer
sap.ui.define([
"sap/m/TableRenderer"
], function(Control) {
return Control.extend("myapp.controls.MyTableRenderer", {
});
});
I suppose I could have extended the ColumnListItem but that was more effort than I wanted to put into the table extension
I have managed to find the solution, please find sample code to achieve.
//--->disable the selected department checkboxes
var tbl = that.getView().byId("idImpactTable");
var header = tbl.$().find("thead");
var selectAllCb = header.find(".sapMCb");
selectAllCb.remove();
var aItems = that.byId("idImpactTable").getItems();
//---> Check individual item property value and select the item
aItems.forEach(function(oItem) {
debugger;
//---> If using OData Model items Binding, get the item object
var mObject = oItem.getBindingContext().getObject();
var sPath = oItem.getBindingContextPath();
var completed = oItem.oBindingContexts.impactModel.getProperty("COMPLETED");
//--->get the id of Multi Checkbox
var cb = oItem.$().find(".sapMCb");
var oCb = sap.ui.getCore().byId(cb.attr("id"));
if (completed === "X") {
oCb.setEditable(false);
oItem.setSelected(true);
oItem.getCells()[4].setEnabled(false);
} else {
oItem.setSelected(false);
}
});
Thank you,
Jacob.Kata
//--->disable the selected department checkboxes
var tbl = that.getView().byId('idImpactTable');
tbl.getItems().forEach(function(r) {
// this makes the trick --->
var oMultiSelCtrl = r.getMultiSelectControl();
oMultiSelCtrl.setDisplayOnly( true );
});

In SAPUI5 SmartTable on event beforeRebindTable adding some filters

My requiremnt is to put some filters on smartTable form my controller.
In Event beforeRebindTable i am using the following code to put filter using this code which is working fine.
onBeforeRebindTable: function (oEvent) {
var oBindingParams = oEvent.getParameter("bindingParams");
statFilter = new sap.ui.model.Filter("Claim_TYPE", "EQ", "1234");
oBindingParams.filters.push(statFilter);
}
But the problem is when the user is clicling on table column on filter again, the filter i am adding in above code is not visible in the selection dialog. User may need to delete this filter, If its not visible in dialog they wont be able to delete it.
I am not able to establish the link why the dialog is not getting updated, or should i add this somewhere else.
Thanks
Sonal.
onBeforeRebindTable: function (oEvent) {
var oSmartTable = oEvent.getSource();
if (this._isOnInit == null) this._isOnInit = true;
if (this._isOnInit) {
oSmartTable.applyVariant(
{
filter: {
filterItems: [{
columnKey: "YourSelectedColumn",
exclude: false,
operation: "EQ",
value1: "SomeEnteredValue",
value2: ""
}]
}
}
);
this._isOnInit = false;
}
}

add input row at the beginning ui5

I'm having problems concerning adding a row with input field to add item to the table. I'm trying to use this example
addEntry : function(oEvent) {
var path = oEvent.getSource().getBindingContext().getPath();
var obj = {
fname: null,
lname: null,
desc: null,
createNew: false,
removeNew: false,
saveNew: true
};
var oModel = this.getView().getModel();
oModel.setProperty(path, obj);
},
The only difference that i want is for the row to be visible from the start (without the + icon) so that the user can directly add fields and when OK is clicked, a new row needs to be added.
Thank you
You should remove the addEntry() function as it is just triggering from the Add Icon and instead create the object on your onInit() function.
It will look like this:
onInit : function() {
var dummyData = [{"fname": "",
"lname": "",
"desc": "",
"removeNew": false,
"saveNew": true}];
var oModel = new sap.ui.model.json.JSONModel({data : dummyData});
this.getView().setModel(oModel);
}
When you click on the save button, the saveEntry() function will be triggered and the new entry will be pushed to the model.
A new form will show up by calling the addEmptyObject() function at the end of it.
Here is a working example:
https://jsbin.com/wutefaz/edit?html,js,output

Binding/Displaying OData data in a sap.m.Table control

I'm running into issue binding OData in a table control and I'm hoping one of you experts can spare a millisecond to tell me where I'm screwing up.
I can get the OData info from the backend server - step one is I just want to display it in a table with columns and step two is to present users with a segmented button to enable/disable processing of a countries data. Lets just get the data displayed now.
Here is the OData that is returned from the backed
backend odata
Here is my createContent code - I want to do it in JavaScript:
var oTable = new Table({
height: '100%',
firstVisibleRow: 0,
visibleRowCountMode: sap.ui.table.VisibleRowCountMode.Auto,
selectionMode: sap.ui.table.SelectionMode.None,
selectionBehavior: sap.ui.table.SelectionBehavior.RowOnly
}).addStyleClass('suggCompTableStyle');
var oColName = new sap.ui.table.Column().setLabel('{i18n>txt_countryName}').bindElement("/data>LANDX");
oTable.addColumn(oColName);
var oModel = sap.ui.getCore().getModel();
oModel.callFunction("/getCountryActiveList",
"GET",
{SPRAS: 'E'},
null,
function(oData, oResponse)
{ oTable.setModel( new sap.ui.model.json.JSONModel({data : oData.results}));
oTable.bindRows("/data");
alert("ok"); },
function(oError) {alert("err"); });
/* eslint-enable no-alert */
oTable.placeAt("content");
var oPage = new sap.m.Page({
title: "{i18n>title}",
content: [
oTable
]
});
var app = new sap.m.App("myApp", {
initialPage: "oPage"
});
app.addPage(oPage);
return app;
}/* end createContent function */
My table is created with the correct number of rows but not displaying the column data. I guess I'm confused on how to bind the column data?
Thanks for the assistance.
Steve
The issue is in your binding oTable.bindRows("/data");.
The bindRows method is expecting a row template control of the type sap.ui.table.Row.
You can look into https://sapui5.hana.ondemand.com/#/api/sap.ui.base.ManagedObject/methods/bindAggregation for more information. The bindRows method expects an input parameter equal to the oBindingInfo of the bindAggregation method from the link I above.

How to get the data of a view

I´m using SAPUI5, I have a MasterPage and a DetailPage, in the MasterPage I have a List and when I select de Item in the List the information is displayed in the DetailPage.
In the DetailPage I have a PositiveAction, When I press the PositiveAction I need to get the Data of the DetailPage but I don't know how to do this.
My code of the Item Press
onPoSelect : function(oEvent) {
var oListItem = oEvent.getParameter('listItem');
var oRouter = sap.ui.core.UIComponent.getRouterFor(this);
oRouter.navTo("DetailPanel", {
invoicePath: oListItem.getBindingContext("solped").getPath().substr(1)
});
},
My code in the DetailPanel
onInit: function (){
var oRouter = sap.ui.core.UIComponent.getRouterFor(this);
oRouter.getRoute("DetailPanel").attachPatternMatched(this._onObjectMatched, this);
},
_onObjectMatched: function (oEvent) {
this.getView().bindElement({
path: "/" + oEvent.getParameter("arguments").invoicePath,
model: "solped"
});
},
The line "oEvent.getParameter("arguments").invoicePath,"
returns this.
Invoices(CustomerName='Alfreds Futterkiste',Discount=0f,OrderID=10702,ProductID=3,ProductName='Aniseed Syrup',Quantity=6,Salesperson='Margaret Peacock',ShipperName='Speedy Express',UnitPrice=10.0000M)
I have the information but it is a String, How can I convert this String in an Object? Or, how else can I access the information in the view?
The image of the View
enter image description here
I assume you can already see the data of the detail in your Detail view.
You binded the data to the view by bindElement function and to retrieve them back in the code you are looking for "getBindingContext" function.
Create following function in your Detail controller:
// this must be connected to Button -> <Button press="onPositivePress">
onPositivePress: function(oEvent) {
var oBindingContext = this.getView().getBindingContext("solped");
// this is the path you can use to call odata service
var sPath = oBindingContext.getPath();
// this is data you are looking for
var oReqData = oBindingContext.getObject();
}
You can get all the properties as an object by passing the binding path as an argument to the getProperty function of the underlying Data model.
var oModel = this.getView().getModel("solped");
var oProps = oModel.getProperty(oListItem.getBindingContext("solped").getPath());
You can then access these properties as
oProps.CustomerName;
oProps.OrderID;
...
for converting string to object see below example.
var a = "how r u";
var b = [a];
you will get object of a in b.