summaryrefslogtreecommitdiff
path: root/fxjs/xfa/cjx_instancemanager.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'fxjs/xfa/cjx_instancemanager.cpp')
-rw-r--r--fxjs/xfa/cjx_instancemanager.cpp119
1 files changed, 117 insertions, 2 deletions
diff --git a/fxjs/xfa/cjx_instancemanager.cpp b/fxjs/xfa/cjx_instancemanager.cpp
index 23048f98a5..86f8cf3e88 100644
--- a/fxjs/xfa/cjx_instancemanager.cpp
+++ b/fxjs/xfa/cjx_instancemanager.cpp
@@ -6,6 +6,7 @@
#include "fxjs/xfa/cjx_instancemanager.h"
+#include <algorithm>
#include <vector>
#include "fxjs/cfxjse_engine.h"
@@ -31,6 +32,90 @@ CJX_InstanceManager::CJX_InstanceManager(CXFA_InstanceManager* mgr)
CJX_InstanceManager::~CJX_InstanceManager() {}
+int32_t CJX_InstanceManager::SetInstances(int32_t iDesired) {
+ CXFA_OccurData occurData(GetXFANode()->GetOccurNode());
+ if (iDesired < occurData.GetMin()) {
+ ThrowTooManyOccurancesException(L"min");
+ return 1;
+ }
+
+ int32_t iMax = occurData.GetMax();
+ if (iMax >= 0 && iDesired > iMax) {
+ ThrowTooManyOccurancesException(L"max");
+ return 2;
+ }
+
+ int32_t iCount = GetXFANode()->GetCount();
+ if (iDesired == iCount)
+ return 0;
+
+ if (iDesired < iCount) {
+ WideString wsInstManagerName = GetCData(XFA_Attribute::Name);
+ WideString wsInstanceName = WideString(
+ wsInstManagerName.IsEmpty()
+ ? wsInstManagerName
+ : wsInstManagerName.Right(wsInstManagerName.GetLength() - 1));
+ uint32_t dInstanceNameHash =
+ FX_HashCode_GetW(wsInstanceName.AsStringView(), false);
+ CXFA_Node* pPrevSibling =
+ iDesired == 0 ? GetXFANode() : GetXFANode()->GetItem(iDesired - 1);
+ while (iCount > iDesired) {
+ CXFA_Node* pRemoveInstance =
+ pPrevSibling->GetNodeItem(XFA_NODEITEM_NextSibling);
+ if (pRemoveInstance->GetElementType() != XFA_Element::Subform &&
+ pRemoveInstance->GetElementType() != XFA_Element::SubformSet) {
+ continue;
+ }
+ if (pRemoveInstance->GetElementType() == XFA_Element::InstanceManager) {
+ NOTREACHED();
+ break;
+ }
+ if (pRemoveInstance->GetNameHash() == dInstanceNameHash) {
+ GetXFANode()->RemoveItem(pRemoveInstance, true);
+ iCount--;
+ }
+ }
+ } else {
+ while (iCount < iDesired) {
+ CXFA_Node* pNewInstance = GetXFANode()->CreateInstance(true);
+ GetXFANode()->InsertItem(pNewInstance, iCount, iCount, false);
+ iCount++;
+ CXFA_FFNotify* pNotify = GetDocument()->GetNotify();
+ if (!pNotify)
+ return 0;
+
+ pNotify->RunNodeInitialize(pNewInstance);
+ }
+ }
+
+ CXFA_LayoutProcessor* pLayoutPro = GetDocument()->GetLayoutProcessor();
+ if (pLayoutPro) {
+ pLayoutPro->AddChangedContainer(
+ ToNode(GetDocument()->GetXFAObject(XFA_HASHCODE_Form)));
+ }
+ return 0;
+}
+
+int32_t CJX_InstanceManager::MoveInstance(int32_t iTo, int32_t iFrom) {
+ int32_t iCount = GetXFANode()->GetCount();
+ if (iFrom > iCount || iTo > iCount - 1) {
+ ThrowIndexOutOfBoundsException();
+ return 1;
+ }
+ if (iFrom < 0 || iTo < 0 || iFrom == iTo)
+ return 0;
+
+ CXFA_Node* pMoveInstance = GetXFANode()->GetItem(iFrom);
+ GetXFANode()->RemoveItem(pMoveInstance, false);
+ GetXFANode()->InsertItem(pMoveInstance, iTo, iCount - 1, true);
+ CXFA_LayoutProcessor* pLayoutPro = GetDocument()->GetLayoutProcessor();
+ if (pLayoutPro) {
+ pLayoutPro->AddChangedContainer(
+ ToNode(GetDocument()->GetXFAObject(XFA_HASHCODE_Form)));
+ }
+ return 0;
+}
+
CJS_Return CJX_InstanceManager::moveInstance(
CJS_V8* runtime,
const std::vector<v8::Local<v8::Value>>& params) {
@@ -39,7 +124,7 @@ CJS_Return CJX_InstanceManager::moveInstance(
int32_t iFrom = runtime->ToInt32(params[0]);
int32_t iTo = runtime->ToInt32(params[1]);
- InstanceManager_MoveInstance(iTo, iFrom);
+ MoveInstance(iTo, iFrom);
CXFA_FFNotify* pNotify = GetDocument()->GetNotify();
if (!pNotify)
@@ -100,7 +185,7 @@ CJS_Return CJX_InstanceManager::setInstances(
if (params.size() != 1)
return CJS_Return(JSGetStringFromID(JSMessage::kParamError));
- InstanceManager_SetInstances(runtime->ToInt32(params[0]));
+ SetInstances(runtime->ToInt32(params[0]));
return CJS_Return(true);
}
@@ -180,3 +265,33 @@ CJS_Return CJX_InstanceManager::insertInstance(
return CJS_Return(value->DirectGetValue().Get(runtime->GetIsolate()));
}
+
+void CJX_InstanceManager::max(CFXJSE_Value* pValue,
+ bool bSetting,
+ XFA_Attribute eAttribute) {
+ if (bSetting) {
+ ThrowInvalidPropertyException();
+ return;
+ }
+ pValue->SetInteger(CXFA_OccurData(GetXFANode()->GetOccurNode()).GetMax());
+}
+
+void CJX_InstanceManager::min(CFXJSE_Value* pValue,
+ bool bSetting,
+ XFA_Attribute eAttribute) {
+ if (bSetting) {
+ ThrowInvalidPropertyException();
+ return;
+ }
+ pValue->SetInteger(CXFA_OccurData(GetXFANode()->GetOccurNode()).GetMin());
+}
+
+void CJX_InstanceManager::count(CFXJSE_Value* pValue,
+ bool bSetting,
+ XFA_Attribute eAttribute) {
+ if (bSetting) {
+ pValue->SetInteger(GetXFANode()->GetCount());
+ return;
+ }
+ SetInstances(pValue->ToInteger());
+}