i am writing a script for photoshop and I´m looking for a way to copy a layer-style from one layer to another. The applied layerstyle can vary so I must be able to look for any possible style and copy it. I found some code to copy a layer style but the settings won´t be copied. Using the script listener does not help me much because it´s all hardcoded..
Is there a way to also copy the settings of a style? And a way to do this for all possible styles?
It is my understanding that Adobe does not have any methods for retrieving styles or style properties in the scripting interface. Apparently though, this can be done manually through Action Manager code. This post in the Adobe forums discuss some of the ways to go about doing that: How to get the style of a layer using Photoshop Scripting ?
I Haven't tested this but this maybe what you are looking for:
if (app.documents.length > 0 && app.activeDocument.layers.length > 1) {
transferEffects(app.activeDocument.layers.getByName("styleLayer"), app.activeDocument.activeLayer);
};
// function to copy layer effects of one layer and apply them to another one
function transferEffects(layer1, layer2) {
app.activeDocument.activeLayer = layer1;
try {
var id157 = charIDToTypeID("CpFX");
executeAction(id157, undefined, DialogModes.ALL);
app.activeDocument.activeLayer = layer2;
var id158 = charIDToTypeID("PaFX");
executeAction(id158, undefined, DialogModes.ALL);
} catch (e) {
alert("the layer has no effects");
app.activeDocument.activeLayer = layer2;
}
};
Related
I'm using a Viewport3DX with a lot of different MeshGeometryModel3D elements.
The User Interface integrates a slider that will update the opacity (alpha-value of PhongMaterials) of all model3d elements.
This is my current implementation of the code that updates the opacity:
geometryhandler.cs
public void UpdateOpacity(double value)
{
if (_mainWindow.MyBuildingComponents == null) return;
foreach (var component in _mainWindow.MyBuildingComponents)
{
// assign new material and later assign it back, to get the changes of the material recognized
var newmaterial = (_meshIdTogeometryModel3D[component.Id].Material as PhongMaterial).Clone();
// create new DiffusColor because setting the alpha property directly is not possible
newmaterial.DiffuseColor = new Color4(newmaterial.DiffuseColor.Red, newmaterial.DiffuseColor.Green, newmaterial.DiffuseColor.Blue, (float)value);
_meshIdTogeometryModel3D[component.Id].Material = newmaterial;
}
}
MainWindow.xaml.cs
private void UpdateOpacity(object sender, RoutedPropertyChangedEventArgs<double> e)
{
Geometryhandler?.UpdateOpacity(SliderModelOpacity.Value);
}
The UpdateOpacity function is called each time the value of the slider changes, iterates through a dictionary of MeshGeometryModel3D elements and updates their materials.
I tried many different version, but in the end this was the only implementation that did the job. However the update is very slow and 'laggy', even in release mode.
I recognized two things:
I had to clone the existing material, update it and assign it back to get the material to change in the viewport
I couldn't directly set the alpha-property of the Diffusecolor, but instead instantiate a new color object
Does somebody have an idea where the bottleneck might be here. Is it the cloning of the material, instantiating the new color or both? Or something completely different? Are there any better ways of doing the updates?
Curious to hear your suggestion. Thanks a lot already!
I'm going to reference my comment here so we can close out this question.
Are you using the "ValueChanged" event to trigger the UpdateOpacity? You might want to look into only updating the Opacity when the user is done dragging the slider: social.msdn.microsoft.com/Forums/vstudio/en-US/…. The only other suggestion I have is to try and combine/group together elements that have the same base color, so there are fewer material changes required with the opacity update.
...
msdn.microsoft.com/en-us/library/bb613553.aspx
I'm supper new here, either Javascript and JXA, so pardon me if I make some stupid questions. But I'm trying to figure out a way to get the string from the highlighted text using JXA - JavaScript for Automation, for Javascript can be recognized in Automator since Yosemite, I thought I can make something work with these:
window.getSelection in:
function getSelectedText() {
if (window.getSelection) {
txt = window.getSelection();
} else if (window.document.getSelection) {
txt =window.document.getSelection();
} else if (window.document.selection) {
txt = window.document.selection.createRange().text;
}
return txt;
}
This code is not mine, somebody posted this. But I've found out that I can't use window or document here in Automator to make change to Mac OS, so can someone show me how to convert this Javascript code into JXA which Automator can understand?
Thanks a lot!
In general, you can use the System Events app to copy and paste with any app.
'use strict';
//--- GET A REF TO CURRENT APP WITH STD ADDITONS ---
var app = Application.currentApplication()
app.includeStandardAdditions = true
var seApp = Application('System Events')
//--- Set the Clipboard so we can test for no selection ---
app.setTheClipboardTo("[NONE]")
//--- Activate the App to COPY the Selection ---
var safariApp = Application("Safari")
safariApp.activate()
delay(0.2) // adjust the delay as needed
//--- Issue the COPY Command ---
seApp.keystroke('c', { using: 'command down' }) // Press ⌘C
delay(0.2) // adjust the delay as needed
//--- Get the Text on the Clipboard ---
var clipStr = app.theClipboard()
console.log(clipStr)
//--- Display Alert if NO Selection was Made ---
if (clipStr === "[NONE]") {
var msgStr = "NO Selection was made"
console.log(msgStr)
app.activate()
app.displayAlert(msgStr)
}
For more info see:
Sending Keystrokes in JXA
JXA Resources
You need to mix JXA and Safari’s javaScript…
var Safari = Application("Safari") // get Safari
selection = Safari.doJavaScript("document.getSelection().toString()",{
in: Safari.windows[0].tabs[0] // assume frontmost window and tab
})
The script is in JXA, but the document.getSelection().toString() is Safari’s javaScript.
Of course you will need to enable apple events in Safari… http://osxdaily.com/2011/11/03/enable-the-develop-menu-in-safari/
If you want the selected text from another application, the code might be very different.
Don't do that, it's only applicable to JavaScript embedded inside a web browser. JXA is a standalone JS interpreter that has absolutely no understanding of web pages or DOM (and frankly doesn't have much clue about Mac application scripting either, btw).
Instead, use Automator to create an OS X Service as services can manipulate selected text in almost any OS X app; no application scripting required.
I'm looking to do a Play Scala project where I'll do especially drag & drop.
Is jQuery UI the best and the simplest way to do that? and How could one do this? could someone give me some examples or pointers?
In Play 1.0 there is a good example on how to use jQuery UI (http://www.playframework.com/modules/jqueryui-1.0/home) but I don't found examples or documentation on Play2.0 Scala !
first of all you need to define an endpoint for your data in the controller.
Simething like this:
def autocompleteSearch(a: String) = Action {
request =>
val data = List("apple", "apple iphone", "apple ipad", "microsoft windows", "microsot office");
val filteredData = data.filter(_.startsWith(a))
Ok(Json.toJson(filteredData))
}
Then you need to add this endpoint to your routes:
GET /some-ajax controllers.Application.autocompleteSearch
Then in your .scala.html file you can write a script that will do a get you you, example:
var updateTime = function() {
$.get("#routes.Application.timeUpdate()", function(data) {
display.html(data)
})
return false
}
When you have the var you just pass it to the jQueryUI.
My examples are copied from different things and they don't really fit together :) but I hope you can grasp the general idea.
Sorry the answer is not more specific, but I'm no JavaScript master and had to fight with the jQuery once, and this is what I have left from the struggle.
Cheers!
Does anyone know what might have changed since v3.0.5 that would enable extensions to work? Or, maybe I'm missing a setting somewhere? I wrote this add-on that works fine with newer versions, but I can't get it to launch in older ones. Specifically, I can't even get this part to work (this is in my browser overlay.xul):
<html:script>
<![CDATA[
var Cc = Components.classes;
var Ci = Components.interfaces;
var obSvc = Cc["#mozilla.org/observer-service;1"].getService(Ci.nsIObserverService);
gBrowser.consoleService = Cc["#mozilla.org/consoleservice;1"].getService(Ci.nsIConsoleService);
gBrowser.log = function(msg){
this.consoleService.logStringMessage(msg);
}
gBrowser.newObj= new MyAddOn();
gBrowser.log("initializing...");
function regListener()
{
obSvc.addObserver(gBrowser.newObj, "http-on-modify-request", false);
}
function unregListener()
{
obSvc.removeObserver(gBrowser.newObj, "http-on-modify-request");
}
window.addEventListener("load", regListener, false);
window.addEventListener("unload", unregListener, false);
]]>
This should attach listeners to the new obj (defined by a linked .js) However, I'm not even getting the "initializing..." message in the console. Any ideas?
Don't use <html:script>, use <script> (assuming you have xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul" on your root <overlay> element).
Don't register an application-global listener (http-on-modify-request) from a window overlay. Doing so will make your code run one time in each window the user may have open. Use an XPCOM component instead - https://developer.mozilla.org/en/Setting_HTTP_request_headers
Don't pollute common objects (like gBrowser or the global object (with var Cc)) with your own properties. If everyone did that, no two extensions would work together. Put all your code properties on your own object with a unique name.
accessing gBrowser before the load event is probably what's causing your specific problem.
Set up your environment and check the Error Console to debug problems.
Don't waste time trying to support Firefox 3. It's not supported by Mozilla itself for over a year and shouldn't be used to access the web.
It looks like gBrowser.log is not defined, or at least is not a function, as the error console will probably tell you. I've never heard of it either. Maybe it was added in Fx 3.5?
I'm trying to implement a comparison chart-like table, and a large list of selectable objects would work just perfectly, save for a few functionality changes that I need. I see that both of these have been addressed in previous questions, but neither of them provide complete solutions.
This question addressed the multiple select behavior by default, but only says 'I did it on my own' without providing anything. Looking at the internals of selectable, I see that if I play with the !event.metaKey condition I could probably get the behavior I'm looking for without too much trouble, but was wondering if anyone had a solution that didn't involve editing the internals.
Similarly, this page addresses the lasso toggle effect that I desired, but I'm not sure where in the code the lasso functionality was changed and as the rest of the script (the sortable functionality) is reported to not work in chrome or IE8 (link) and is outdated as this point, I'd rather not rely on the entire thing.
So if anyone could help me out with either of these, I'd appreciate it. Thanks
[Edit] Formatting...
I'm sure there's a better way to do this, but here's what I've did within the selectable js file.
For the always multi-selection:
I added an option 'alwaysMulti' (default false). Then I replaced the three instances of !event.metaKey with (!event.metaKey && !options.alwaysMulti) and the two instances of event.metaKey with (event.metaKey || options.alwaysMulti).
To get the selection lasso to toggle the selected status, I found the changes I needed from the second page I linked to. I also added an option 'lassoToggle' (default false) to trigger this functionality. Within _mouseDrag, there is a condition if (hit), it gets changed to the following:
if (hit) {
// SELECT
selectee.deselect = false;
if (selectee.selected || (options.lassoToggle && (selectee.startselected && event.metaKey)) {
selectee.$element.removeClass('ui-selected');
selectee.selected = false;
selectee.deselect = true;
}
if (selectee.unselecting) {
selectee.$element.removeClass('ui-unselecting');
selectee.unselecting = false;
}
if (!selectee.selecting && (!options.lassoToggle || !selectee.deselect) {
selectee.$element.addClass('ui-selecting');
selectee.selecting = true;
// selectable SELECTING callback
self._trigger("selecting", event, {
selecting: selectee.element
});
}
if(selectee.deselect && options.lassoToggle) {
selectee.$element.removeClass('ui-selecting');
selectee.selecting = false;
selectee.$element.addClass('ui-unselecting');
selectee.unselecting = true;
// selectable UNSELECTING callback
self._trigger("unselecting", event, {
unselecting: selectee.element
});
}
}
Note: The event.metaKey change for the multi-select isn't in that code sample.
Hopefully this helps someone else!