Помилка AppleScript: я не в змозі перетворити насичений текст у звичайний текст


3

Я створив файл AppleScript (.scpt) під назвою " Введіть буфер обміну як однорядний звичайний текст ". Сценарій запускається комбінацією клавіш, встановленою FastScripts.

Бажана поведінка:

Я хочу, щоб цей скрипт взяв вміст буфера обміну, видалив усе форматування, а потім видалити будь-які розриви рядків або вкладки з цього тексту. Нарешті, я хочу, щоб сценарій набрав новий текст. Я хочу зберегти - не перезаписати - оригінальний вміст буфера обміну.

Конкретна проблема:

Конкретна помилка полягає в тому, що мій сценарій не видаляє все форматування з якогось багатого тексту.

Я не можу включати повноцінний текстовий вміст у публікацію Stack Exchange. Тому, щоб засвідчити мою точну проблему, завантажте цей .rtf-файл через Dropbox . Відкрийте цей файл в TextEdit.app. Виділіть речення та скопіюйте його до буфера обміну. Потім запустіть мій сценарій, коли ваш курсор знаходиться у формі, яка підтримує та показує розширений текст (так що ви можете бачити, що сценарій буде вводити розширений текст).

Ви помітите, що набране речення має багатий текстовий вміст і все ще містить елементи форматування. Ці елементи включають оригінальний шрифт тексту (Helvetica) та оригінальний розмір шрифту (12). Ці елементи мали бути відкинуті. Таким чином, або мій код є недбалим, або я знайшов справжню помилку в самому AppleScript. Я припускаю, що саме остання.

Найкоротший код, необхідний для відтворення помилки:

use AppleScript version "2.4"
use scripting additions
use framework "Foundation"
use framework "AppKit"

-- Back up clipboard contents:
set savedClipboard to my fetchStorableClipboard()

(*
    Converting the clipboard text to plain text to remove any formatting:
    From: http://lifehacker.com/127683/clear-text-formatting-on-os-x
*)
set theClipboardTextWithoutAnyFormatting to (the clipboard as text)

(*
    Removing line breaks and indentations in clipboard text:
    From: http://stackoverflow.com/a/12546965 
*)
set AppleScript's text item delimiters to {return & linefeed, return, linefeed, character id 8233, character id 8232}
set theClipboardTextWithoutAnyFormatting to text items of (theClipboardTextWithoutAnyFormatting as text)
set AppleScript's text item delimiters to {" "}
set theClipboardTextWithoutAnyLineBreaksOrFormatting to theClipboardTextWithoutAnyFormatting as text

set the clipboard to theClipboardTextWithoutAnyLineBreaksOrFormatting
tell application "System Events" to keystroke "v" using {command down}
delay 0.1 -- Without this delay, may restore clipboard before pasting.
-- Restore the original clipboard:
my putOnClipboard:savedClipboard

on fetchStorableClipboard()
    set aMutableArray to current application's NSMutableArray's array() -- used to store contents
    -- get the pasteboard and then its pasteboard items
    set thePasteboard to current application's NSPasteboard's generalPasteboard()
    -- loop through pasteboard items
    repeat with anItem in thePasteboard's pasteboardItems()
        -- make a new pasteboard item to store existing item's stuff
        set newPBItem to current application's NSPasteboardItem's alloc()'s init()
        -- get the types of data stored on the pasteboard item
        set theTypes to anItem's types()
        -- for each type, get the corresponding data and store it all in the new pasteboard item
        repeat with aType in theTypes
            set theData to (anItem's dataForType:aType)'s mutableCopy()
            if theData is not missing value then
                (newPBItem's setData:theData forType:aType)
            end if
        end repeat
        -- add new pasteboard item to array
        (aMutableArray's addObject:newPBItem)
    end repeat
    return aMutableArray
end fetchStorableClipboard

on putOnClipboard:theArray
    -- get pasteboard
    set thePasteboard to current application's NSPasteboard's generalPasteboard()
    -- clear it, then write new contents
    thePasteboard's clearContents()
    thePasteboard's writeObjects:theArray
end putOnClipboard:

По-перше, чи може хтось підтвердити, що зазначена проблема виникає на їхньому комп’ютері?

Якщо так, то як я можу видалити все форматування насиченого тексту в AppleScript, враховуючи цю помилку, яку я виявив?


1
Питання, що шукають довідки про налагодження ("чому цей код не працює?"), Повинні включати бажану поведінку, конкретну проблему чи помилку та найкоротший код, необхідний для відтворення її у самому питанні. Питання без чіткої постановки проблеми не корисні іншим читачам. Див.: Як створити приклад мінімального, повного та перевіреного .
гр

Одне, що ви сказали: " Потім, запустіть мій скрипт, коли ваш курсор знаходиться у формі, яка підтримує та показує багатий текст ". Чи можете ви надати та приклад цієї " форми ", доступної для всіх?
користувач3439894

@ user3439894 Що я мав на увазі під цим реченням, це те, що, очевидно, слід "набрати як однорядний звичайний текст" у формі, яка показує розширене форматування тексту, якщо вони хотіли стати свідком про помилку (тобто, форматування результатів розширеного тексту результатів сценарію). В іншому випадку помилка маскується, як ви автоматично бачите звичайний текст результату сценарію. Наприклад, документ Microsoft Word, документ TextEdit .rtf та повідомлення електронної пошти демонструватимуть форматування розширеного тексту. Коментар або відповідь Stack Exchange не відповів би.
сфера

@grgarside Я щойно відредагував своє запитання, щоб воно відповідало правилам щодо питань налагодження.
сфера

Відповіді:


1

Оскільки the clipboardкоманда додає інші типи автоматично, протестуйте цей сценарій:

set the clipboard to "hello" as string
delay 1
return clipboard info

результат -> {{Unicode текст, 10}, {рядок, 5}, {стилі брухту, 22}, {«клас utf8», 5}, {«клас ut16», 12}, {стилі брухту, 22 }}


Щоб уникнути стилів, використовуйте методи NSPasteboard :

-- *** add the missing lines from your script here  ***
--- set the clipboard to theClipboardTextWithoutAnyLineBreaksOrFormatting -- don't use this command to avoid the scrap styles type.
my putTextOnClipboard:theClipboardTextWithoutAnyLineBreaksOrFormatting -- use this method to put some string in the clipboard.

tell application "System Events" to keystroke "v" using {command down}
delay 0.1 -- Without this delay, may restore clipboard before pasting.
-- Restore the original clipboard:
my putOnClipboard:savedClipboard


on putTextOnClipboard:t
    set thePasteboard to current application's NSPasteboard's generalPasteboard()
    thePasteboard's clearContents()
    thePasteboard's declareTypes:{current application's NSPasteboardTypeString} owner:(missing value)
    thePasteboard's setString:t forType:(current application's NSPasteboardTypeString)
    --> now the clipboard contains these types only: class utf8», «class ut16», string and Unicode text)
end putTextOnClipboard:

1

Тестуючи свій код, а потім і власний простий код AppleScript , я можу відтворити (небажану) поведінку до певної міри. Я погоджуюся, що поведінка не є тим, що хотілося, і може вважатися помилкою, однак вирішення трохи неприємно .

У цьому методі замість встановлення theClipboardTextWithoutAnyLineBreaksOrFormattingбезпосередньо в буфер обміну, тому що тут проблема полягає в тому , що він буде записаний у тимчасовий файл, потім розміщений у буфері обміну за pbcopyдопомогою do shell script команди, а потім тимчасовий файл видаляється. Потім його можна вставити до цільової точки вставки.

Щоб перевірити код вирішення нижче, коментуйте set the clipboard to theClipboardTextWithoutAnyLineBreaksOrFormattingрядок, а потім розмістіть код обходу безпосередньо після нього та перед tell application "System Events" to keystroke "v" using {command down}рядком.

set tempFileToRead to POSIX path of (path to desktop) & ".tmpfile"
try
    set referenceNumber to open for access tempFileToRead with write permission
    write theClipboardTextWithoutAnyLineBreaksOrFormatting to referenceNumber
    close access referenceNumber
on error eStr number eNum
    display dialog eStr & " number " & eNum buttons {"OK"} default button 1 with title "File I/O Error..." with icon caution
    try
        close access referenceNumber
    end try
    return
end try
do shell script "pbcopy<" & tempFileToRead & "; rm " & tempFileToRead

Ваше рішення вирішує проблему, і рішення, яке надає @ jackjr300, робить так само: набирається справді звичайний текст вмісту буфера обміну. Чому ви кажете, що це "може вважатися помилкою"? Чи не поведінка AppleScript, яку я описав досить чітко, виявила помилку, оскільки, коли оголошувати змінну as text, насичений шрифт тексту та розмір шрифту не слід зберігати?
сфера

@ rubik сфера. Причина, по якій я її сформулював так, як це я зробила, це тому, що я був зосереджений більше на вирішенні питання, а не на самій проблемі. Я вважаю це помилкою, так! Ви повинні подати звіт про помилку в Apple.
користувач3439894

ГАРАЗД. Я не маю досвіду роботи з будь-якими іншими мовами програмування. Здається, у AppleScript більше помилок, ніж у інших мовах? Ми з вами особисто виявили кілька подібних помилок в AppleScript, і мені просто цікаво, якщо це відповідає курсу.
сфера
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.