Insert data to grid in acumatica - acumatica

I have a grid (show the devices) and action MATERIALS (a grid in a smart panel - show the materials of each device).
In an action Get Devices (code below), I want to load devices from another table to this grid also materials of each device to smart panel MATERIALS.
After the action is executed, just the devices are shown. The panel MATERIALS doesn't have any record, I try to press the Refresh button but there still doesn't have data.
The magic is that after I press Save button in the header, data in MATERIALS is shown correctly.
public PXAction<PSMTPhieuYeuCauSuaChuaMHTBHeader> GetDevices;
[PXUIField(DisplayName = "Get Devices")]
[PXButton(CommitChanges = true)]
protected void getDevices()
{
PSMTRequestRepairMaint thisGraph = PXGraph.CreateInstance<PSMTRequestRepairMaint>();
foreach (var record in PSMTPhieuYeuCauSuaChuaMMTBDeviceSelectedView.Cache.Updated)
{
PSMTPhieuYeuCauSuaChuaMMTBViewDevice device = (PSMTPhieuYeuCauSuaChuaMMTBViewDevice)record;
if (device.Check.HasValue && device.Check.Value)
{
PSMTPhieuYeuCauSuaChuaMMTBLineGrid line = (PSMTPhieuYeuCauSuaChuaMMTBLineGrid)thisGraph.PSMTPhieuYeuCauSuaChuaMMTBLineGridView.Cache.CreateInstance();
line = PSMTPhieuYeuCauSuaChuaMMTBLineGridView.Insert(line);
line.DeviceID = device.HeaderID;
line.FromDate = device.LastMaintenanceDate;
line.ToDate = device.LastMaintenanceDate;
device.Check = false;
line = PSMTPhieuYeuCauSuaChuaMMTBLineGridView.Update(line);
var materials = PXSelect<PSMTAllowedReplacementMaterial,
Where<PSMTAllowedReplacementMaterial.headerID,
Equal<Required<PSMTPhieuYeuCauSuaChuaMHTBHeader.soMay>>>>.Select(this, line.DeviceID);
foreach (var item in materials)
{
var allowedMaterial = (PSMTAllowedReplacementMaterial)item;
PSMTPhieuYeuCauSuaChuaMMTBMaterial material = (PSMTPhieuYeuCauSuaChuaMMTBMaterial)thisGraph.PSMTPhieuYeuCauSuaChuaMMTBMaterialView.Cache.CreateCopy(new PSMTPhieuYeuCauSuaChuaMMTBMaterial());
material = PSMTPhieuYeuCauSuaChuaMMTBMaterialView.Insert(material);
//material.LineGridID = line.GridID;
material.MaterialID = allowedMaterial.MaterialID;
material.Quantity = allowedMaterial.Quantity;
material = PSMTPhieuYeuCauSuaChuaMMTBMaterialView.Update(material);
}
}
}
}
Grid
Panel

Related

how to query exo trackselector in seperate dialog like video and audio in seperate dialog

I want to query exo quality dialog or default dialog in different dialog. like when user press setting button it will load only video or quality list if they press subtitle button that query only available subtitle and same way for audio track.
is there any possibilities to so this
current implementation
MappingTrackSelector.MappedTrackInfo mappedTrackInfo = trackSelector.getCurrentMappedTrackInfo();
if (mappedTrackInfo != null) {
CharSequence title = "Video";
int rendererIndex = 0;
int rendererType = mappedTrackInfo.getRendererType(rendererIndex);
boolean allowAdaptiveSelections = rendererType == C.TRACK_TYPE_VIDEO && mappedTrackInfo.getTypeSupport(C.TRACK_TYPE_VIDEO) == MappingTrackSelector.MappedTrackInfo.RENDERER_SUPPORT_NO_TRACKS;
TrackSelectionDialog trackSelectionDialog = TrackSelectionDialog.createForPlayer(simpleExoPlayer,
/* onDismissListener= */ dismissedDialog -> isShowingTrackSelectionDialog = false);
trackSelectionDialog.show(getSupportFragmentManager(), /* tag= */ null);

Why doesn't my BLC 'save' action save all records unless its at the very end of the cache insert?

I have BLC code that is parsing out the AuditHistory 'ModifiedFields' field so that I have multiple lines with separate 'Field' and 'Value' fields. The 'ModifiedFields' field contains null separated values, so my BLC C# code uses the split function to put these into an array. This all works fine. The problem I'm having is saving to a table in Acumatica via the Graph / Cache 'insert' function. If I use the 'Actions.PressSave()' method after every iteration of the array, it doesn't save every record - effectively skipping records. I have no idea why this would happen. If I put the 'Actions.PressSave()' method at the very end of everything, I get all the records - but sometimes it times out, I'm assuming because of (in some cases) the massive amount of records being cached before the save.
Putting the PressSave method at ANY other point in the loop(s) results in missed records.
Here is my BLC code (note the several places I placed the PressSave method for testing, but commented out - leaving the last one):
public PXAction<AUAuditSetup> CreateAuditRecords;
[PXProcessButton]
[PXUIField(DisplayName = "Create Audit Records", MapEnableRights = PXCacheRights.Update, MapViewRights = PXCacheRights.Update)]
protected virtual IEnumerable createAuditRecords(PXAdapter adapter)
{
PXLongOperation.StartOperation(Base, delegate ()
{
//Create graph of TAC screen...
var osdm = PXGraph.CreateInstance<OpenSourceDataMaint>();
xTACOpenSourceDetail osd;
int recordID = 1;
//Get records from AuditHistory
//PXResultset<AuditHistory> res = PXSelect<AuditHistory>.Select(Base);
PXResultset<AuditHistory> res = PXSelect<AuditHistory,
Where<AuditHistory.changeDate, GreaterEqual<Required<AuditHistory.changeDate>>>>.Select(Base, Convert.ToDateTime("01/01/2013"));
var companyID = Convert.ToString(PX.Common.PXContext.GetSlot<int?>("singleCompanyID"));
foreach (PXResult<AuditHistory> rec in res)
{
var ah = (AuditHistory)rec;
if (ah != null)
{
string[] fields = ah.ModifiedFields.Split('\0');
for (int i = 0; i < fields.GetUpperBound(0); i+=2)
{
osd = new xTACOpenSourceDetail();
osd.OpenSourceName = "AuditHistoryTable";
osd.DataID = "1";
osd.String01 = Convert.ToString(PX.Common.PXContext.GetSlot<int?>("singleCompanyID"));
osd.Number01 = ah.BatchID;
osd.Number02 = ah.ChangeID;
osd.Number03 = recordID;
osd.String02 = ah.ScreenID;
osd.String03 = Convert.ToString(ah.UserID);
osd.Date01 = ah.ChangeDate;
osd.String04 = ah.Operation;
osd.String05 = ah.TableName;
osd.String06 = ah.CombinedKey;
osd.String07 = fields[i];
osd.String08 = fields[i + 1];
osd.String09 = Convert.ToString(ah.ChangeDate);
osdm.OpenSourceDataDetail.Insert(osd);
//if (osd != null)
//osdm.Actions.PressSave();
recordID++;
}
recordID = 1;
//osdm.Actions.PressSave();
}
//osdm.Actions.PressSave();
}
osdm.Actions.PressSave();
});
return adapter.Get();
}
Any ideas?
A couple of things you could try:
Instead of instantiating osd directly, replace with:
osd = osdm.OpenSourceDataDetail.Insert();
and then after assigning values and prior to PressSave(), use .Update on the cache:
osdm.OpenSourceDataDetail.Update(osd);
and then after PressSave(), clear the graph:
osdm.Clear();
Importantly, does your DAC have an IsKey = true on the DataID field and marked PXDBIdentity, hence auto-assigned and unique?
Example:
public abstract class dataID : PX.Data.IBqlField {}
[PXDBIdentity(IsKey = true)]
[PXUIField(Visible = false, Enabled = false)]
public virtual int? DataID {get; set;}
If the changes are successful, you could then try moving the .PressSave() and .Clear() after the For loop.

How to programmatically create and confirm shipment for an order using ADD Order popup?

I am trying to create and confirm shipment programmatically for a single order. But I am stuck on how to select all the lines that are displayed on ADD Order popup for adding SOLines on Shipments screen. Any help on this?
string operation = SOOperation.Issue;
SOShipmentEntry shipmentGraph = PXGraph.CreateInstance<SOShipmentEntry>();
BAccountR customer = null;
INSite warehouse = null;
PXResultset<SOOrder> objSOOrder = PXSelect<SOOrder, Where<SOOrder.customerRefNbr, Equal<Required<SOImportFilter.referenceID>>>>.Select(this, currentFilter.ReferenceID);
foreach(SOOrder order in objSOOrder)
{
shipmentGraph.Clear();
var shipment = shipmentGraph.Document.Insert();
customer = (BAccountR)PXSelect<BAccountR,
Where<BAccountR.bAccountID, Equal<Required<BAccountR.bAccountID>>>>
.SelectSingleBound(shipmentGraph, new object[] { }, order.CustomerID);
shipment.CustomerID = customer.BAccountID;
shipment = shipmentGraph.Document.Update(shipment);
warehouse = (INSite)PXSelect<INSite,
Where<INSite.siteID, Equal<Required<INSite.siteID>>>>
.SelectSingleBound(shipmentGraph, new object[] { }, "159");
shipment.SiteID = warehouse.SiteID;
shipment = shipmentGraph.Document.Update(shipment);
var addorder = shipmentGraph.addsofilter.Insert();
addorder.Operation = operation;
addorder = shipmentGraph.addsofilter.Update(addorder);
addorder.OrderType = order.OrderType;
addorder = shipmentGraph.addsofilter.Update(addorder);
addorder.OrderNbr = order.OrderNbr;
addorder = shipmentGraph.addsofilter.Update(addorder);
foreach (PXResult<SOShipmentPlan, SOLineSplit, SOLine> plan in
shipmentGraph.soshipmentplan.Select())
{
SOShipmentPlan shipmentPlan = (SOShipmentPlan)plan;
shipmentPlan.Selected = true;
shipmentGraph.soshipmentplan.Update(plan);
shipmentGraph.Actions.PressSave();
}
shipmentGraph.Actions.PressSave();
}
I have difficulty understanding the feature you are trying to implement from the description. Usually you would automate CreateShipment and ConfirmShipment actions to do this.
Perhaps you have to handle a special case, if all that is blocking you is selecting the data from the grid inside the "Add Order" smart panel:
Using Inspect Element feature, determine the name of the DataView you target by clicking on the grid:
Use View Business Logic Source to look up the DataView source code:
From the source code for that DataView, we see that it returns 3 DAC (SOShipmentPlan, SOLineSplit and SOLine):
PXSelectJoinOrderBy<SOShipmentPlan,
InnerJoin<SOLineSplit, On<SOLineSplit.planID, Equal<SOShipmentPlan.planID>>,
InnerJoin<SOLine, On<SOLine.orderType, Equal<SOLineSplit.orderType>, And<SOLine.orderNbr, Equal<SOLineSplit.orderNbr>, And<SOLine.lineNbr, Equal<SOLineSplit.lineNbr>>>>>>,
OrderBy<Asc<SOLine.sortOrder, Asc<SOLine.lineNbr, Asc<SOLineSplit.lineNbr>>>>> soshipmentplan;
With that information we can now iterate the DataView using the Select method:
foreach (PXResult<SOShipmentPlan, SOLineSplit, SOLine> plan in Base.soshipmentplan.Select())
{
SOShipmentPlan shipmentPlan = (SOShipmentPlan)plan;
SOLineSplit lineSplit = (SOLineSplit)plan;
SOLine line = (SOLine)plan;
}
I used Base member to reference SOShipmentEntry graph in order to get the DataView. This should be used when you are in the context of a SOShipmentEntry graph extension:
Base.soshipmentplan.Select()
If you have a direct reference to SOShipmentEntry graph instead you can use that directly:
SOShipmentEntry shipmentEntry = PXGraph.CreateInstance<SOShipmentEntry>();
shipmentEntry.soshipmentplan.Select()
EDIT
Code for automating the Add Order dialog:
shipmentEntry.addsofilter.Current.OrderType = SOOrderTypeConstants.SalesOrder;
shipmentEntry.addsofilter.Current.OrderNbr = "000001";
shipmentEntry.addsofilter.Update(shipmentEntry.addsofilter.Current);
foreach (SOShipmentPlan line in shipmentEntry.soshipmentplan.Select())
{
line.Selected = true;
shipmentEntry.soshipmentplan.Update(line);
}
shipmentEntry.addSO.Press();

How do I get an object from an observable item Collection by index?

I need to get the object in an observable collection by index to access a property of the item at that index.
This is a snippet of the code:
public ObservableCollection<TipsModel> TipObjects;
private void LoadContent()
{
TipObjects = new ObservableCollection<TipsModel>();
for (int i = 0; i < 5; i++)
{
TipsModel item = new TipsModel()
{
Image = ImageSource.FromFile("nonindustryIcon.png"),
Title = "Kill energy vampires and save up to $100 a year",
Text = "Seventy-five percentof the electrical use by home electronics occurs when they're at home. \n People not at home means no electricity. Do not stay at home. Go stay on the streets. ",
};
TipObjects.Add(item);
}
foreach (TipsModel item in TipObjects)
{
img = item.Image;
tipTitle = item.Title;
tip = item.Text;
item.Content = CreateContent();
}
slideView.ItemsSource = TipObjects;
}
private void slideView_SlidedToIndex(object sender, Telerik.XamarinForms.Primitives.SlideView.SlideViewSlidedToIndexEventArgs e)
{
var slideId = slideView.Id;
//TipsModel tip = TipObjects.item at index[18];
}
You can just normally do
var tip = TipObjects[18];
Observable collection is just a normal, fully functional collection that supports indexing.
Alternatively you can use the Items property as well. Both approaches are equivalent:
var tip = TipObjects.Items[18];

How to get drives( 'C' or 'E' or 'F' )available in a system?

I am developing an Bootstrapper application. When we move to the installation location selection wizard, we can have a browse option to change the location of our setup installation.
When we clock that browse option, i need to show only the drives( 'C', 'D' and 'F') available in a system. When we select the drive, it will not expand. i need that drive alone (Ex: C:) in the installation location text in the installation wizard.
Can anyone please guide me that how to achieve my requirement?
My code:
private void btn_Browse_Click(object sender, EventArgs e)
{
txt_InstallLocation.Focus();
FBD_Source.RootFolder = Environment.SpecialFolder.Desktop;
if (FBD_Source.ShowDialog() == DialogResult.OK)
{
txt_InstallLocation.TextBox.Text = FBD_Source.SelectedPath;
BA.Model.Bootstrapper.Engine.StringVariables["APPDIR"] = FBD_Source.SelectedPath + "\\";
}
}
I need to modify the below line of code.
FBD_Source.RootFolder = Environment.SpecialFolder.Desktop;
Can anyone please assist me to proceed further or direct me in right path?
Your can find the available drives like this.
var drives = System.Environment.GetLogicalDrives();
foreach (string d in drives)
Console.WriteLine(d);
Don't use the FolderBrowserDialog.
Create a form with a dynamically created radiobutton/list and make the user select one of those options
Something like this
var drives = System.Environment.GetLogicalDrives();
Form selectionForm = new Form() { MaximizeBox = false, FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog, StartPosition = FormStartPosition.CenterScreen };
ListBox lb = new ListBox() { Dock = DockStyle.Fill };
foreach (var item in drives)
lb.Items.Add(item);
selectionForm.Controls.Add(lb);
Button btnOk = new Button() { Dock = DockStyle.Left, Width = selectionForm.Width / 2 };
btnOk.Text = "OK";
Button btnCancel = new Button() { Dock = DockStyle.Right, Width = selectionForm.Width / 2 };
btnCancel.Text = "Cancel";
Panel bottomPanel = new Panel() { Dock = DockStyle.Bottom, Height = 50 };
bottomPanel.Controls.Add(btnOk);
bottomPanel.Controls.Add(btnCancel);
selectionForm.Controls.Add(bottomPanel);
selectionForm.ShowDialog();
MessageBox.Show(lb.SelectedItem.ToString());

Resources