Re: Is there a way to prepare NSAttaributedString like "attribute runs"?
Re: Is there a way to prepare NSAttaributedString like "attribute runs"?
- Subject: Re: Is there a way to prepare NSAttaributedString like "attribute runs"?
- From: Takaaki Naganoya <email@hidden>
- Date: Mon, 11 Dec 2017 23:27:31 +0900
I did.
<AppleScript>
use AppleScript version "2.4"
use scripting additions
use framework "Foundation"
use framework "AppKit"
set fRes to choose file of type {"public.rtf"}
set aFilePath to current application's NSString's stringWithString:(POSIX path
of fRes)
set aData to current application's NSData's dataWithContentsOfFile:aFilePath
options:0 |error|:(missing value)
set theStyledText to current application's NSMutableAttributedString's
alloc()'s initWithData:aData options:(missing value)
documentAttributes:(missing value) |error|:(missing value)
set attrRes to getAttributeRunsFromAttrString(theStyledText) of me
(*
{{stringVal:"abcdefg
", colorVal:{0, 0, 0},
fontName:"Helvetica", fontSize:12.0},
{stringVal:"12234534353534", colorVal:{255,
0, 0}, fontName:"Helvetica",
fontSize:12.0}, {stringVal:"
dewhuiwheiuweriuwherwe
", colorVal:{0, 0, 0},
fontName:"Helvetica", fontSize:12.0},
{stringVal:"asda192837137129831
", colorVal:{255, 0, 0},
fontName:"Helvetica", fontSize:12.0}}
*)
on getAttributeRunsFromAttrString(theStyledText)
set thePureString to theStyledText's |string|() --pure string from
theStyledText
set styleList to {} ---for output
set theLength to theStyledText's |length|()
set startIndex to 0
repeat
set {theAtts, theRange} to theStyledText's
attributesAtIndex:startIndex longestEffectiveRange:(reference) inRange:{0,
theStyledText's |length|()}
--String
set aText to (thePureString's substringWithRange:theRange) as
string
--Color
set aColor to (theAtts's valueForKeyPath:"NSColor")
if aColor is not equal to missing value then
set aSpace to aColor's colorSpace()
set colName to aSpace's localizedName()
set colModel to aSpace's colorSpaceModel()
set colComps to aSpace's numberOfColorComponents()
if {colModel, colComps} = {1, 3} then --RGB Color Space
(maybe)
set aRed to (aColor's redComponent()) * 255
set aGreen to (aColor's greenComponent()) * 255
set aBlue to (aColor's blueComponent()) * 255
else
error "Detected color is not RGB (" & colName &
")"
end if
set colList to {aRed as integer, aGreen as integer,
aBlue as integer}
else
set colList to {0, 0, 0}
end if
--Font
set aFont to (theAtts's valueForKeyPath:"NSFont")
if aFont is not equal to missing value then
set aDFontName to aFont's displayName()
set aDFontSize to aFont's pointSize()
end if
set the end of styleList to {stringVal:aText, colorVal:colList,
fontName:aDFontName as string, fontSize:aDFontSize}
-- do stuff with theAtts here
set rangeEnd to current application's NSMaxRange(theRange)
if rangeEnd ≥ theLength - 1 then exit repeat
set startIndex to rangeEnd + 1
end repeat
return styleList
end getAttributeRunsFromAttrString
</AppleScript>
--
Takaaki Naganoya
email@hidden
http://piyocast.com/as/
> 2017/12/11 22:43、Takaaki Naganoya <email@hidden>のメール:
>
>> 2017/12/11 20:33、Shane Stanley <email@hidden>のメール:
>> On 11 Dec 2017, at 7:34 pm, Takaaki Naganoya <email@hidden> wrote:
>>> We can prepare styled text with TextEditor.app with “attribute runs”.
>>> So, we can filter text whose color is red. This is very useful and ordinary
>>> processing in AppleScript.
>>>
>>> I am looking for similar one with NSAttributedString in vain.
>>>
>>> Is there a way to prepare NSAttributedString like “attribute runs”?
>>
>> Sure. If you have an attributed string in a variable called attString and
>> run this code:
>>
>> set {theAtts, theRange} to attString's attributesAtIndex:0
>> longestEffectiveRange:(reference) inRange:{0, attString's |length|()}
>>
>> The variable theAtts will contain a dictionary of the attributes, where you
>> can check the color, and theRange will contain the equivalent of the
>> attribute run. You can put it in a repeat loop, each time changing the index
>> to just after the previous range. So something like:
>>
>> set theLength to attString's |length|()
>> set startIndex to 0
>> repeat
>> set {theAtts, theRange} to attString's attributesAtIndex:startIndex
>> longestEffectiveRange:(reference) inRange:{0, attString's |length|()}
>> -- do stuff with theAtts here
>> set rangeEnd to current application's NSMaxRange(theRange)
>> if rangeEnd ≥ theLength - 1 then exit repeat
>> set startIndex to rangeEnd + 1
>> end repeat
>>
>> Alternatively, you can use -attribute:atIndex:longestEffectiveRange:inRange:
>> instead, and get back the value for a particular attribute, like text color.
>
> Thanks Shane!
>
> By using your taught scripts, I made almost same as “attribute runs”.
> How can we get string value from NSAttributedString by range?
>
>
> <AppleScript>
> use AppleScript version "2.4"
> use scripting additions
> use framework "Foundation"
> use framework "AppKit"
>
> set fRes to choose file of type {"public.rtf"}
>
> set aFilePath to current application's NSString's stringWithString:(POSIX
> path of fRes)
> set aData to current application's NSData's dataWithContentsOfFile:aFilePath
> options:0 |error|:(missing value)
> set theStyledText to current application's NSMutableAttributedString's
> alloc()'s initWithData:aData options:(missing value)
> documentAttributes:(missing value) |error|:(missing value)
>
> set styleList to {}
>
> set theLength to theStyledText's |length|()
> set startIndex to 0
> repeat
> set {theAtts, theRange} to theStyledText's attributesAtIndex:startIndex
> longestEffectiveRange:(reference) inRange:{0, theStyledText's |length|()}
>
> --String
> --set aText to theAtts's |string|()
> --log aText
>
> --Color
> set aColor to (theAtts's valueForKeyPath:"NSColor")
> if aColor is not equal to missing value then
> set aRed to (aColor's redComponent()) * 255
> set aGreen to (aColor's greenComponent()) * 255
> set aBlue to (aColor's blueComponent()) * 255
> set colList to {aRed as integer, aGreen as integer, aBlue as
> integer}
> else
> set colList to {0, 0, 0}
> end if
>
> --Font
> set aFont to (theAtts's valueForKeyPath:"NSFont")
> if aFont is not equal to missing value then
> set aDFontName to aFont's displayName()
> set aDFontSize to aFont's pointSize()
> log {aDFontName, aDFontSize}
> end if
>
> set the end of styleList to {colorVal:colList, fontName:aDFontName as
> string, fontSize:aDFontSize}
>
> -- do stuff with theAtts here
> set rangeEnd to current application's NSMaxRange(theRange)
> if rangeEnd ≥ theLength - 1 then exit repeat
> set startIndex to rangeEnd + 1
> end repeat
>
> return styleList
> —> {{colorVal:{0, 0, 0},
> fontName:”Helvetica”, fontSize:12.0},
> {colorVal:{255, 0, 0},
> fontName:"Helvetica", fontSize:12.0},
> {colorVal:{0, 0, 0},
> fontName:"Helvetica", fontSize:12.0},
> {colorVal:{255, 0, 0},
> fontName:"Helvetica", fontSize:12.0}}
> </AppleScript>
>
>
> --
> Takaaki Naganoya
> email@hidden
> http://piyocast.com/as/
_______________________________________________
Do not post admin requests to the list. They will be ignored.
AppleScript-Users mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
Archives: http://lists.apple.com/archives/applescript-users
This email sent to email@hidden