/* "createCustomEffect.jsx" www.nabscripts.com This script allows you to create your own custom effect with as many controls as you want (slider, angle, etc). */ { // find each checked checkbox and store the corresponding control type & quantity function findControls(thePanel) { var controls = new Array(); var n = 0; for (var i = 0; i < thePanel.children.length; i++) { controls[n] = new Array(); var curChild = thePanel.children[i]; var nextChild = thePanel.children[i+1]; if (curChild.value == true && nextChild.text != "") { for (var j = 0; j < nextChild.text; j++) controls[n][j] = curChild.text; n++; } } return controls; } // find each checked checkbox and store the corresponding control name function findNames(thePanel) { var controlsnames = new Array(); var n = 0; for (var i = 0; i < thePanel.children.length; i++) { controlsnames[i] = new Array(); var curChild = thePanel.children[i]; var nextChild = thePanel.children[i+1]; if (curChild.value == true && nextChild.text != "") { for (var j = 0; j < nextChild.text.split(",").length; j++) controlsnames[n][j] = nextChild.text.split(",")[j].substring(0,30); n++; } } return controlsnames; } // main function (called when the user click on the \"Create\" button) function createCustomEffect(theControls) { if (!app.project) alert("Open a project first."); else { var myProj = app.project; if (isNetworkAccessAllowed() == true) { var tempFile = new File(AEPath + "temp.xml"); // write var XMLFile = new File(AEPath + "PresetEffects.xml"); // read var XMLFileIsOK = XMLFile.open("r","TEXT","????"); var tempFileIsOK = tempFile.open("w","TEXT","????"); var myMatchName = MatchNameEt.text.substring(0,31); var myEffectName = EffectNameEt.text.substring(0,31); if (myMatchName != "" && myEffectName != "" && XMLFileIsOK && tempFileIsOK) { // retrieve controls var myControls = findControls(myPanel_Parameters); if (myControls.length > 0) { var curLine; while (!XMLFile.eof) { curLine = XMLFile.readln(); if (curLine.indexOf("") == -1) tempFile.writeln(curLine); else break; } var firstLine = " "; tempFile.writeln(firstLine); // retrieve names var ControlsNames = new Array(); if (hasClicked) ControlsNames = findNames(myPanel_ParametersNames); else { for (var i = 0; i < myControls.length; i++) { ControlsNames[i] = new Array(); for (var j = 0; j < myControls[i].length; j++) ControlsNames[i][j] = myControls[i][j]; } } // write each control's description in the temp XML file for (var p = 0; p < myControls.length; p++) { for (var q = 0; q < myControls[p].length; q++) { var curControl = myControls[p][q]; // specification var spec = ""; if (hasClicked && curControl == "Angle" && angleDefCb.value == true && angleDefEt.text != "" && angleDefEt.text.split(",").length == 0) spec = "default=\"" + angleDefEt.text + "\""; else if (hasClicked && curControl == "Slider" && sliderDefCb.value == true && sliderDefEt.text != "" && sliderDefEt.text.split(",").length == 3) spec = "default=\"" + sliderDefEt.text.split(",")[0] + "\" valid_min=\"" + sliderDefEt.text.split(",")[1] + "\" valid_max=\"" + sliderDefEt.text.split(",")[2] + "\""; else { switch (curControl) { case "Angle": spec = "default=\"0\""; break; case "Checkbox": spec = "default=\"false\""; break; case "Color": spec = "default_red=\"255\" default_green=\"0\" default_blue=\"0\""; break; case "Layer": spec = "default_self=\"false\""; break; case "Point": spec = "default_x=\"0\" default_y=\"0\""; break; case "Slider": spec = "default=\"0\" valid_min=\"-1000000\" valid_max=\"1000000\""; break; default : break; } } var definitionLine = " <" + curControl + " name=\"" + trim(ControlsNames[p][q]) + "=" + ControlsNames[p][q] + "\" " + spec + "/>"; tempFile.writeln(definitionLine); } } tempFile.writeln(" \r\r\r"); tempFile.writeln(""); tempFile.close(); XMLFile.close(); // write in "PresetEffects.xml" XMLFileIsOK = XMLFile.open("w","TEXT","????"); tempFileIsOK = tempFile.open("r","TEXT","????"); if (XMLFileIsOK && tempFileIsOK) { while (!tempFile.eof) { curLine = tempFile.readln(); XMLFile.writeln(curLine); } } tempFile.close(); XMLFile.close(); // ask for saving/closing/reopening the project var IsOKToContinue = confirm("The script needs to save and close the project.\r\r" + "Do you want to continue ?"); if (IsOKToContinue) { myProj.save(); alert("The application must now quit. Reopen AE to load the new parameters.\r\r" + "A startup script will complete the procedure."); var startupScritStr = "// You shouldn't see this. Remove this script from the Startup folder.\r" + "// www.nabscripts.com\r\r" + "{\r\r" + "var myProj = app.project;\r\r" + "// create comp\r" + "var tempComp = myProj.items.addComp(\"my Custom Effect Comp\",200,200,1,1,12);\r\r" + "// apply the custom effect to a solid\r" + "var tempLayer = tempComp.layers.addSolid([1,1,1], \"my Custom Effect\",200,200,1,1);\r" + "tempLayer.comment = \"With the effect and its parameters selected, \\rdrag and drop into the effect panel \\rto save it as an animation preset.\"; \r\r" + "var myEffect = tempLayer.Effects.addProperty(\"" + myMatchName + "\");\r" + "myEffect.name = \"" + myEffectName + "\";\r\r" + "var StartUpScriptPath = \"C:\\" + "\\Program Files\\" + "\\Adobe\\" + "\\Adobe After Effects 7.0\\" + "\\Support Files\\" + "\\Scripts\\" + "\\Startup\\" + "\\" + "\";\r\r" + "for (var i = 1; i <= tempComp.layer(1).Effects.property(1).numProperties; i++)\r" + "\ttempComp.layer(1).Effects.property(1).property(i).selected = true;\r\r" + "var isOK = confirm (\"Custom Effect Creation has terminated successfully.\\r\\rYou can open the comp named \\" + "\"my Custom Effect Comp\\" + "\" \\rand save the effect on the white solid as an animation\\r preset.\\r\\rTo clean the temporary startup script, click \\" + "\"Yes\\" + "\".\");\r" + "if (isOK) {\r" + "\tvar scriptFile = new File(StartUpScriptPath + \"createCustomEffect_startup.jsx\");\r" + "\tscriptFile.remove();\r" + "}\r\r" + "}"; var scriptFile = new File(StartUpScriptPath + "createCustomEffect_startup.jsx"); var OpenIsOK = scriptFile.open("w","TEXT","????"); if (OpenIsOK) scriptFile.write(startupScritStr); app.quit(); } } } } } } function trim(Str) { var newStr = ""; for (var i = 0; i < Str.split(" ").length; i++) newStr += Str.split(" ")[i]; return newStr; } function isNetworkAccessAllowed() { var securitySetting = app.preferences.getPrefAsLong("Main Pref Section", "Pref_SCRIPTING_FILE_NETWORK_SECURITY"); if (!securitySetting) alert ("The application preference \"Allow Scripts to Write Files and Access Network\" must be set."); return securitySetting; } function checkVersion() { var isOK = true; if (parseFloat(app.version) < 7.0) { alert("This script requires AE 7.0 or later."); isOK = false; } return isOK; } // palette management function addCb1(theName) { var cb = myPanel_Parameters.add("checkbox", [startX,startY,startX+60,startY+20], theName); cb.onClick = on_Cb1_click; startX += 65; var et = myPanel_Parameters.add("edittext", [startX,startY,startX+40,startY+20], ""); et.visible = false; return cb; } function addCb2(theName) { var cb = myPanel_ParametersNames.add("checkbox", [startX,startY,startX+60,startY+20], theName); cb.onClick = on_Cb2_click; startX += 65; var et = myPanel_ParametersNames.add("edittext", [startX,startY,startX+170,startY+20], ""); et.visible = false; return cb; } function on_Cb1_click() { var theIndex; for (var i = 0; i < myPanel_Parameters.children.length; i++) { var curChild = myPanel_Parameters.children[i]; if (this.text == curChild.text) { theIndex = i; break; } } var curChildEt = myPanel_Parameters.children[theIndex+1]; if (curChildEt.visible == true) curChildEt.visible = false; else curChildEt.visible = true; } function on_Cb2_click() { var theIndex; for (var i = 0; i < myPanel_ParametersNames.children.length; i++) { var curChild = myPanel_ParametersNames.children[i]; if (this.text == curChild.text) { theIndex = i; break; } } var curChildEt = myPanel_ParametersNames.children[theIndex+1]; if (curChildEt.visible == true) curChildEt.visible = false; else curChildEt.visible = true; } function on_angleDefCb_click() { angleDefEt.visible = !angleDefEt.visible; } function on_sliderDefCb_click() { sliderDefEt.visible = !sliderDefEt.visible; sliderDefSt.visible = !sliderDefSt.visible; } function moreOptions() { hasClicked = !hasClicked; if (hasClicked) myPalette.bounds = [400,300,695,565+310]; else myPalette.bounds = [400,300,695,565]; } function localizeStr(Str) { var langCode = ""; switch (app.language) { case Language.ENGLISH: langCode = "en"; break; case Language.FRENCH: langCode = "fr"; break; default: langCode = "en"; break; } return Str[langCode]; } function on_aboutButton_click() { alert(localizeStr(helpStr)); } // MAIN SCRIPT if (checkVersion) { var helpFR = "\"createCustomEffect.jsx\"\r" + " www.nabscripts.com\r\r" + ""; var helpEN = "\"createCustomEffect.jsx\"\r" + " www.nabscripts.com\r\r" + "This script allows you to create your own custom effect\r" + "with many controls (slider, angle, color, etc)."; var helpStr = {en:helpEN, fr:helpFR}; var AEPath = "C:\\Program Files\\Adobe\\Adobe After Effects 7.0\\Support Files\\"; // "PresetEffects.xml" location folder var StartUpScriptPath = "C:\\Program Files\\Adobe\\Adobe After Effects 7.0\\Support Files\\Scripts\\Startup\\"; // "Startup" script folder // build palette var myPalette = new Window("palette", "CreateCustomEffect", [400,300,695,565]); myPalette.add("statictext", [10, 5, 200, 20], "Create Custom Effect"); myPalette.add("panel",[5,22,267,26]); var aboutButton = myPalette.add("button", [270,5,290,25], "?"); aboutButton.onClick = on_aboutButton_click; var myPanel_Name = myPalette.add("panel", [10,30,285,105], "Effect Name"); myPanel_Name.add("statictext", [30, 20, 100, 40], "matchName :"); var MatchNameEt = myPanel_Name.add("edittext",[105, 17, 216, 37], ""); myPanel_Name.add("statictext", [30, 45, 100, 65], "name :"); var EffectNameEt = myPanel_Name.add("edittext",[105, 42, 216, 62], ""); var myPanel_Parameters = myPalette.add("panel", [10,110,285,225], "Number of Controls"); var startX = 10; var startY = 20; addCb1("Angle"); startX = 10; startY = 50; addCb1("Checkbox"); startX = 10; startY = 80; addCb1("Color"); startX = 155; startY = 20; addCb1("Layer"); startX = 155; startY = 50; addCb1("Point"); startX = 155; startY = 80; addCb1("Slider"); var moreButton = myPalette.add("button", [10,234,100,256],"more options"); moreButton.onClick = moreOptions; var runButton = myPalette.add("button", [150,234,285,256],"Create"); runButton.onClick = createCustomEffect; var myPanel_ParametersNames = myPalette.add("panel", [10,265,285,465], "Names of Controls (comma separated)"); startX = 10; startY = 20; addCb2("Angle"); startX = 10; startY = 50; addCb2("Checkbox"); startX = 10; startY = 80; addCb2("Color"); startX = 10; startY = 110; addCb2("Layer"); startX = 10; startY = 140; addCb2("Point"); startX = 10; startY = 170; addCb2("Slider"); var myPanel_ParametersDefaults = myPalette.add("panel", [10,470,285,564], "Defaults"); var angleDefCb = myPanel_ParametersDefaults.add("checkbox", [10,20,70,40],"Angle"); var angleDefEt = myPanel_ParametersDefaults.add("edittext", [75,20,110,40],""); var sliderDefCb = myPanel_ParametersDefaults.add("checkbox", [10,50,70,70],"Slider"); var sliderDefEt = myPanel_ParametersDefaults.add("edittext", [75,50,200,70],""); var sliderDefSt = myPanel_ParametersDefaults.add("statictext", [75,72,270,87],"(default/min/max comma separated)"); angleDefCb.onClick = on_angleDefCb_click; sliderDefCb.onClick = on_sliderDefCb_click; angleDefEt.visible = false; sliderDefEt.visible = false; sliderDefSt.visible = false; var hasClicked = false; // "more options" flag (palette's height contraction/extension) myPalette.show(); } }