From a492088913229e4ac59a50a05638d5568857b03e Mon Sep 17 00:00:00 2001 From: mathis Date: Mon, 9 Oct 2023 17:45:54 +0200 Subject: [PATCH] deleted precompiled rules++ --- rules++/base.p | 70 - rules++/base.r | 3515 ------------------------------------------------ rules++/rpp | Bin 8808864 -> 0 bytes 3 files changed, 3585 deletions(-) delete mode 100644 rules++/base.p delete mode 100644 rules++/base.r delete mode 100755 rules++/rpp diff --git a/rules++/base.p b/rules++/base.p deleted file mode 100644 index 2bb5754..0000000 --- a/rules++/base.p +++ /dev/null @@ -1,70 +0,0 @@ - -/////////////////////////////////////// -// presets -/////////////////////////////////////// -/****************************************************************************** - -*/ -preset Clear() - - OverrideLayer(); - Insert(0); -end - - - -preset FillObjects(array object aObjects) - -// - if (s:debug) - if (aObjects.count == 0) - warning("preset.FillObjects(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return; - end - end -// - - for (i = 0 to aObjects.last) - coord cAnchor = aObjects[i].anchor; - - for (j = 0 to aObjects[i].last) - coord cRelativePos = util:RelativePos(cAnchor, aObjects[i][j]); - - Insert(aObjects[i][j]).If( - IndexAt([cRelativePos.x * -1, cRelativePos.y * -1]).Is(cAnchor) - ).NoDefaultPosRule(); - end - end -end - - - -preset Checkerboard(int iIndex1, int iIndex2) - -// - if (s:debug) - if (iIndex1 < 0 or iIndex1 > 255) - warning("preset.Checkerboard(int " + iIndex1.name() + ", int " + iIndex2.name() + ") -> " + iIndex1.name() + " needs to be in range [0-255]."); - return; - end - - if (iIndex2 < 0 or iIndex2 > 255) - warning("preset.Checkerboard(int " + iIndex1.name() + ", int " + iIndex2.name() + ") -> " + iIndex2.name() + " needs to be in range [0-255]."); - return; - end - end -// - - OverrideLayer(); - Insert(iIndex1); - Insert(g:mask).If( - IndexAt([0, 0]).IsEmpty(), IndexAt([-1, 0], [0, -1]).IsNot(g:mask, iIndex2) - ); - Insert(iIndex2).If( - IndexAt([0, 0]).Is(iIndex1), IndexAt([-1, 0], [0, -1]).IsNot(g:mask, iIndex2) - ); - - NewRun(); - OverrideLayer(); - Replace(g:mask, 0); -end diff --git a/rules++/base.r b/rules++/base.r deleted file mode 100644 index e904f5e..0000000 --- a/rules++/base.r +++ /dev/null @@ -1,3515 +0,0 @@ - -/////////////////////////////////////// -// global variables (internal) -/////////////////////////////////////// -/****************************************************************************** - -*/ -// value holders -int g:vInsertIndex = 0; -object g:vInsertObject; - -array int g:vTestIndices; - -// values -int g:intMax = 2147483647; -int g:intMin = -2147483648; - -int g:and = 0; -int g:or = 1; -int g:group = 0; -int g:mask = 255; - - - -/////////////////////////////////////// -// settings -/////////////////////////////////////// -/****************************************************************************** - -*/ -bool s:debug = true; - - - -/////////////////////////////////////// -// -int top = 1000; -int right = 1001; -int bottom = 1002; -int left = 1003; -int topLeft = 1004; -int topRight = 1005; -int bottomLeft = 1006; -int bottomRight = 1007; -int all = 1008; -/////////////////////////////////////// -// utility functions -/////////////////////////////////////// -/****************************************************************************** - -*/ -function->array bool util:ArrayBool(array bool aValues) - - return aValues; -end - - - -function->array int util:ArrayInt(array int aValues) - - return aValues; -end - - - -function->array coord util:ArrayCoord(array coord aValues) - - return aValues; -end - - - -function->array range util:ArrayRange(array range aValues) - - return aValues; -end - - - -function->array float util:ArrayFloat(array float aValues) - - return aValues; -end - - - -function->array string util:ArrayString(array string aValues) - - return aValues; -end - - - -function->array object util:ArrayObject(array object aValues) - - return aValues; -end - - - -function->int util:RemoveRotation(int iIndex) - - float fIndex = iIndex; - return fIndex; -end - - - -function->array int util:RemoveRotation(array int aIndices) - - array int aResult; - if (aIndices.count != 0) - for (i = 0 to aIndices.last) - aResult.push(util:RemoveRotation(aIndices[i])); - end - end - return aResult; -end - - - -function->int util:N(int iIndex) - - return iIndex.N; -end - - - -function->array int util:N(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].N); - end - end - return aResult; -end - - - -function->object util:N(object oObject) - - return oObject.N; -end - - - -function->array object util:N(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].N); - end - end - return aResult; -end - - - -function->int util:V(int iIndex) - - return iIndex.V; -end - - - -function->array int util:V(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].V); - end - end - return aResult; -end - - - -function->object util:V(object oObject) - - return oObject.V; -end - - - -function->array object util:V(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].V); - end - end - return aResult; -end - - - -function->int util:H(int iIndex) - - return iIndex.H; -end - - - -function->array int util:H(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].H); - end - end - return aResult; -end - - - -function->object util:H(object oObject) - - return oObject.H; -end - - - -function->array object util:H(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].H); - end - end - return aResult; -end - - - -function->int util:R(int iIndex) - - return iIndex.R; -end - - - -function->array int util:R(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].R); - end - end - return aResult; -end - - - -function->object util:R(object oObject) - - return oObject.R; -end - - - -function->array object util:R(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].R); - end - end - return aResult; -end - - - -function->int util:VH(int iIndex) - - return iIndex.VH; -end - - - -function->array int util:VH(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VH); - end - end - return aResult; -end - - - -function->object util:VH(object oObject) - - return oObject.VH; -end - - - -function->array object util:VH(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VH); - end - end - return aResult; -end - - - -function->int util:VR(int iIndex) - - return iIndex.VR; -end - - - -function->array int util:VR(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VR); - end - end - return aResult; -end - - - -function->object util:VR(object oObject) - - return oObject.VR; -end - - - -function->array object util:VR(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VR); - end - end - return aResult; -end - - - -function->int util:HR(int iIndex) - - return iIndex.HR; -end - - - -function->array int util:HR(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].HR); - end - end - return aResult; -end - - - -function->object util:HR(object oObject) - - return oObject.HR; -end - - - -function->array object util:HR(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].HR); - end - end - return aResult; -end - - - -function->int util:VHR(int iIndex) - - return iIndex.VHR; -end - - - -function->array int util:VHR(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VHR); - end - end - return aResult; -end - - - -function->object util:VHR(object oObject) - - return oObject.VHR; -end - - - -function->array object util:VHR(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - aResult.push(aArray[i].VHR); - end - end - return aResult; -end - - - -function->array int util:Rotations(int iIndex) - - array int aResult; - aResult.push(iIndex.N); - aResult.push(iIndex.R); - aResult.push(iIndex.VH); - aResult.push(iIndex.VHR); - return aResult; -end - - - -function->array int util:Rotations(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - int iIndex = aArray[i]; - aResult.push(iIndex.N); - aResult.push(iIndex.R); - aResult.push(iIndex.VH); - aResult.push(iIndex.VHR); - end - end - return aResult; -end - - - -function->array object util:Rotations(object oObject) - - array object aResult; - aResult.push(oObject.N); - aResult.push(oObject.R); - aResult.push(oObject.VH); - aResult.push(oObject.VHR); - return aResult; -end - - - -function->array object util:Rotations(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - object oObject = aArray[i]; - aResult.push(oObject.N); - aResult.push(oObject.R); - aResult.push(oObject.VH); - aResult.push(oObject.VHR); - end - end - return aResult; -end - - - -function->array int util:Mirrors(int iIndex) - - array int aResult; - aResult.push(iIndex.V); - aResult.push(iIndex.H); - aResult.push(iIndex.VR); - aResult.push(iIndex.HR); - return aResult; -end - - - -function->array int util:Mirrors(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - int iIndex = aArray[i]; - aResult.push(iIndex.V); - aResult.push(iIndex.H); - aResult.push(iIndex.VR); - aResult.push(iIndex.HR); - end - end - return aResult; -end - - - -function->array object util:Mirrors(object oObject) - - array object aResult; - aResult.push(oObject.V); - aResult.push(oObject.H); - aResult.push(oObject.VR); - aResult.push(oObject.HR); - return aResult; -end - - - -function->array object util:Mirrors(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - object oObject = aArray[i]; - aResult.push(oObject.V); - aResult.push(oObject.H); - aResult.push(oObject.VR); - aResult.push(oObject.HR); - end - end - return aResult; -end - - - -function->array int util:All(int iIndex) - - array int aResult; - aResult.push(iIndex.N); - aResult.push(iIndex.V); - aResult.push(iIndex.H); - aResult.push(iIndex.R); - aResult.push(iIndex.VH); - aResult.push(iIndex.VR); - aResult.push(iIndex.HR); - aResult.push(iIndex.VHR); - return aResult; -end - - - -function->array int util:All(array int aIndices) - - array int aResult; - - if (aIndices.count != 0) - array int aArray = aIndices.unique(); - - for (i = 0 to aArray.last) - int iIndex = aArray[i]; - aResult.push(iIndex.N); - aResult.push(iIndex.V); - aResult.push(iIndex.H); - aResult.push(iIndex.R); - aResult.push(iIndex.VH); - aResult.push(iIndex.VR); - aResult.push(iIndex.HR); - aResult.push(iIndex.VHR); - end - end - return aResult; -end - - - -function->array object util:All(object oObject) - - array object aResult; - aResult.push(oObject.N); - aResult.push(oObject.V); - aResult.push(oObject.H); - aResult.push(oObject.R); - aResult.push(oObject.VH); - aResult.push(oObject.VR); - aResult.push(oObject.HR); - aResult.push(oObject.VHR); - return aResult; -end - - - -function->array object util:All(array object aObjects) - - array object aResult; - - if (aObjects.count != 0) - array object aArray = aObjects.unique(); - - for (i = 0 to aArray.last) - object oObject = aArray[i]; - aResult.push(oObject.N); - aResult.push(oObject.V); - aResult.push(oObject.H); - aResult.push(oObject.R); - aResult.push(oObject.VH); - aResult.push(oObject.VR); - aResult.push(oObject.HR); - aResult.push(oObject.VHR); - end - end - return aResult; -end - - - -function->bool util:Is(int iIndex) - -// - if (s:debug) - if (iIndex < -1 or iIndex > 255) - error("util:Is(int " + iIndex.name() + ") -> " + iIndex.name() + " needs to be in range [-1-255]."); - end - end -// - - insert.rule.pos.type = index; - insert.rule.pos.index = iIndex; - - return true; -end - - - -function->bool util:Is(array int aIndices) - -// - if (s:debug) - if (aIndices.count == 0) - warning("util:Is(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < -1 or aIndices[i] > 255) - error("util:Is(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - insert.rule.pos.type = index; - for (i = 0 to aIndices.last) - insert.rule.pos.index = aIndices[i]; - end - return true; -end - - - -function->bool util:IsNot(int iIndex) - -// - if (s:debug) - if (iIndex < -1 or iIndex > 255) - error("util:IsNot(int " + iIndex.name() + ") -> " + iIndex.name() + " needs to be in range [-1-255]."); - end - end -// - - insert.rule.pos.type = notindex; - insert.rule.pos.index = iIndex; - - return true; -end - - - -function->bool util:IsNot(array int aIndices) - -// - if (s:debug) - if (aIndices.count == 0) - warning("util:IsNot(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < -1 or aIndices[i] > 255) - error("util:IsNot(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - insert.rule.pos.type = notindex; - for (i = 0 to aIndices.last) - insert.rule.pos.index = aIndices[i]; - end - return true; -end - - - -function->bool util:IsEmpty() - - insert.rule.pos.type = empty; - return true; -end - - - -function->bool util:IsFull() - - insert.rule.pos.type = full; - return true; -end - - - -function->bool util:IsOut() - - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - return true; -end - - - -function->bool util:IsNotOut() - - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - return true; -end - - - -function->null util:NewRule() - - insert.newrule; -end - - - -function->null util:NewPosRule(coord cPos) - - insert.rule.pos = cPos; -end - - - -function->null util:InsertIndex(int iIndex) - -// - if (s:debug) - if (iIndex < 0 or iIndex > 255) - error("util:InsertIndex(int " + iIndex.name() + ") -> value needs to be in range [0-255]."); - end - end -// - - insert.rule.index = iIndex; -end - - - -function->null util:NoDefaultPosRule() - - insert.rule.nodefault; -end - - - -function->null util:Chance(float fProbability) - - insert.rule.random = fProbability; -end - - - -function->array float util:CopiesOf(int iCopies, float fValue) - -// - if (s:debug) - if (iCopies < 1) - error("util:CopiesOf(int " + iCopies.name() + ", float " + fValue.name() + ") -> " + iCopies.name() + " needs to be greater than 0."); - end - end -// - - array float aResult; - for (i = 0 to iCopies - 1) - aResult.push(fValue); - end - return aResult; -end - - - -function->int util:Negate(int iValue) - - return iValue * -1; -end - - - -function->coord util:Negate(coord cValue) - - return [cValue.x * -1, cValue.y * -1]; -end - - - -function->coord util:RelativePos(coord cAnchor, int iIndex) - - coord cPos = iIndex; - - bool hasV = cAnchor.rotate.V; - bool hasH = cAnchor.rotate.H; - bool hasR = cAnchor.rotate.R; - - if (hasV and hasH and hasR) - return [cPos.y - cAnchor.y, cAnchor.x - cPos.x]; - end - if (hasV and hasH) - return [cAnchor.x - cPos.x, cAnchor.y - cPos.y]; - end - if (hasV and hasR) - return [cAnchor.y - cPos.y, cAnchor.x - cPos.x]; - end - if (hasH and hasR) - return [cPos.y - cAnchor.y, cPos.x - cAnchor.x]; - end - if (hasV) - return [cAnchor.x - cPos.x, cPos.y - cAnchor.y]; - end - if (hasH) - return [cPos.x - cAnchor.x, cAnchor.y - cPos.y]; - end - if (hasR) - return [cAnchor.y - cPos.y, cPos.x - cAnchor.x]; - end - - return [cPos.x - cAnchor.x, cPos.y - cAnchor.y]; -end - - - -function->bool util:Found(int iResult) - - return iResult != -1; -end - - - -function->int util:Min(array int aValues) - - if (aValues.count == 0) - return g:intMin; - end - - int iResult = g:intMax; - for (i = 0 to aValues.last) - if (aValues[i] < iResult) - iResult = aValues[i]; - end - end - return iResult; -end - - - -function->int util:Max(array int aValues) - - if (aValues.count == 0) - return g:intMax; - end - - int iResult = g:intMin; - for (i = 0 to aValues.last) - if (aValues[i] > iResult) - iResult = aValues[i]; - end - end - return iResult; -end - - - -function->array int util:Rect(object oObject) - -// - if (s:debug) - if (oObject.count == 0) - error("util:Rect(object " + oObject.name() + ") -> " + oObject.name() + " cannot be empty."); - end - end -// - - array int aX; - array int aY; - - coord cAnchor = oObject.anchor; - for (i = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[i]); - - aX.push(cRelativePos.x); - aY.push(cRelativePos.y); - end - - array int aResult; - aResult.push(0, util:Max(aX), util:Max(aY), util:Min(aX)); // top, right, bottom, left - - return aResult; -end - - - -function->coord util:Size(object oObject) - -// - if (s:debug) - if (oObject.count == 0) - error("util:Size(object " + oObject.name() + ") -> " + oObject.name() + " cannot be empty."); - end - end -// - - array int aRect = util:Rect(oObject); - return [aRect[1] - aRect[3] + 1, aRect[2] - aRect[0] + 1]; -end - - - -function->float util:SumOf(array float aValues) - -// - if (s:debug) - if (aValues.count == 0) - error("util:SumOf(array float " + aValues.name() + ") -> " + aValues.name() + " cannot be empty."); - end - end -// - - float fSum = 0.0; - for (i = 0 to aValues.last) - fSum = fSum + aValues[i]; - end - return fSum; -end - - - -function->array float util:Normalize(array float aValues, float fBound) - -// - if (s:debug) - if (aValues.count == 0) - error("util:Normalize(array float " + aValues.name() + ", float " + fBound.name() + ") -> " + aValues.name() + " cannot be empty."); - end - end -// - - float fFactor = fBound / util:SumOf(aValues); - - array float aResult; - for (i = 0 to aValues.last) - aResult.push(aValues[i] * fFactor); - end - return aResult; -end - - - -function->array float util:Unbias(array float aProbabilities) - -// - if (s:debug) - if (aProbabilities.count == 0) - error("util:Unbias(array float " + aProbabilities.name() + ") -> " + aProbabilities.name() + " cannot be empty."); - end - end -// - - float fSum = util:SumOf(aProbabilities); - - array float aClamped = aProbabilities; - if (fSum > 100.0) - aClamped = util:Normalize(aProbabilities, 100.0); - end - - float fRemaining = 100.0; - - array float aResult; - for (i = 0 to aClamped.last) - float fUnbiased = aClamped[i] / fRemaining * 100.0; - fRemaining = fRemaining - aClamped[i]; - aResult.push(fUnbiased); - end - return aResult; -end - - - -function->array float util:ToProbabilities(array float aPercents) - -// - if (s:debug) - if (aPercents.count == 0) - error("util:ToProbabilities(array float " + aPercents.name() + ") -> " + aPercents.name() + " cannot be empty."); - end - end -// - - array float aResult; - for (i = 0 to aPercents.last) - aResult.push(100.0 / aPercents[i]); - end - return aResult; -end - - - -function->int util:OppositeSide(int iSide) - -// - if (s:debug) - if (iSide < top or iSide > left) - error("util:OppositeSide(int " + iSide.name() + ") -> value needs to be top, right, bottom or left."); - end - end -// - - int iResult = iSide + 2; - if (iResult > left) - return iResult - 4; - end - return iResult; -end - - - - - -/////////////////////////////////////// -// -bool g:randomize = false; -bool g:roll = false; -bool g:hasAt = false; -/////////////////////////////////////// -// internal utility functions -/////////////////////////////////////// -/****************************************************************************** - -*/ -function->null internal:ResetFlags() - - g:randomize = false; - g:roll = false; - g:hasAt = false; -end - - - -function->bool internal:TestIndicesEmpty() - - if (g:vTestIndices.count != 0) - insert.rule.pos.type = notindex; - for (i = 0 to g:vTestIndices.last) - insert.rule.pos.index = g:vTestIndices[i]; - end - return true; - end - insert.rule.pos.type = empty; - return true; -end - - - -function->bool internal:TestIndicesFull() - - if (g:vTestIndices.count != 0) - insert.rule.pos.type = index; - for (i = 0 to g:vTestIndices.last) - insert.rule.pos.index = g:vTestIndices[i]; - end - return true; - end - insert.rule.pos.type = full; - return true; -end - - - - - -/////////////////////////////////////// -// general functions -/////////////////////////////////////// -/****************************************************************************** - -*/ -function->null AutoMapper(string sName) - - insert.automapper = sName; -end - - - -function->null NewRun() - - insert.newrun = 1; -end - - - -function->null NewRun(int iCopies) - -// - if (s:debug) - if (iCopies < 1) - error("NewRun(int " + iCopies.name() + ") -> " + iCopies.name() + " needs to be greater than 0."); - end - end -// - - insert.newrun = iCopies; -end - - - -function->null OverrideLayer() - - insert.nocopy; -end - - - -function->object Indices(array int aIndices) - -// - if (s:debug) - if (aIndices.count == 0) - error("Indices(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, object would be invalid."); - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < 1 or aIndices[i] > 255) - error("Indices(array int " + aIndices.name() + ") -> values need to be in range [1-255]."); - end - end - end -// - - object oResult = aIndices; - return oResult; -end - - - -function->object Rect(int iTopLeft, int iBottomRight) - -// - if (s:debug) - if (iTopLeft < 1 or iTopLeft > 255) - error("Rect(int " + iTopLeft.name() + ", int " + iBottomRight.name() + ") -> " + iTopLeft.name() + " needs to be in range [1-255]."); - end - - if (iBottomRight < 1 or iBottomRight > 255) - error("Rect(int " + iTopLeft.name() + ", int " + iBottomRight.name() + ") -> " + iBottomRight.name() + " needs to be in range [1-255]."); - end - end -// - - coord cTopLeft = iTopLeft; - coord cBottomRight = iBottomRight; - -// - if (s:debug) - if (cTopLeft.x > cBottomRight.x or cTopLeft.y > cBottomRight.y) - warning("Rect(int " + iTopLeft.name() + ", int " + iBottomRight.name() + ") -> " + iTopLeft.name() + " is not the top left corner of the rectangle."); - end - end -// - - array int aIndices; - for (x = cTopLeft.x to cBottomRight.x) - for (y = cTopLeft.y to cBottomRight.y) - aIndices.push([x, y]); - end - end - - object oResult = aIndices; - return oResult; -end - - - -function->array coord Area(coord cPos, coord cSize) - -// - if (s:debug) - if (cSize.x < 1 or cSize.y < 1) - error("Area(coord " + cPos.name() + ", coord " + cSize.name() + ") -> " + cSize.name() + " needs to be greater than 0."); - end - end -// - - array coord aResult; - - for (x = cPos.x to cPos.x + cSize.x - 1) - for (y = cPos.y to cPos.y + cSize.y - 1) - aResult.push([x, y]); - end - end - return aResult; -end - - - -function->array coord Radius(coord cPos, int iRadius) - -// - if (s:debug) - if (iRadius < 0) - error("Radius(coord " + cPos.name() + ", int " + iRadius.name() + ") -> " + iRadius.name() + " needs to be greater than or equal to 0."); - end - end -// - - array coord aResult; - - for (x = util:Negate(iRadius) to iRadius) - for (y = util:Negate(iRadius) to iRadius) - int iDiffX = cPos.x - x; - int iDiffY = cPos.y - y; - - if (iDiffX * iDiffX + iDiffY * iDiffY <= iRadius * iRadius) - aResult.push([x, y]); - end - end - end - return aResult; -end - - - -function->array coord Footprint(object oObject, int iOrientation) - -// - if (s:debug) - if (oObject.count == 0) - error("Footprint(object " + oObject.name() + ", int " + iOrientation.name() + ") -> " + oObject.name() + " cannot be empty."); - end - - if (iOrientation < top or iOrientation > left) - error("Footprint(object " + oObject.name() + ", int " + iOrientation.name() + ") -> " + iOrientation.name() + " needs to be top, right, bottom or left."); - end - end -// - - array coord aResult; - array int aRect = util:Rect(oObject); - - for (i = 0 to oObject.last) - coord cRelativePos = util:RelativePos(oObject.anchor, oObject[i]); - - if (iOrientation == top and cRelativePos.y == aRect[0]) - aResult.push([cRelativePos.x, cRelativePos.y - 1]); - end - if (iOrientation == right and cRelativePos.x == aRect[1]) - aResult.push([cRelativePos.x + 1, cRelativePos.y]); - end - if (iOrientation == bottom and cRelativePos.y == aRect[2]) - aResult.push([cRelativePos.x, cRelativePos.y + 1]); - end - if (iOrientation == left and cRelativePos.x == aRect[3]) - aResult.push([cRelativePos.x - 1, cRelativePos.y]); - end - end - return aResult; -end - - - -/////////////////////////////////////// -// -bool g:initInsert = true; - -array float g:argInsertChance; -int g:argInsertChanceIndex = 0; -/****************************************************************************** - -*/ -function->null internal:InsertResetFlags() - - g:initInsert = true; -end - - - -function->null internal:UpdateProbabilities(int iLast) - - if (iLast == 0) - g:roll = false; - end - - array float aProbabilities; - - if (not g:roll) - if (g:randomize) - for (i = 0 to iLast) - aProbabilities.push(g:argInsertChance[g:argInsertChanceIndex]); - - g:argInsertChanceIndex = g:argInsertChanceIndex + 1; - if (g:argInsertChanceIndex > g:argInsertChance.last) - g:argInsertChanceIndex = 0; - end - end - - g:argInsertChance = util:ToProbabilities(util:Unbias(aProbabilities)); - end - if (not g:randomize) - for (i = 0 to iLast) - aProbabilities.push(1.0); - end - g:argInsertChance = aProbabilities; - end - end - if (g:roll) - for (i = 0 to iLast) - aProbabilities.push(iLast + 1 - i); - end - g:argInsertChance = aProbabilities; - end - - g:argInsertChanceIndex = 0; -end - - - -function->null Insert(array int aIndices) - nested( - At, - NoDefaultPosRule, Chance, Roll, If - ) - -// - if (s:debug) - if (aIndices.count == 0) - warning("Insert(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < 0 or aIndices[i] > 255) - error("Insert(array int " + aIndices.name() + ") -> values need to be in range [0-255]."); - end - end - end -// - - invoke(nested); - g:initInsert = false; - - internal:UpdateProbabilities(aIndices.last); - if (g:roll or g:randomize) - insert.nocopy; - end - - for (i = 0 to aIndices.last) - g:vInsertIndex = aIndices[i]; - - insert.newrule; - util:InsertIndex(g:vInsertIndex); - util:Chance(g:argInsertChance[g:argInsertChanceIndex]); - - invoke(nested); - - g:argInsertChanceIndex = g:argInsertChanceIndex + 1; - end - - array float aEmpty; - g:argInsertChance = aEmpty; - g:argInsertChanceIndex = 0; - - internal:InsertResetFlags(); - internal:ResetFlags(); -end - - - -nested function->null Insert.At(coord cPos) - - if (g:initInsert) - g:hasAt = true; - return; - end - -// - if (s:debug) - if (cPos.x < 0) - warning("Insert.At(coord " + cPos.name() + ") -> " + cPos.name() + ".x was negative, function had no effect."); - return; - end - if (cPos.y < 0) - warning("Insert.At(coord " + cPos.name() + ") -> " + cPos.name() + ".y was negative, function had no effect."); - return; - end - end -// - - coord cPosNegated = util:Negate(cPos); - - insert.rule.pos = cPosNegated; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - - insert.rule.pos = [cPosNegated.x - 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [0, cPosNegated.y - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.nodefault; -end - - - -nested function->null Insert.NoDefaultPosRule() - - if (g:initInsert) - return; - end - insert.rule.nodefault; -end - - - -nested function->null Insert.Chance(array float aProbabilities) - -// - if (s:debug) - if (aProbabilities.count == 0) - warning("Insert.Chance(array float " + aProbabilities.name() + ") -> " + aProbabilities.name() + " was empty, function had no effect."); - return; - end - - for (i = 0 to aProbabilities.last) - if (aProbabilities[i] <= 0) - error("Insert.Chance(array float " + aProbabilities.name() + ") -> values need to be greater than 0."); - end - end - end -// - - if (g:initInsert) - g:randomize = true; - g:argInsertChance = aProbabilities; - return; - end -end - - - -nested function->null Insert.Roll() - - if (g:initInsert) - g:roll = true; - return; - end -end - - - -nested function->null Insert.If(array bool bTests) -end - - - -/////////////////////////////////////// -// -bool g:initIndexAt = true; - -coord g:posIndexAt = [0, 0]; - -int g:borderTop = 1; -int g:borderRight = 1; -int g:borderBottom = 1; -int g:borderLeft = 1; -int g:borderTopLeft = 1; -int g:borderTopRight = 1; -int g:borderBottomLeft = 1; -int g:borderBottomRight = 1; - -int this = 99999; -/****************************************************************************** - -*/ -function->null internal:IndexAtResetFlags() - - g:initIndexAt = true; - - g:posIndexAt = [0, 0]; -end - - - -function->null internal:ResetBorderFlags() - - g:borderTop = 1; - g:borderRight = 1; - g:borderBottom = 1; - g:borderLeft = 1; - g:borderTopLeft = 1; - g:borderTopRight = 1; - g:borderBottomLeft = 1; - g:borderBottomRight = 1; -end - - - -function->null internal:BorderRule() - - if (g:borderTop == 1 and g:borderRight == 1 and g:borderBottom == 1 and g:borderLeft == 1 and g:borderTopLeft == 1 and g:borderTopRight == 1 and g:borderBottomLeft == 1 and g:borderBottomRight == 1) - return; - end - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - if (g:borderTop == 0) insert.rule.pos = [iX , iY - 1]; internal:TestIndicesEmpty(); end - if (g:borderRight == 0) insert.rule.pos = [iX + 1, iY ]; internal:TestIndicesEmpty(); end - if (g:borderBottom == 0) insert.rule.pos = [iX , iY + 1]; internal:TestIndicesEmpty(); end - if (g:borderLeft == 0) insert.rule.pos = [iX - 1, iY ]; internal:TestIndicesEmpty(); end - if (g:borderTopLeft == 0) insert.rule.pos = [iX - 1, iY - 1]; internal:TestIndicesEmpty(); end - if (g:borderTopRight == 0) insert.rule.pos = [iX + 1, iY - 1]; internal:TestIndicesEmpty(); end - if (g:borderBottomLeft == 0) insert.rule.pos = [iX - 1, iY + 1]; internal:TestIndicesEmpty(); end - if (g:borderBottomRight == 0) insert.rule.pos = [iX + 1, iY + 1]; internal:TestIndicesEmpty(); end - - if (g:borderTop == 1) insert.rule.pos = [iX , iY - 1]; internal:TestIndicesFull(); end - if (g:borderRight == 1) insert.rule.pos = [iX + 1, iY ]; internal:TestIndicesFull(); end - if (g:borderBottom == 1) insert.rule.pos = [iX , iY + 1]; internal:TestIndicesFull(); end - if (g:borderLeft == 1) insert.rule.pos = [iX - 1, iY ]; internal:TestIndicesFull(); end - if (g:borderTopLeft == 1) insert.rule.pos = [iX - 1, iY - 1]; internal:TestIndicesFull(); end - if (g:borderTopRight == 1) insert.rule.pos = [iX + 1, iY - 1]; internal:TestIndicesFull(); end - if (g:borderBottomLeft == 1) insert.rule.pos = [iX - 1, iY + 1]; internal:TestIndicesFull(); end - if (g:borderBottomRight == 1) insert.rule.pos = [iX + 1, iY + 1]; internal:TestIndicesFull(); end -end - - - -function->bool IndexAt(array coord aCoords) - nested( - TestIndices, - Is, IsNot, IsEmpty, IsEmptyAt, IsFull, IsFullAt, IsOut, IsNotOut, - IsWithinArea, IsNotWithinArea, - IsWithinRadius, IsNotWithinRadius, - IsEdge, IsNotEdge, - IsNextTo, IsNotNextTo, - IsWall, IsOuterCorner, IsInnerCorner, - HasSpaceFor, - IsOverlapping, IsNotOverlapping - ) - -// - if (s:debug) - if (aCoords.count == 0) - warning("IndexAt(array coord " + aCoords.name() + ") -> " + aCoords.name() + " was empty, function had no effect."); - return false; - end - end -// - - if (g:initInsert or g:hasAt) - return false; - end - - invoke(nested); - g:initIndexAt = false; - - for (i = 0 to aCoords.last) - g:posIndexAt = aCoords[i]; - invoke(nested); - - internal:BorderRule(); - internal:ResetBorderFlags(); - end - - array int aEmpty; - g:vTestIndices = aEmpty; - - internal:IndexAtResetFlags(); - internal:ResetFlags(); - return true; -end - - - -nested function->bool IndexAt.TestIndices(array int aIndices) - -// - if (s:debug) - if (aIndices.count == 0) - warning("IndexAt.TestIndices(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < 0 or aIndices[i] > 255) - error("IndexAt.TestIndices(array int " + aIndices.name() + ") -> values need to be in range [0-255]."); - end - end - end -// - - if (g:initIndexAt) - g:vTestIndices = aIndices; - return false; - end - return true; -end - - - -nested function->bool IndexAt.Is(array int aIndices) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aIndices.count == 0) - warning("IndexAt.Is(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if ((aIndices[i] < -1 or aIndices[i] > 255) and aIndices[i] != this) - error("IndexAt.Is(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = index; - for (i = 0 to aIndices.last) - int iIndex = aIndices[i]; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - end - return true; -end - - - -nested function->bool IndexAt.IsNot(array int aIndices) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aIndices.count == 0) - warning("IndexAt.IsNot(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if ((aIndices[i] < -1 or aIndices[i] > 255) and aIndices[i] != this) - error("IndexAt.IsNot(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = notindex; - for (i = 0 to aIndices.last) - int iIndex = aIndices[i]; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - end - return true; -end - - - -nested function->bool IndexAt.IsEmpty() - - if (g:initIndexAt) - return false; - end - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = empty; - return true; -end - - - -nested function->bool IndexAt.IsEmptyAt(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsEmptyAt(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if (aOrientations[i] < top or aOrientations[i] > bottomRight) - error("IndexAt.IsEmptyAt(array int " + aOrientations.name() + ") -> values need to be top, right, bottom, left, topLeft, topRight, bottomLeft or bottomRight."); - end - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aOrientations.last) - int iOrientation = aOrientations[i]; - - if (iOrientation == top) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = empty; - end - if (iOrientation == right) - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = empty; - end - if (iOrientation == bottom) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = empty; - end - if (iOrientation == left) - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = empty; - end - if (iOrientation == topLeft) - insert.rule.pos = [iX - 1, iY - 1]; - insert.rule.pos.type = empty; - end - if (iOrientation == topRight) - insert.rule.pos = [iX + 1, iY - 1]; - insert.rule.pos.type = empty; - end - if (iOrientation == bottomLeft) - insert.rule.pos = [iX - 1, iY + 1]; - insert.rule.pos.type = empty; - end - if (iOrientation == bottomRight) - insert.rule.pos = [iX + 1, iY + 1]; - insert.rule.pos.type = empty; - end - end - return true; -end - - - -nested function->bool IndexAt.IsFull() - - if (g:initIndexAt) - return false; - end - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = full; - return true; -end - - - -nested function->bool IndexAt.IsFullAt(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsFullAt(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if (aOrientations[i] < top or aOrientations[i] > bottomRight) - error("IndexAt.IsFullAt(array int " + aOrientations.name() + ") -> values need to be top, right, bottom, left, topLeft, topRight, bottomLeft or bottomRight."); - end - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aOrientations.last) - int iOrientation = aOrientations[i]; - - if (iOrientation == top) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = full; - end - if (iOrientation == right) - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = full; - end - if (iOrientation == bottom) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = full; - end - if (iOrientation == left) - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = full; - end - if (iOrientation == topLeft) - insert.rule.pos = [iX - 1, iY - 1]; - insert.rule.pos.type = full; - end - if (iOrientation == topRight) - insert.rule.pos = [iX + 1, iY - 1]; - insert.rule.pos.type = full; - end - if (iOrientation == bottomLeft) - insert.rule.pos = [iX - 1, iY + 1]; - insert.rule.pos.type = full; - end - if (iOrientation == bottomRight) - insert.rule.pos = [iX + 1, iY + 1]; - insert.rule.pos.type = full; - end - end - return true; -end - - - -nested function->bool IndexAt.IsOut() - - if (g:initIndexAt) - return false; - end - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - return true; -end - - - -nested function->bool IndexAt.IsNotOut() - - if (g:initIndexAt) - return false; - end - - insert.rule.pos = g:posIndexAt; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - return true; -end - - - -nested function->bool IndexAt.IsWithinArea(int iWidth, int iHeight) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (iWidth < 1) - error("IndexAt.IsWithinArea(int " + iWidth.name() + ", int " + iHeight.name() + ") -> " + iWidth.name() + " needs to be greater than 0."); - end - if (iHeight < 1) - error("IndexAt.IsWithinArea(int " + iWidth.name() + ", int " + iHeight.name() + ") -> " + iHeight.name() + " needs to be greater than 0."); - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (x = iX to iX + iWidth - 1) - for (y = iY to iY + iHeight - 1) - insert.rule.pos = [x, y]; - internal:TestIndicesFull(); - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - end - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool IndexAt.IsNotWithinArea(int iWidth, int iHeight) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (iWidth < 1) - error("IndexAt.IsNotWithinArea(int " + iWidth.name() + ", int " + iHeight.name() + ") -> " + iWidth.name() + " needs to be greater than 0."); - end - if (iHeight < 1) - error("IndexAt.IsNotWithinArea(int " + iWidth.name() + ", int " + iHeight.name() + ") -> " + iHeight.name() + " needs to be greater than 0."); - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (x = iX to iX + iWidth - 1) - for (y = iY to iY + iHeight - 1) - insert.rule.pos = [x, y]; - internal:TestIndicesEmpty(); - end - end - return true; -end - - - -nested function->bool IndexAt.IsWithinRadius(int iRadius) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (iRadius < 0) - error("IndexAt.IsWithinRadius(int " + iRadius.name() + ") -> " + iRadius.name() + " needs to be greater than or equal to 0."); - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (x = util:Negate(iRadius) to iRadius) - for (y = util:Negate(iRadius) to iRadius) - int iDiffX = iX - x; - int iDiffY = iY - y; - - if (iDiffX * iDiffX + iDiffY * iDiffY <= iRadius * iRadius) - insert.rule.pos = [x, y]; - internal:TestIndicesFull(); - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - end - end - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool IndexAt.IsNotWithinRadius(int iRadius) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (iRadius < 0) - error("IndexAt.IsNotWithinRadius(int " + iRadius.name() + ") -> " + iRadius.name() + " needs to be greater than or equal to 0."); - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (x = util:Negate(iRadius) to iRadius) - for (y = util:Negate(iRadius) to iRadius) - int iDiffX = iX - x; - int iDiffY = iY - y; - - if (iDiffX * iDiffX + iDiffY * iDiffY <= iRadius * iRadius) - insert.rule.pos = [x, y]; - internal:TestIndicesEmpty(); - end - end - end - return true; -end - - - -nested function->bool IndexAt.IsEdge(int iOrientation) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (iOrientation < top or iOrientation > bottomRight) - error("IndexAt.IsEdge(int " + iOrientation.name() + ") -> value needs to be top, right, bottom, left, topLeft, topRight, bottomLeft or bottomRight."); - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - if (iOrientation == top) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == right) - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == bottom) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == left) - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == topLeft) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == topRight) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == bottomLeft) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - if (iOrientation == bottomRight) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - end - return true; -end - - - -nested function->bool IndexAt.IsNotEdge(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsNotEdge(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if ((aOrientations[i] < top or aOrientations[i] > left) and aOrientations[i] != all) - error("IndexAt.IsNotEdge(array int " + aOrientations.name() + ") -> values need to be top, right, bottom, left or all."); - end - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aOrientations.last) - if (aOrientations[i] == top or aOrientations[i] == all) - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == right or aOrientations[i] == all) - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == bottom or aOrientations[i] == all) - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == left or aOrientations[i] == all) - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - end - return true; -end - - - -nested function->bool IndexAt.IsNextTo(array int aIndices) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aIndices.count == 0) - warning("IndexAt.IsNextTo(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if ((aIndices[i] < -1 or aIndices[i] > 255) and aIndices[i] != this) - error("IndexAt.IsNextTo(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aIndices.last) - int iIndex = aIndices[i]; - - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = index; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = index; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = index; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = index; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool IndexAt.IsNotNextTo(array int aIndices) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aIndices.count == 0) - warning("IndexAt.IsNotNextTo(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if ((aIndices[i] < -1 or aIndices[i] > 255) and aIndices[i] != this) - error("IndexAt.IsNotNextTo(array int " + aIndices.name() + ") -> values need to be in range [-1-255]."); - end - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aIndices.last) - int iIndex = aIndices[i]; - - insert.rule.pos = [iX - 1, iY]; - insert.rule.pos.type = notindex; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - - insert.rule.pos = [iX, iY - 1]; - insert.rule.pos.type = notindex; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - - insert.rule.pos = [iX + 1, iY]; - insert.rule.pos.type = notindex; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - - insert.rule.pos = [iX, iY + 1]; - insert.rule.pos.type = notindex; - if (iIndex != this) insert.rule.pos.index = iIndex; end - if (iIndex == this) insert.rule.pos.index = g:vInsertIndex; end - end - return true; -end - - - -nested function->bool IndexAt.IsWall(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsWall(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if (aOrientations[i] < top or aOrientations[i] > left) - error("IndexAt.IsWall(array int " + aOrientations.name() + ") -> values need to be top, right, bottom or left."); - end - end - end -// - - if (g:vTestIndices.count != 0) - insert.rule.pos = g:posIndexAt; - internal:TestIndicesFull(); - end - - if (aOrientations.has(top)) - g:borderTop = 0; - g:borderTopLeft = -1; - g:borderTopRight = -1; - end - if (aOrientations.has(right)) - g:borderRight = 0; - g:borderTopRight = -1; - g:borderBottomRight = -1; - end - if (aOrientations.has(bottom)) - g:borderBottom = 0; - g:borderBottomLeft = -1; - g:borderBottomRight = -1; - end - if (aOrientations.has(left)) - g:borderLeft = 0; - g:borderTopLeft = -1; - g:borderBottomLeft = -1; - end - return true; -end - - - -nested function->bool IndexAt.IsOuterCorner(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsOuterCorner(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if (aOrientations[i] < topLeft or aOrientations[i] > bottomRight) - error("IndexAt.IsOuterCorner(array int " + aOrientations.name() + ") -> values need to be topLeft, topRight, bottomLeft or bottomRight."); - end - end - end -// - - if (g:vTestIndices.count != 0) - insert.rule.pos = g:posIndexAt; - internal:TestIndicesFull(); - end - - if (aOrientations.has(topLeft)) - g:borderTop = 0; - g:borderLeft = 0; - g:borderTopLeft = -1; - g:borderTopRight = -1; - g:borderBottomLeft = -1; - end - if (aOrientations.has(topRight)) - g:borderTop = 0; - g:borderRight = 0; - g:borderTopLeft = -1; - g:borderTopRight = -1; - g:borderBottomRight = -1; - end - if (aOrientations.has(bottomLeft)) - g:borderBottom = 0; - g:borderLeft = 0; - g:borderTopLeft = -1; - g:borderBottomLeft = -1; - g:borderBottomRight = -1; - end - if (aOrientations.has(bottomRight)) - g:borderBottom = 0; - g:borderRight = 0; - g:borderTopRight = -1; - g:borderBottomLeft = -1; - g:borderBottomRight = -1; - end - return true; -end - - - -nested function->bool IndexAt.IsInnerCorner(array int aOrientations) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("IndexAt.IsInnerCorner(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if (aOrientations[i] < topLeft or aOrientations[i] > bottomRight) - error("IndexAt.IsInnerCorner(array int " + aOrientations.name() + ") -> values need to be topLeft, topRight, bottomLeft or bottomRight."); - end - end - end -// - - if (g:vTestIndices.count != 0) - insert.rule.pos = g:posIndexAt; - internal:TestIndicesFull(); - end - - if (aOrientations.has(topLeft)) - g:borderTopLeft = 0; - end - if (aOrientations.has(topRight)) - g:borderTopRight = 0; - end - if (aOrientations.has(bottomLeft)) - g:borderBottomLeft = 0; - end - if (aOrientations.has(bottomRight)) - g:borderBottomRight = 0; - end - return true; -end - - - -nested function->bool IndexAt.HasSpaceFor(object oObject) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (oObject.count == 0) - warning("IndexAt.HasSpaceFor(object " + oObject.name() + ") -> " + oObject.name() + " was empty, function had no effect."); - return false; - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to oObject.last) - coord cRelativePos = util:RelativePos(oObject.anchor, oObject[i]); - - insert.rule.pos = [cRelativePos.x + iX, cRelativePos.y + iY]; - internal:TestIndicesFull(); - end - return true; -end - - - -nested function->bool IndexAt.IsOverlapping(array object aObjects) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("IndexAt.IsOverlapping(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aObjects.last) - coord cAnchor = aObjects[i].anchor; - - for (j = 0 to aObjects[i].last) - coord cRelativePos = util:RelativePos(cAnchor, aObjects[i][j]); - - insert.rule.pos = [iX + cRelativePos.x * -1, iY + cRelativePos.y * -1]; - insert.rule.pos.type = index; - insert.rule.pos.index = cAnchor; - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - end - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool IndexAt.IsNotOverlapping(array object aObjects) - - if (g:initIndexAt) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("IndexAt.IsNotOverlapping(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - int iX = g:posIndexAt.x; - int iY = g:posIndexAt.y; - - for (i = 0 to aObjects.last) - coord cAnchor = aObjects[i].anchor; - - for (j = 0 to aObjects[i].last) - coord cRelativePos = util:RelativePos(cAnchor, aObjects[i][j]); - - insert.rule.pos = [iX + cRelativePos.x * -1, iY + cRelativePos.y * -1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cAnchor; - end - end - return true; -end - - - -/****************************************************************************** - -*/ -function->null Replace(int iFrom, int iTo) - nested( - Chance - ) - -// - if (s:debug) - if (iFrom < 0 or iFrom > 255) - error("Replace(int " + iFrom.name() + ", int " + iTo.name() + ") -> " + iFrom.name() + " needs to be in range [0-255]."); - end - - if (iTo < 0 or iTo > 255) - error("Replace(int " + iFrom.name() + ", int " + iTo.name() + ") -> " + iTo.name() + " needs to be in range [0-255]."); - end - end -// - - Insert(iTo).If(IndexAt([0, 0]).Is(iFrom)); - invoke(nested); -end - - - -nested function->null Replace.Chance(float fProbability) - -// - if (s:debug) - if (fProbability <= 0) - error("Replace.Chance(float " + fProbability.name() + ") -> " + fProbability.name() + " needs to be greater than 0."); - end - end -// - - util:Chance(fProbability); -end - - - -/****************************************************************************** - -*/ -function->null ReplaceNot(int iNot, int iTo) - nested( - Chance - ) - -// - if (s:debug) - if (iNot < 0 or iNot > 255) - error("ReplaceNot(int " + iNot.name() + ", int " + iTo.name() + ") -> " + iNot.name() + " needs to be in range [0-255]."); - end - - if (iTo < 0 or iTo > 255) - error("ReplaceNot(int " + iNot.name() + ", int " + iTo.name() + ") -> " + iTo.name() + " needs to be in range [0-255]."); - end - end -// - - Insert(iTo).If(IndexAt([0, 0]).IsNot(iNot)); - invoke(nested); -end - - - -nested function->null ReplaceNot.Chance(float fProbability) - -// - if (s:debug) - if (fProbability <= 0) - error("ReplaceNot.Chance(float " + fProbability.name() + ") -> " + fProbability.name() + " needs to be greater than 0."); - end - end -// - - util:Chance(fProbability); -end - - - -/////////////////////////////////////// -// -array int g:argShift; -/****************************************************************************** - -*/ -function->null Shift(array int aIndices) - nested( - By - ) - -// - if (s:debug) - if (aIndices.count == 0) - warning("Shift(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < 0 or aIndices[i] > 255) - error("Shift(array int " + aIndices.name() + ") -> values need to be in range [0-255]."); - end - end - end -// - - g:argShift = aIndices; - invoke(nested); -end - - - -nested function->null Shift.By(coord cPos) - - for (i = 0 to g:argShift.last) - Insert(0).If(IndexAt([0, 0]).Is(g:argShift[i])); - end - for (i = 0 to g:argShift.last) - Insert(g:argShift[i]).If(IndexAt(cPos).Is(g:argShift[i])).NoDefaultPosRule(); - end -end - - - -/////////////////////////////////////// -// -/****************************************************************************** - -*/ -function->null InsertObject(array object aObjects) - nested( - At, - NoDefaultPosRule, Chance, Roll, If - ) - -// - if (s:debug) - if (aObjects.count == 0) - warning("InsertObject(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return; - end - end -// - - invoke(nested); - g:initInsert = false; - - internal:UpdateProbabilities(aObjects.last); - if (g:roll or g:randomize) - insert.nocopy; - end - - for (i = 0 to aObjects.last) - g:vInsertObject = aObjects[i]; - g:vInsertIndex = aObjects[i].anchor; - - insert.newrule; - util:InsertIndex(g:vInsertIndex); - util:Chance(g:argInsertChance[g:argInsertChanceIndex]); - - invoke(nested); - - g:argInsertChanceIndex = g:argInsertChanceIndex + 1; - end - - array float aEmpty; - g:argInsertChance = aEmpty; - g:argInsertChanceIndex = 0; - - internal:InsertResetFlags(); - internal:ResetFlags(); -end - - - -nested function->null InsertObject.At(coord cPos) - - if (g:initInsert) - g:hasAt = true; - return; - end - -// - if (s:debug) - if (cPos.x < 0) - warning("InsertObject.At(coord " + cPos.name() + ") -> " + cPos.name() + ".x was negative, function had no effect."); - return; - end - if (cPos.y < 0) - warning("InsertObject.At(coord " + cPos.name() + ") -> " + cPos.name() + ".y was negative, function had no effect."); - return; - end - end -// - - coord cPosNegated = util:Negate(cPos); - - insert.rule.pos = cPosNegated; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - - insert.rule.pos = [cPosNegated.x - 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [0, cPosNegated.y - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.nodefault; -end - - - -nested function->null InsertObject.NoDefaultPosRule() - - if (g:initInsert) - return; - end - insert.rule.nodefault; -end - - - -nested function->null InsertObject.Chance(array float aProbabilities) - -// - if (s:debug) - if (aProbabilities.count == 0) - warning("InsertObject.Chance(array float " + aProbabilities.name() + ") -> " + aProbabilities.name() + " was empty, function had no effect."); - return; - end - - for (i = 0 to aProbabilities.last) - if (aProbabilities[i] <= 0) - error("InsertObject.Chance(array float " + aProbabilities.name() + ") -> values need to be greater than 0."); - end - end - end -// - - if (g:initInsert) - g:randomize = true; - g:argInsertChance = aProbabilities; - return; - end -end - - - -nested function->null InsertObject.Roll() - - if (g:initInsert) - g:roll = true; - return; - end -end - - - -nested function->null InsertObject.If(array bool bTests) -end - - - -/////////////////////////////////////// -// -bool g:initObject = true; - -int g:vObjectTop = 0; -int g:vObjectRight = 0; -int g:vObjectBottom = 0; -int g:vObjectLeft = 0; -/****************************************************************************** - -*/ -function->null internal:ObjectResetFlags() - - g:initObject = true; -end - - - -function->bool Object() - nested( - TestIndices, - HasSpace, Fits, IsOver, - IsTouchingObjectAt, IsTouchingWallAt, - IsEdge, IsNotEdge, - IsNextTo, IsNotNextTo, - IsOverlapping, IsNotOverlapping - ) - - if (g:initInsert or g:hasAt) - return false; - end - - invoke(nested); - g:initObject = false; - - insert.nocopy; - - array int aRect = util:Rect(g:vInsertObject); - g:vObjectTop = aRect[0]; - g:vObjectRight = aRect[1]; - g:vObjectBottom = aRect[2]; - g:vObjectLeft = aRect[3]; - - invoke(nested); - - array int aEmpty; - g:vTestIndices = aEmpty; - - internal:ObjectResetFlags(); - internal:ResetFlags(); - return true; -end - - - -nested function->bool Object.TestIndices(array int aIndices) - -// - if (s:debug) - if (aIndices.count == 0) - warning("InsertObject.TestIndices(array int " + aIndices.name() + ") -> " + aIndices.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aIndices.last) - if (aIndices[i] < 0 or aIndices[i] > 255) - error("InsertObject.TestIndices(array int " + aIndices.name() + ") -> values need to be in range [0-255]."); - end - end - end -// - - if (g:initObject) - g:vTestIndices = aIndices; - return false; - end - return true; -end - - - -nested function->bool Object.HasSpace() - - if (g:initObject) - return false; - end - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - for (i = 0 to oObject.last) - insert.rule.pos = util:RelativePos(cAnchor, oObject[i]); - internal:TestIndicesFull(); - end - return true; -end - - - -nested function->bool Object.Fits() - - if (g:initObject) - return false; - end - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - array coord aRelativePos; - for (i = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[i]); - - aRelativePos.push(cRelativePos); - - insert.rule.pos = cRelativePos; - internal:TestIndicesFull(); - end - - for (i = 0 to aRelativePos.last) - coord cPos = aRelativePos[i]; - - coord cTop = [cPos.x, cPos.y - 1]; - coord cRight = [cPos.x + 1, cPos.y]; - coord cBottom = [cPos.x, cPos.y + 1]; - coord cLeft = [cPos.x - 1, cPos.y]; - - if (not aRelativePos.has(cTop)) - insert.rule.pos = cTop; - internal:TestIndicesEmpty(); - end - if (not aRelativePos.has(cRight)) - insert.rule.pos = cRight; - internal:TestIndicesEmpty(); - end - if (not aRelativePos.has(cBottom)) - insert.rule.pos = cBottom; - internal:TestIndicesEmpty(); - end - if (not aRelativePos.has(cLeft)) - insert.rule.pos = cLeft; - internal:TestIndicesEmpty(); - end - end - return true; -end - - - -nested function->bool Object.IsOver(array object aObjects) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("Object.IsOver(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - insert.rule.pos = [0, 0]; - for (i = 0 to aObjects.last) - insert.rule.pos.type = index; - insert.rule.pos.index = aObjects[i].anchor; - end - return true; -end - - - -nested function->bool Object.IsTouchingObjectAt(object oObject, int iSide) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (oObject.count == 0) - warning("Object.IsTouchingObjectAt(object " + oObject.name() + ", int " + iSide.name() + ") -> " + oObject.name() + " was empty, function had no effect."); - return false; - end - if (iSide < top or iSide > left) - error("Object.IsTouchingObjectAt(object " + oObject.name() + ", int " + iSide.name() + ") -> " + iSide.name() + " needs to be top, right, bottom or left."); - end - end -// - - array coord aFootprintPos = Footprint(g:vInsertObject, iSide); - - array int aFootprintX; - array int aFootprintY; - array int aDistanceX; - array int aDistanceY; - for (i = 0 to aFootprintPos.last) - aFootprintX.push(aFootprintPos[i].x); - aFootprintY.push(aFootprintPos[i].y); - if (i > 0) - aDistanceX.push(aFootprintPos[i].x - aFootprintPos[i - 1].x); - aDistanceY.push(aFootprintPos[i].y - aFootprintPos[i - 1].y); - end - end - - array coord aOtherFootprintPos = Footprint(oObject, util:OppositeSide(iSide)); - - if (aFootprintPos.count <= aOtherFootprintPos.count) - array int aOtherFootprintX; - array int aOtherFootprintY; - array int aOtherDistanceX; - array int aOtherDistanceY; - for (j = 0 to aOtherFootprintPos.last) - aOtherFootprintX.push(aOtherFootprintPos[j].x); - aOtherFootprintY.push(aOtherFootprintPos[j].y); - if (j > 0) - aOtherDistanceX.push(aOtherFootprintPos[j].x - aOtherFootprintPos[j - 1].x); - aOtherDistanceY.push(aOtherFootprintPos[j].y - aOtherFootprintPos[j - 1].y); - end - end - - int iMatchIndex = 0; - if (iSide == top or iSide == bottom) - iMatchIndex = aOtherDistanceX.find(aDistanceX); - end - if (iSide == left or iSide == right) - iMatchIndex = aOtherDistanceY.find(aDistanceY); - end - - if (util:Found(iMatchIndex)) - if (iSide == top) - insert.rule.pos = [aFootprintX[0] - aOtherFootprintX[0], util:Negate(aOtherFootprintPos[0].y)]; - end - if (iSide == bottom) - insert.rule.pos = [aFootprintX[0] - aOtherFootprintX[0], aFootprintPos[0].y]; - end - if (iSide == left) - insert.rule.pos = [util:Negate(aOtherFootprintPos[0].x), aFootprintY[0] - aOtherFootprintY[0]]; - end - if (iSide == right) - insert.rule.pos = [aFootprintPos[0].x, aFootprintY[0] - aOtherFootprintY[0]]; - end - insert.rule.pos.type = index; - insert.rule.pos.index = oObject.anchor; - - return true; - end - end - -// - if (s:debug) - warning("Object.IsTouchingObjectAt(object " + oObject.name() + ", int " + iSide.name() + ") -> matching footprint was not found, function had no effect."); - end -// - return false; -end - - - -nested function->bool Object.IsTouchingWallAt(int iSide) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (iSide < top or iSide > left) - error("Object.IsTouchingWallAt(int " + iSide.name() + ") -> value needs to be top, right, bottom or left."); - end - end -// - - object oObject = g:vInsertObject; - - array coord aFootprintPos = Footprint(oObject, iSide); - for (i = 0 to aFootprintPos.last) - insert.rule.pos = aFootprintPos[i]; - internal:TestIndicesFull(); - end - return true; -end - - - -nested function->bool Object.IsEdge(int iOrientation) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (iOrientation < top or iOrientation > bottomRight) - error("Object.IsEdge(int " + iOrientation.name() + ") -> value needs to be top, right, bottom, left, topLeft, topRight, bottomLeft or bottomRight."); - end - end -// - - if (iOrientation == top) - insert.rule.pos = [0, g:vObjectTop - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == right) - insert.rule.pos = [g:vObjectRight + 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == bottom) - insert.rule.pos = [0, g:vObjectBottom + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == left) - insert.rule.pos = [g:vObjectLeft - 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == topLeft) - insert.rule.pos = [0, g:vObjectTop - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [g:vObjectLeft - 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == topRight) - insert.rule.pos = [0, g:vObjectTop - 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [g:vObjectRight + 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == bottomLeft) - insert.rule.pos = [0, g:vObjectBottom + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [g:vObjectLeft - 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - if (iOrientation == bottomRight) - insert.rule.pos = [0, g:vObjectBottom + 1]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - insert.rule.pos = [g:vObjectRight + 1, 0]; - insert.rule.pos.type = index; - insert.rule.pos.index = -1; - - return true; - end - return true; -end - - - -nested function->bool Object.IsNotEdge(array int aOrientations) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (aOrientations.count == 0) - warning("Object.IsNotEdge(array int " + aOrientations.name() + ") -> " + aOrientations.name() + " was empty, function had no effect."); - return false; - end - - for (i = 0 to aOrientations.last) - if ((aOrientations[i] < top or aOrientations[i] > left) and aOrientations[i] != all) - error("Object.IsNotEdge(array int " + aOrientations.name() + ") -> values need to be top, right, bottom, left or all."); - end - end - end -// - - for (i = 0 to aOrientations.last) - if (aOrientations[i] == top or aOrientations[i] == all) - insert.rule.pos = [0, g:vObjectTop - 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == right or aOrientations[i] == all) - insert.rule.pos = [g:vObjectRight + 1, 0]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == bottom or aOrientations[i] == all) - insert.rule.pos = [0, g:vObjectBottom + 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - if (aOrientations[i] == left or aOrientations[i] == all) - insert.rule.pos = [g:vObjectLeft - 1, 0]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = -1; - end - end - return true; -end - - - -nested function->bool Object.IsNextTo(array object aObjects) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("Object.IsNextTo(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - array coord aNextToPos; - for (i = 0 to aObjects.last) - coord cOtherAnchor = aObjects[i].anchor; - - array coord aPos; - for (j = 0 to aObjects[i].last) - coord cOtherRelativePos = util:RelativePos(cOtherAnchor, aObjects[i][j]); - - for (k = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[k]); - - coord cPos1 = [cRelativePos.x - cOtherRelativePos.x - 1, cRelativePos.y - cOtherRelativePos.y]; - coord cPos2 = [cRelativePos.x - cOtherRelativePos.x + 1, cRelativePos.y - cOtherRelativePos.y]; - coord cPos3 = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y - 1]; - coord cPos4 = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y + 1]; - - if (not aNextToPos.has(cPos1)) - aNextToPos.push(cPos1); - end - if (not aNextToPos.has(cPos2)) - aNextToPos.push(cPos2); - end - if (not aNextToPos.has(cPos3)) - aNextToPos.push(cPos3); - end - if (not aNextToPos.has(cPos4)) - aNextToPos.push(cPos4); - end - end - end - end - - for (n = 0 to aNextToPos.last) - for (i = 0 to aObjects.last) - coord cOtherAnchor = aObjects[i].anchor; - - insert.rule.pos = aNextToPos[n]; - insert.rule.pos.type = index; - insert.rule.pos.index = cOtherAnchor; - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - - array coord aPos; - for (j = 0 to aObjects[i].last) - coord cOtherRelativePos = util:RelativePos(cOtherAnchor, aObjects[i][j]); - - for (k = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[k]); - - coord cPos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y]; - if (not aPos.has(cPos)) - aPos.push(cPos); - - insert.rule.pos = cPos; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - end - end - end - end - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool Object.IsNotNextTo(array object aObjects) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("Object.IsNotNextTo(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - for (i = 0 to aObjects.last) - coord cOtherAnchor = aObjects[i].anchor; - - array coord aPos; - for (j = 0 to aObjects[i].last) - coord cOtherRelativePos = util:RelativePos(cOtherAnchor, aObjects[i][j]); - - for (k = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[k]); - - coord cPos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y]; - if (not aPos.has(cPos)) - aPos.push(cPos); - - insert.rule.pos = cPos; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - end - - insert.rule.pos = [cRelativePos.x - cOtherRelativePos.x - 1, cRelativePos.y - cOtherRelativePos.y]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - - insert.rule.pos = [cRelativePos.x - cOtherRelativePos.x + 1, cRelativePos.y - cOtherRelativePos.y]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - - insert.rule.pos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y - 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - - insert.rule.pos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y + 1]; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - end - end - end - return true; -end - - - -nested function->bool Object.IsOverlapping(array object aObjects) - - if (g:initObject) - return false; - end - -// - if (s:debug) - if (aObjects.count == 0) - warning("Object.IsOverlapping(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - for (i = 0 to aObjects.last) - coord cOtherAnchor = aObjects[i].anchor; - - array coord aPos; - for (j = 0 to aObjects[i].last) - coord cOtherRelativePos = util:RelativePos(cOtherAnchor, aObjects[i][j]); - - for (k = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[k]); - - coord cPos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y]; - if (not aPos.has(cPos)) - aPos.push(cPos); - - insert.rule.pos = cPos; - insert.rule.pos.type = index; - insert.rule.pos.index = cOtherAnchor; - insert.rule.pos.operator = g:or; - insert.rule.pos.group = g:group; - end - end - end - end - - g:group = g:group + 1; - return true; -end - - - -nested function->bool Object.IsNotOverlapping(array object aObjects) - -// - if (s:debug) - if (aObjects.count == 0) - warning("Object.IsNotOverlapping(array object " + aObjects.name() + ") -> " + aObjects.name() + " was empty, function had no effect."); - return false; - end - end -// - - object oObject = g:vInsertObject; - coord cAnchor = g:vInsertIndex; - - for (i = 0 to aObjects.last) - coord cOtherAnchor = aObjects[i].anchor; - - array coord aPos; - for (j = 0 to aObjects[i].last) - coord cOtherRelativePos = util:RelativePos(cOtherAnchor, aObjects[i][j]); - - for (k = 0 to oObject.last) - coord cRelativePos = util:RelativePos(cAnchor, oObject[k]); - - coord cPos = [cRelativePos.x - cOtherRelativePos.x, cRelativePos.y - cOtherRelativePos.y]; - if (not aPos.has(cPos)) - aPos.push(cPos); - - insert.rule.pos = cPos; - insert.rule.pos.type = notindex; - insert.rule.pos.index = cOtherAnchor; - end - end - end - end - return true; -end diff --git a/rules++/rpp b/rules++/rpp deleted file mode 100755 index b915fcc5cc0be8cacbc6d236084094a379545dab..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 8808864 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