Para ciertos caracteres y símbolos especiales, AppleScript fallará en keystroke
el carácter real y, en su lugar, simplemente escribirá la letra a
.
El siguiente código AppleScript:
tell application "System Events" to keystroke "² ³ é ½ ₭"
escribe la siguiente cadena de texto (sin importar en qué aplicación esté):
a a a a a
Uno puede "escribir" el texto de manera efectiva colocando los caracteres especiales en el portapapeles y luego pegando el portapapeles, así:
set the clipboard to "² ³ é ½ ₭"
tell application "System Events" to keystroke "v" using command down
Evito usar el método anterior para poner texto en el portapapeles en AppleScript, porque necesariamente convierte el portapapeles en texto enriquecido en el proceso.
Prefiero emplear el método provisto aquí , para asegurar que el texto sin formato se coloque en el portapapeles. Pero este método convierte los caracteres especiales en mojibake.
Por ejemplo, usando la misma cadena que la anterior, este método coloca el siguiente texto en el portapapeles:
² ³ é ½ ₭
Sin embargo, puede dar cuenta manualmente de este problema agregando una replace_chars
declaración para cada carácter especial.
¿Hay alguna manera de escribir caracteres especiales a través de AppleScript, sin tener que utilizar el portapapeles?
Por ejemplo, ¿hay alguna manera de que pueda agregar los caracteres especiales deseados a un "banco" o archivo de sistema en algún lugar, para que la System Events
aplicación los conozca?
Es posible con CoreGraphics ( CGEventPost
), es una API de C (no funciona en un Cocoa-AppleScript), pero es posible llamar a un ejecutable desde un AppleScript.
Este es el método para crear el ejecutable con Xcode (Versión 8.3.3):
Puedes hacerlo tú mismo (puedes descargar Xcode desde la App Store ), o pedirle a una persona de confianza que cree el ejecutable.
1- Abra Xcode, seleccione el menú " Archivo " --> " Nuevo " --> " Proyecto ..."
2- Seleccione macOS y Command Line Tool , haga clic en el botón " Siguiente ".
3- Nómbrelo TypeCharacters
, seleccione Objective-C como Idioma, haga clic en el botón " Siguiente ".
4- Guarde el proyecto en la carpeta deseada.
5- En la ventana de Xcode, selecciona el main.m
icono, borra el texto de la ventana y pega uno de estos dos códigos:
El código necesita un bucle debido a un error, el CGEventKeyboardSetUnicodeString()
método trunca una cadena que supera los veinte caracteres o es un límite (no documentado).
Este código usa un bucle para escribir una lista de caracteres en cada iteración, la lista puede contener de uno a veinte caracteres. (Es rápido, 1 segundo escribir 2400 caracteres en un documento de TextEdit en mi computadora).
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
if (argc > 1) {
NSString *theString = [NSString stringWithUTF8String:argv[1]];
NSUInteger len = [theString length];
NSUInteger n, i = 0;
CGEventRef keyEvent = CGEventCreateKeyboardEvent(nil, 0, true);
unichar uChars[20];
while (i < len) {
n = i + 20;
if (n>len){n=len;}
[theString getCharacters:uChars range:NSMakeRange(i, n-i)];
CGEventKeyboardSetUnicodeString(keyEvent, n-i, uChars);
CGEventPost(kCGHIDEventTap, keyEvent); // key down
CGEventSetType(keyEvent, kCGEventKeyUp);
CGEventPost(kCGHIDEventTap, keyEvent); // key up (type 20 characters maximum)
CGEventSetType(keyEvent, kCGEventKeyDown);
i = n;
[NSThread sleepForTimeInterval:0.004]; // wait 4/1000 of second, 0.002 it's OK on my computer, I use 0.004 to be safe, increase it If you still have issues
}
CFRelease(keyEvent);
}
}
return 0;
}
Este código usa un bucle para escribir un carácter en cada iteración (es más lento que el primer código).
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
if (argc > 1) {
NSString *theString = [NSString stringWithUTF8String:argv[1]];
UniChar uChar;
CGEventRef keyEvent = CGEventCreateKeyboardEvent(nil, 0, true);
for (int i = 0; i < [theString length]; i++)
{
uChar = [theString characterAtIndex:i];
CGEventKeyboardSetUnicodeString(keyEvent, 1, &uChar);
CGEventPost(kCGHIDEventTap, keyEvent); // key down
CGEventSetType(keyEvent, kCGEventKeyUp);
CGEventPost(kCGHIDEventTap, keyEvent); // key up (type the character)
CGEventSetType(keyEvent, kCGEventKeyDown);
[NSThread sleepForTimeInterval:0.001]; // wait 1/1000 of second, no need of this line on my computer, I use 0.001 to be safe, increase it If you still have issues
}
CFRelease(keyEvent);
}
}
return 0;
}
Nota : este código funciona en macOS Sierra y debería funcionar en El Capitan , pero no en un sistema operativo anterior .
6- Seleccione el menú " Producto " --> " Construir ".
7- Seleccione el TypeCharacters
icono en la carpeta Producto , haga clic derecho y seleccione el menú " Mostrar en Finder " en el menú contextual.
8- Desde el Finder, mueve el archivo " TypeCharacters " a la carpeta deseada, sal de Xcode , eso es todo.
Desde un AppleScript , llame al ejecutable, así
set myString to "ùéèà ² ³ é ½ ₭ "
do shell script "'/full path/of/TypeCharacters' " & quoted form of myString
Una solución (con el portapapeles):
1 - Puedes usar un método de cacao desde una cáscara:
set tString to "² ³ é ½ ₭"
my stringToClipboard(tString)
tell application "System Events" to keystroke "v" using command down
on stringToClipboard(t1)
do shell script "/usr/bin/python -c 'import sys;from AppKit import NSPasteboard, NSPasteboardTypeString; cb=NSPasteboard.generalPasteboard();cb.declareTypes_owner_([NSPasteboardTypeString], None);cb.setString_forType_(sys.argv[1].decode(\"utf8\"), NSPasteboardTypeString)' " & quoted form of t1
end stringToClipboard
2 - O un subprograma Cocoa-AppleScript:
use framework "AppKit"
use scripting additions
set tString to "² ³ é ½ ₭"
my stringToClipboard(tString)
tell application "System Events" to keystroke "v" using command down
on stringToClipboard(t1)
set ca to current application
set cb to ca's NSPasteboard's generalPasteboard()
cb's declareTypes:{ca's NSPasteboardTypeString} owner:(missing value)
cb's setString:t1 forType:(ca's NSPasteboardTypeString)
end stringToClipboard
Para keystroke
un carácter, ese carácter debe asignarse a una tecla real en su teclado seleccionado.
Por ejemplo, puedo usar keystroke
é y ² perfectamente, porque estoy usando la distribución de teclado de PC en francés . Sin embargo, un teclado QWERTY estadounidense estándar no incluye esas teclas y no podrá keystroke
usarlas.
Puede definir todos sus juegos de caracteres especiales como variables, así
on specialKeys(input)
tell application "System Events"
keystroke input
end tell
end specialKeys
set characterSet1 to "²³é½₭ "
set characterSet2 to "³ "
set characterSet3 to "é "
set characterSet4 to "¬Ω "
set characterSet5 to "₭ "
set characterSet6 to characterSet1 & characterSet2 & characterSet3 & characterSet4 & characterSet5
specialKeys(characterSet1)
-- ² ³ é ½ ₭ is the result from calling specialKeys(characterSet1) After adding the text replacement for “a a a a a” in my keyboard preferences
Algunos caracteres especiales se pulsan correctamente cuando los establece como variables. Cualquiera de los caracteres especiales que configura como variables que no se pulsan correctamente, puede agregar "reemplazos de texto" en las preferencias del sistema para su teclado.
Asegúrese de seleccionar todos los elementos y arrastrarlos a su escritorio o donde sea. Esto creará un archivo .plist que será una copia de seguridad de su configuración original. Puede arrastrar este archivo en cualquier momento.
Luego, en ScriptEditor, asegúrese de tener habilitados los reemplazos de texto en el submenú "sustituciones" del menú de edición.
Podemos ingresar caracteres que no sean ASCII con el portapapeles:
tell application "System Events"
set textBuffer to "² ³ é ½ ₭"
repeat with i from 1 to count characters of textBuffer
set the clipboard to (character i of textBuffer)
delay 0.05
keystroke "v" using command down
end repeat
end tell
esfera de rubik
esfera de rubik
myString
supera los 20 caracteres, la cadena se truncará. Es decir, cualquier texto que siga al vigésimo carácter no se escribirá. ¿Sabes cómo arreglar ésto?jackjr300
esfera de rubik
#import <Foundation/Foundation.h>
línea de su código en su edición, pero esta línea aún es necesaria para una compilación exitosa. Sé que esta línea de código está ahí de forma predeterminada, pero existe cierta ambigüedad porque sus instrucciones dicen "borrar el texto de la ventana".esfera de rubik
= 278,932
pero se escribió la siguiente cadena:=2 78,93
.jackjr300
jackjr300
[NSThread sleepForTimeInterval:0.02]; // wait 2/100 of second, increase it If you still have issues.
. Actualicé el código en mi respuesta. Adjunto otro código en mi respuesta (este código puede escribir 20 caracteres en cada iteración en lugar de un carácter, pruébalo.esfera de rubik
esfera de rubik
jackjr300
sleepForTimeInterval:
método, pero esto es necesario para escribir una lista de caracteres en cada iteración (si la cadena contiene más de veinte caracteres, por supuesto). Actualicé mi respuesta (limpieza).esfera de rubik
TypeCharacters
script no puede escribir caracteres de nueva línea. Además, si la cadena contiene una nueva línea, entonces no escribirá la cadena en absoluto. ¿Sabe cómo conservar las líneas nuevas en el texto escrito? Gracias.BolígrafoBen