Menu

Skip to content
AppleScriptの穴
  • Home
  • Products
  • Books
  • Docs
  • Events
  • Forum
  • About This Blog
  • License
  • 仕事依頼

AppleScriptの穴

Useful & Practical AppleScript archive. Click '★Click Here to Open This Script' Link to download each AppleScript

カテゴリー: Font

AS書類を書式で分解して再構成

Posted on 1月 12 by Takaaki Naganoya

AppleScriptの書類を読み込んでNSAttributedStringに変換し、書式情報にもとづいてNSDictionary in NSArrayに変換。この状態でデータ抽出などを行なっていたのですが、このデータをもとにNSAttributedStringに再構成するAppleScriptです。

本Scriptの通しの処理内容としては、読み込んだAppleScriptを書式情報をもとに分解して、再構成するという……大豆から豆腐を作って、豆腐を崩して豆を得る、みたいな内容です。

NSAttributedStringを再構成する部分の処理を書いていなかったので、必要に迫られて書いてみました。

AppleScript構文色分け設定情報をもとに処理するため、色分け設定で複数の構文要素で同じ色を指定している場合にはエラーを返します。単にNSAttributedStringを解釈して再構成する、といった処理であればAppleScript構文色分け設定へのアクセス自体は必要ないところですが、すでに不可分なレベルで組み込まれているため、現状ではそのままです。

いっそ、こうした処理をする前にplistをバックアップし、必要な情報を書き込んだplistを設定ファイルとして使用するといった処理を行った方がいいのかもしれません。これまでは、「そんな処理はとても行えない」と判断していましたが、よくよく考えればとくに苦労せずに実現できそうです。

AppleScript名:AS書類を書式で分解して再構成.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2025/01/12
—
–  Copyright © 2025 Piyomaru Software, All Rights Reserved
—

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

property NSFont : a reference to current application’s NSFont
property NSColor : a reference to current application’s NSColor
property |NSURL| : a reference to current application’s |NSURL|
property NSString : a reference to current application’s NSString
property OSAScript : a reference to current application’s OSAScript
property NSDictionary : a reference to current application’s NSDictionary
property NSUnarchiver : a reference to current application’s NSUnarchiver
property NSMutableDictionary : a reference to current application’s NSMutableDictionary
property NSFontAttributeName : a reference to current application’s NSFontAttributeName
property NSMutableAttributedString : a reference to current application’s NSMutableAttributedString
property NSForegroundColorAttributeName : a reference to current application’s NSForegroundColorAttributeName

property asCol : {}

set asCol to getAppleScriptSourceColors() of me –AppleScript構文色分け設定をplistから読み込む

set aFile to POSIX path of (choose file of type {"com.apple.applescript.script", "com.apple.applescript.script-bundle"})
set aURL to |NSURL|’s fileURLWithPath:(aFile)
set theScript to current application’s OSAScript’s alloc()’s initWithContentsOfURL:aURL |error|:(missing value)
set styledText to theScript’s richTextSource()

–Styled TextをDictionarry in Listに
set sRes to getAttributeRunsFromAttrStringRBO(styledText) of styleTextToDict

–Dictionarry in ListをStyled Textに再構成
set bRes to retAttributedStringFromAttrDict(sRes) of attrDictToAttrStr

script styleTextToDict
  use AppleScript
  
use framework "Foundation"
  
use framework "AppKit"
  
use scripting additions
  
property parent : AppleScript
  
  
–Styled Textを
  
on getAttributeRunsFromAttrStringRBO(theStyledText)
    script aSpd
      property styleList : {}
    end script
    
    
set (styleList of aSpd) to {} —for output
    
    
set thePureString to theStyledText’s |string|() –pure string from theStyledText
    
    
set theLength to theStyledText’s |length|()
    
set startIndex to 0
    
set aCount to 0
    
    
repeat until (startIndex = theLength)
      set {theAtts, theRange} to theStyledText’s attributesAtIndex:startIndex longestEffectiveRange:(reference) inRange:{startIndex, theLength – startIndex}
      
      
–String  
      
set aText to (thePureString’s substringWithRange:theRange) as string
      
set strLen to (length of aText)
      
      
–Color
      
set aColor to (theAtts’s valueForKeyPath:"NSColor")
      
if aColor is not equal to missing value then
        set aSpace to aColor’s colorSpace()
        
        
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} –for comparison
        
set colStrForFind to (aRed as integer as string) & " " & (aGreen as integer as string) & " " & (aBlue as integer as string) –for filtering
      else
        set colList to {0, 0, 0}
        
set colStrForFind 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
      
      
–Range
      
set the end of (styleList of aSpd) to {stringVal:aText, atrIndex:aCount, colorStr:colStrForFind, colorVal:colList, fontName:aDFontName as string, fontSize:aDFontSize}
      
set startIndex to current application’s NSMaxRange(theRange)
      
      
set aCount to aCount + 1
    end repeat
    
    
return (styleList of aSpd)
    
  end getAttributeRunsFromAttrStringRBO
  
  
–NSColorからRGBの値を取り出す
  
on retColListFromNSColor(aCol, aMAX as integer)
    using terms from scripting additions
      set aRed to round ((aCol’s redComponent()) * aMAX) rounding as taught in school
      
set aGreen to round ((aCol’s greenComponent()) * aMAX) rounding as taught in school
      
set aBlue to round ((aCol’s blueComponent()) * aMAX) rounding as taught in school
    end using terms from
    
if aRed > aMAX then set aRed to aMAX
    
if aGreen > aMAX then set aGreen to aMAX
    
if aBlue > aMAX then set aBlue to aMAX
    
    
return {aRed, aGreen, aBlue}
  end retColListFromNSColor
  
  
–aMaxValを最大値とする数値でNSColorを作成して返す
  
on makeNSColorFromRGBAval(redValue as integer, greenValue as integer, blueValue as integer, alphaValue as integer, aMaxVal as integer)
    set aRedCocoa to (redValue / aMaxVal) as real
    
set aGreenCocoa to (greenValue / aMaxVal) as real
    
set aBlueCocoa to (blueValue / aMaxVal) as real
    
set aAlphaCocoa to (alphaValue / aMaxVal) as real
    
set aColor to NSColor’s colorWithCalibratedRed:aRedCocoa green:aGreenCocoa blue:aBlueCocoa alpha:aAlphaCocoa
    
return aColor
  end makeNSColorFromRGBAval
  
end script

script attrDictToAttrStr
  use AppleScript
  
use framework "Foundation"
  
use framework "AppKit"
  
use scripting additions
  
property parent : AppleScript
  
  
–書式つきテキストを組み立てる(メイン側)
  
on retAttributedStringFromAttrDict(attrRes)
    script aSpd
      property styleList : {}
    end script
    
    
set (styleList of aSpd) to {} —for output
    
    
set allAttrStr to NSMutableAttributedString’s alloc()’s init()
    
    
repeat with i in attrRes
      set j to contents of i
      
set tmpAttrStr to makeRTFfromParameters(stringVal of j, fontName of j, fontSize of j, colorVal of j) of me
      
      (
allAttrStr’s appendAttributedString:tmpAttrStr)
    end repeat
    
    
return allAttrStr
  end retAttributedStringFromAttrDict
  
  
–書式つきテキストを組み立てる(パーツ組み立て用サブ側)
  
on makeRTFfromParameters(aStr as string, fontName as string, aFontSize as real, aColorList as list)
    –Font & Size
    
set aVal1 to NSFont’s fontWithName:fontName |size|:aFontSize
    
set aKey1 to (NSFontAttributeName)
    
    
–Color
    
copy aColorList to {rCol, gCol, bCOl}
    
set aVal2 to makeNSColorFromRGBAval(rCol, gCol, bCOl, 255, 255) of asCol
    
set aKey2 to (NSForegroundColorAttributeName)
    
    
set keyList to {aKey1, aKey2}
    
set valList to {aVal1, aVal2}
    
set attrsDictionary to NSMutableDictionary’s dictionaryWithObjects:valList forKeys:keyList
    
    
–Text
    
set attrStr to NSMutableAttributedString’s alloc()’s initWithString:aStr attributes:attrsDictionary
    
return attrStr
  end makeRTFfromParameters
  
  
  
–aMaxValを最大値とする数値でNSColorを作成して返す
  
on makeNSColorFromRGBAval(redValue as integer, greenValue as integer, blueValue as integer, alphaValue as integer, aMaxVal as integer)
    set aRedCocoa to (redValue / aMaxVal) as real
    
set aGreenCocoa to (greenValue / aMaxVal) as real
    
set aBlueCocoa to (blueValue / aMaxVal) as real
    
set aAlphaCocoa to (alphaValue / aMaxVal) as real
    
set aColor to NSColor’s colorWithCalibratedRed:aRedCocoa green:aGreenCocoa blue:aBlueCocoa alpha:aAlphaCocoa
    
return aColor
  end makeNSColorFromRGBAval
  
end script

–AppleScriptの構文色分けのカラー値をRGBで取得する
on getAppleScriptSourceColors()
  — get the plist info as a dictionary
  
set thePath to NSString’s stringWithString:"~/Library/Preferences/com.apple.applescript.plist"
  
set thePath to thePath’s stringByExpandingTildeInPath()
  
set theInfo to NSDictionary’s dictionaryWithContentsOfFile:thePath
  
  
— extract relevant part and loop through
  
set theArray to (theInfo’s valueForKey:"AppleScriptSourceAttributes") as list
  
  
set colList to {}
  
  
repeat with i from 1 to count of theArray
    set anEntry to item i of theArray
    
    
set colorData to NSColor of anEntry
    
set theColor to (NSUnarchiver’s unarchiveObjectWithData:colorData)
    
    
set {rVal, gVal, bVal} to retColListFromNSColor(theColor, 255) of me
    
    
set fontData to NSFont of anEntry
    
set theFont to (NSUnarchiver’s unarchiveObjectWithData:fontData)
    
    
set aFontName to theFont’s displayName() as text
    
set aFontSize to theFont’s pointSize()
    
    
set aColRec to {redValue:rVal, greenValue:gVal, blueValue:bVal, fontName:aFontName, fontSize:aFontSize}
    
    
set the end of colList to aColRec
  end repeat
  
  
return colList
end getAppleScriptSourceColors

–NSColorからRGBの値を取り出す
on retColListFromNSColor(aCol, aMAX as integer)
  using terms from scripting additions
    set aRed to round ((aCol’s redComponent()) * aMAX) rounding as taught in school
    
set aGreen to round ((aCol’s greenComponent()) * aMAX) rounding as taught in school
    
set aBlue to round ((aCol’s blueComponent()) * aMAX) rounding as taught in school
  end using terms from
  
  
if aRed > aMAX then set aRed to aMAX
  
if aGreen > aMAX then set aGreen to aMAX
  
if aBlue > aMAX then set aBlue to aMAX
  
  
return {aRed, aGreen, aBlue}
end retColListFromNSColor

★Click Here to Open This Script 

Posted in Color file Font OSA RTF | Tagged 13.0savvy 14.0savvy 15.0savvy NSAttributedString NSColor NSDictionary NSFont NSMutableAttributedString NSMutableDictionary NSString NSUnarchiver NSURL OSAScript | Leave a comment

Pagesで選択中のテキストフレーム内のテキストを、指定記号の前まで太らせる

Posted on 11月 10, 2024 by Takaaki Naganoya

以前にKeynote用に作っておいたAppleScriptを、Pages用に書き直しました。

Pages書類、主に奥付けのテキストなどで、「項目名」「:」(セパレータ)「内容」みたいに列挙している箇所を行頭からセパレータの場所の前まで太字の書体に変更します。ヒラギノ角ゴシックでチェックしており、欧文フォントは考慮していません。

Pages v14.2+macOS 15.2Betaで実験しています。


▲実行前


▲実行後

AppleScript名:フォントを記号の前まで太らせる.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/01
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

–セパレータリスト、表記ゆらぎ対応(ゆらぎ表記個数は可変)
property separatorList : {{":", ":"}, {"mm", "㎜"}, {"cm", "㎝"}}

tell application "Pages"
  tell front document
    set aSel to selection
    
    
    
–Keynote上の選択中のオブジェクトでループ
    
repeat with i in aSel
      set j to contents of i
      
set tmpClass to class of j
      
      
      
–選択中のオブジェクトがテキストアイテムの場合に…….
      
if tmpClass = shape then
        set objText to object text of j
        
set fontName to font of object text of j
        
set fontSize to size of object text of j
        
        
        
–フォントを太らせる(ウェイトを上げる)
        
set fFamilyCount to countFontsInItsFamily(fontName) of me
        
if fFamilyCount = 2 then
          
          
–ヒラギノ角ゴProN W3 → ヒラギノ角ゴProN W6
          
set newFont to incrementFontWeight(fontName, 1) of me
          
        else if fFamilyCount > 4 then
          –ヒラギノ角ゴシック Wn のウェイトを上げ
          
set newFont to incrementFontWeight(fontName, 4) of me
          
        end if
        
        
set aCount to 1
        
set tList to splitByLInes(objText) of me
        
        
        
–行ごとにParseした行ごとのテキストでループ
        
repeat with ii in tList
          set jj to contents of ii
          
          
set anOffset to 0
          
          
–セパレータでループ
          
repeat with iii in separatorList
            –セパレータの「ゆらぎ」表記を考慮してループ
            
repeat with iiii in iii
              set jjjj to contents of iiii
              
set anOffset to offset of jjjj in jj
              
              
if anOffset is not equal to 0 then
                exit repeat
              end if
            end repeat
            
            
if anOffset is not equal to 0 then exit repeat
            
          end repeat
          
          
if anOffset is not equal to 0 then
            try
              set font of characters 1 thru (anOffset – 1) of paragraph aCount of object text of j to newFont
            end try
          end if
          
          
set aCount to aCount + 1
          
        end repeat
      end if
    end repeat
  end tell
end tell

–テキストを行ごとにParse
on splitByLInes(someText) — free to a good home
  set theString to current application’s NSString’s stringWithString:someText
  
set theList to theString’s componentsSeparatedByCharactersInSet:(current application’s NSCharacterSet’s newlineCharacterSet())
  
return theList as list
end splitByLInes

–フォントを太らせる。欧文フォントは考慮していない(別の方法で行う)
on incrementFontWeight(psFontName, incNum)
  set aFont to current application’s NSFont’s fontWithName:psFontName |size|:9.0
  
–> (NSCTFont) "HiraginoSans-W0 9.00 pt. P [] (0x12870af00) fobj=0x11b1e90d0, spc=1.98"
  
  
set fontM to current application’s NSFontManager’s sharedFontManager()
  
  
repeat incNum times
    set aFont to fontM’s convertWeight:true ofFont:aFont
  end repeat
  
  
return (aFont’s fontName()) as string
end incrementFontWeight

–指定フォントのファミリーに属するフォント数を取得
on countFontsInItsFamily(aPSName)
  set aFont to current application’s NSFont’s fontWithName:(aPSName) |size|:9.0
  
set aFamily to aFont’s familyName()
  
set fMan to current application’s NSFontManager’s sharedFontManager()
  
set fList to fMan’s availableMembersOfFontFamily:aFamily
  
return length of (fList as list)
end countFontsInItsFamily

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy Pages | Leave a comment

全フォントのmostCompatibleStringEncodingを求めて集計

Posted on 11月 6, 2024 by Takaaki Naganoya

使用中のmacOS環境にインストールされているフォントのmostCompatibleStringEncodingを求めて、集計出力するAppleScriptです。

mostCompatibleStringEncodingはフォントが対応しているエンコーディングということで、普通そんなものはないように思えますが、EnglishなどのAscii & Numelicだけの言語用フォントであれば、「それにしか対応していない」という意味でのmostCompatibleStringEncodingはあるんじゃないかと。

一応調査するために書いてみたものです。バーコード系のフォントやドットフォントが該当しそうな感じです。

AppleScript名:全フォントのmostCompatibleStringEncodingを求める.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/06
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—
use AppleScript
use scripting additions
use framework "Foundation"

property NSFont : a reference to current application’s NSFont
property NSPredicate : a reference to current application’s NSPredicate
property NSFontManager : a reference to current application’s NSFontManager

script spdf
  property fList : {}
  
property outList : {}
end script

set (outList of spdf) to {}
set (fList of spdf) to getEveryFontPSName() of me

repeat with i in (fList of spdf)
  set j to contents of i
  
set aEnc to chkFontsCompatibleEncoding(j) of me
  
–if aEnc is not equal to "default" then set the end of (outList of spdf) to {fontEncoding:aEnc}
  
set the end of (outList of spdf) to {fontEncoding:aEnc}
end repeat

set aCountedList to countEachRecord((outList of spdf)) of me
–> {{aCount:1, aData:{fontEncoding:"NSSymbolStringEncoding"}}, {aCount:860, aData:{fontEncoding:"default"}}, {aCount:1005, aData:{fontEncoding:"NSMacOSRomanStringEncoding"}}}

–Rec in Listの登場頻度を集計して出力
on countEachRecord(aRecList)
  set theCountedSet to current application’s NSCountedSet’s |set|()
  
repeat with i in aRecList
    set j to contents of i
    (
theCountedSet’s addObject:j)
  end repeat
  
  
set theEnumerator to theCountedSet’s objectEnumerator()
  
set anArray to current application’s NSMutableArray’s alloc()’s init()
  
  
repeat
    set aDict to current application’s NSMutableDictionary’s alloc()’s init()
    
    
set aValue to theEnumerator’s nextObject()
    
if aValue is missing value then exit repeat
    
    
set aCount to theCountedSet’s countForObject:aValue
    
    
aDict’s setObject:aCount forKey:"aCount"
    
aDict’s setObject:aValue forKey:"aData"
    
anArray’s addObject:aDict
  end repeat
  
  
return anArray as anything
end countEachRecord

on getEveryFontPSName()
  script spd
    property aList : {}
  end script
  
  
set aFontList to NSFontManager’s sharedFontManager()’s availableFonts()
  
set thePred to NSPredicate’s predicateWithFormat:"NOT SELF BEGINSWITH ’.’"
  
set aFontList to (aFontList’s filteredArrayUsingPredicate:thePred) as list
  
  
set aList of spd to {}
  
repeat with i in aFontList
    set aName to contents of i
    
set the end of aList of spd to aName
  end repeat
  
  
return aList of spd
end getEveryFontPSName

on chkFontsCompatibleEncoding(fontPSName as string)
  set aFont to current application’s NSFont’s fontWithName:(fontPSName) |size|:16
  
  
if aFont’s mostCompatibleStringEncoding() = (current application’s NSASCIIStringEncoding) then
    return "NSASCIIStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSNEXTSTEPStringEncoding) then
    return "NSNEXTSTEPStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSJapaneseEUCStringEncoding) then
    return "NSJapaneseEUCStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF8StringEncoding) then
    return "NSUTF8StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSISOLatin1StringEncoding) then
    return "NSISOLatin1StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSSymbolStringEncoding) then
    return "NSSymbolStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSNonLossyASCIIStringEncoding) then
    return "NSNonLossyASCIIStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSShiftJISStringEncoding) then
    return "NSShiftJISStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSISOLatin2StringEncoding) then
    return "NSISOLatin2StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUnicodeStringEncoding) then
    return "NSUnicodeStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSWindowsCP1251StringEncoding) then
    return "NSWindowsCP1251StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSWindowsCP1252StringEncoding) then
    return "NSWindowsCP1252StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSWindowsCP1253StringEncoding) then
    return "NSWindowsCP1253StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSWindowsCP1254StringEncoding) then
    return "NSWindowsCP1254StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSWindowsCP1250StringEncoding) then
    return "NSWindowsCP1250StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSISO2022JPStringEncoding) then
    return "NSISO2022JPStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSMacOSRomanStringEncoding) then
    return "NSMacOSRomanStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSProprietaryStringEncoding) then
    return "NSProprietaryStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSISO2022JPStringEncoding) then
    return "NSISO2022JPStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSJapaneseEUCStringEncoding) then
    return "NSJapaneseEUCStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSShiftJISStringEncoding) then
    return "NSShiftJISStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF16BigEndianStringEncoding) then
    return "NSUTF16BigEndianStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF16LittleEndianStringEncoding) then
    return "NSUTF16LittleEndianStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF16StringEncoding) then
    return "NSUTF16StringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUnicodeStringEncoding) then
    return "NSUnicodeStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF32BigEndianStringEncoding) then
    return "NSUTF32BigEndianStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF32LittleEndianStringEncoding) then
    return "NSUTF32LittleEndianStringEncoding"
  else if aFont’s mostCompatibleStringEncoding() = (current application’s NSUTF32StringEncoding) then
    return "NSUTF32StringEncoding"
  else
    return "default"
  end if
end chkFontsCompatibleEncoding

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy | Leave a comment

PostScript名で指定のフォントのTraitMaskを付与する_v3

Posted on 11月 3, 2024 by Takaaki Naganoya

PostScript名で指定したフォントにTraitMaskを付与し、そのPostScript名の文字列を返すAppleScriptです。

指定フォントのBoldバージョンを取得する、という用途においてはこれで済むのですが、すでにBold指定されたフォントを渡したときにExtra Boldのフォントを返すという処理には使えません。

AppleScript名:PostScript名で指定のフォントのTraitMaskを付与する_v3.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/10/19
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

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

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

set aName to "TimesNewRomanPSMT"
set traitsNum to (current application’s NSBoldFontMask)
set bName to getTraitedFontName(aName, traitsNum) of me
–> "TimesNewRomanPS-BoldMT"

on getTraitedFontName(aName, traitsNum)
  set bFont to getBoldFontObj(aName, traitsNum) of me
  
return bFont’s fontName() as string
end getTraitedFontName

–BoldフォントのNSFontを取得
on getBoldFontObj(aName, traitsNum)
  set aFont to current application’s NSFont’s fontWithName:aName |size|:9.0
  
–> (NSCTFont) "HelveticaNeue 9.00 pt. P [] (0x4864eb0e0) fobj=0x12ee73e90, spc=2.50"
  
  
set fontM to current application’s NSFontManager’s sharedFontManager()
  
  
–指定のフォントがBoldのtraitを持っているかをチェック
  
set fRes to fontM’s fontNamed:aName hasTraits:traitsNum
  
if (fRes as boolean) = true then return aFont –すでに該当する
  
  
set bFont to fontM’s convertFont:(aFont) toHaveTrait:(traitsNum)
  
  
return bFont
end getBoldFontObj

–指定フォントのファミリーに属するフォント数を取得
on countFontsInItsFamily(aPSName)
  set aFont to current application’s NSFont’s fontWithName:(aPSName) |size|:9.0
  
set aFamily to aFont’s familyName()
  
set fMan to current application’s NSFontManager’s sharedFontManager()
  
set fList to fMan’s availableMembersOfFontFamily:aFamily
  
return length of (fList as list)
end countFontsInItsFamily

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy NSFontManager | Leave a comment

全フォントから全traitsを調べる v2

Posted on 11月 3, 2024 by Takaaki Naganoya

macOSにインストールされているすべてのフォントに対して、すべてのtraitsを確認して、タブ区切りテキストとして出力するAppleScriptです。

実際にNumbersの表データに入力して、Numbers上のフィルタを用いてtraitsの分布状況を調べてみました。とくに問題はないようです。

AppleScript名:全フォントから全traitsを調べる v2.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/03
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSPredicate : a reference to current application’s NSPredicate
property NSFontManager : a reference to current application’s NSFontManager

set fontStatList to {}
set fList to getEveryFontPSName() of me
set fontM to NSFontManager’s sharedFontManager()

repeat with i in fList
  set j to contents of i
  
set f1Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSItalicFontMask)) as integer
  
set f2Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSBoldFontMask)) as integer
  
set f3Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSUnboldFontMask)) as integer
  
set f4Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSNonStandardCharacterSetFontMask)) as integer
  
set f5Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSNarrowFontMask)) as integer
  
set f6Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSExpandedFontMask)) as integer
  
set f7Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSCondensedFontMask)) as integer
  
set f8Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSSmallCapsFontMask)) as integer
  
set f9Res to (fontM’s fontNamed:(j) hasTraits:(current application’s NSPosterFontMask)) as integer
  
set fARes to (fontM’s fontNamed:(j) hasTraits:(current application’s NSCompressedFontMask)) as integer
  
set fBRes to (fontM’s fontNamed:(j) hasTraits:(current application’s NSFixedPitchFontMask)) as integer
  
set fCRes to (fontM’s fontNamed:(j) hasTraits:(current application’s NSUnitalicFontMask)) as integer
  
set the end of fontStatList to {j, f1Res, f2Res, f3Res, f4Res, f5Res, f6Res, f7Res, f8Res, f9Res, fARes, fBRes, fCRes}
end repeat

–結果のリストをタブ区切りテキストに
set sRes to make2DList2TabSepMultilineText(fontStatList) of me
–>
(*
07LightNovelPOP  0  1  0  0  0  0  0  0  0  0  0  0
07YasashisaGothic  0  0  0  0  0  0  0  0  0  0  0  0
07YasashisaGothicBold  0  0  0  0  0  0  0  0  0  0  0  0
7barP  0  0  0  0  0  0  0  0  0  0  0  0
7barSP  0  0  0  0  0  0  0  0  0  0  0  0……..
*)

on getEveryFontPSName()
  set aFontList to NSFontManager’s sharedFontManager()’s availableFonts()
  
set thePred to NSPredicate’s predicateWithFormat:"NOT SELF BEGINSWITH ’.’"
  
set aFontList to (aFontList’s filteredArrayUsingPredicate:thePred) as list
  
  
set aList to {}
  
repeat with i in aFontList
    set aName to contents of i
    
set the end of aList to aName
  end repeat
  
  
return aList
end getEveryFontPSName

on make2DList2TabSepMultilineText(aList)
  set aStr to ""
  
  
repeat with i in aList
    set j to contents of i
    
set tmpStr to list2TABseparatedText(j) of me
    
set aStr to aStr & tmpStr & return
  end repeat
  
  
return aStr
end make2DList2TabSepMultilineText

–リストをタブ区切りのテキストに変換
on list2TABseparatedText(aList)
  set curDelim to AppleScript’s text item delimiters
  
set AppleScript’s text item delimiters to tab
  
set bList to aList as string
  
set AppleScript’s text item delimiters to curDelim
  
return bList
end list2TABseparatedText

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy NSFontManager | Leave a comment

指定フォントの指定Traitが存在するかをチェック

Posted on 11月 3, 2024 by Takaaki Naganoya

欧文フォントを太らせる処理を行う下調べとして、指定PostScriptフォント名のフォントファミリーに、指定のバリエーションが存在するかどうかを調べるAppleScriptを書いてみました。

Classic MacOS時代はフォントを変形させてボールド表現を行ったり、イタリック表現を行うなどの機能が実装されていました。

一方、OPENSTEPを源流に持つmacOSは、さまざまなバリエーションのフォントをあらかじめ用意しておくことが必要です。このあたりの仕様は、なんとなく技術的な後退を感じますが、まあいいでしょう。

そして、NSFontManagerの機能を用いて、指定のフォントバリエーション(ボールド)が存在するかを確認するはずだったのが本AppleScriptです。

ただ、実際に試してみたところ、どのフォントを指定してもダメでした。「ボールド書体はない」と言われます。あれ????


▲SF Pro Text、18のスタイルを持つ


▲Skia、10のスタイルを持つ

そこで、macOSに入っているすべてのフォントのPostScript名を取得して、すべてのフォントのTraitsをチェック。

結果、けっこうな数のフォントがboldのTraitsを持っている、と返ってきました。名前に「Bold」と入っているフォントばかりが。

つまり、NSFontManagerのfontNamed:① hasTraits:② は、指定のフォント自体にTraitsがあるのか調べるAPIであったということです。自分が誤解していたようでした。

AppleScript名:指定フォントの指定Traitsが存在するかをチェック.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/02
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

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

–set aName to "HelveticaNeue"
–set aName to "Verdana"
–set aName to "TimesNewRomanPSMT"
set aName to "SFProText-Regular"

–指定のフォントがBoldのtraitを持っているかをチェック
set fontM to current application’s NSFontManager’s sharedFontManager()
set fRes to fontM’s fontNamed:aName hasTraits:(current application’s NSBoldFontMask)
–> false(みんなfalse)

★Click Here to Open This Script 

AppleScript名:全フォントからtraitsを調べる.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/03
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSPredicate : a reference to current application’s NSPredicate
property NSFontManager : a reference to current application’s NSFontManager

set okList to {}
set fList to getEveryFontPSName() of me
set fontM to NSFontManager’s sharedFontManager()

repeat with i in fList
  set j to contents of i
  
set fRes to (fontM’s fontNamed:(j) hasTraits:(current application’s NSBoldFontMask))
  
if fRes as boolean = true then set the end of okList to j
end repeat

return okList

on getEveryFontPSName()
  set aFontList to NSFontManager’s sharedFontManager()’s availableFonts()
  
set thePred to NSPredicate’s predicateWithFormat:"NOT SELF BEGINSWITH ’.’"
  
set aFontList to (aFontList’s filteredArrayUsingPredicate:thePred) as list
  
  
set aList to {}
  
repeat with i in aFontList
    set aName to contents of i
    
set the end of aList to aName
  end repeat
  
  
return aList
end getEveryFontPSName

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy | Leave a comment

Keynoteで選択中のtext itemの冒頭のフォントを太くする v2

Posted on 11月 1, 2024 by Takaaki Naganoya

Keynote書類で選択中のテキストアイテムのうち、各行の冒頭からマークの文字までの間を太文字にするAppleScriptです。

v1を改良し、さまざまな区切り記号に対応させるべく、改修を行なってみたものです。

当初は、各テキストアイテムの内部テキストを解析して、共通記号文字を計算して自動で認識処理を行なってみようかと考えていました。統計処理を行なって共通で登場する文字をピックアップさせることを検討していました。

ただ、これだと複数の選択アイテムで別々の区切り文字を採用している場合に対応できません。

統計処理を行わず、技術的にもっとレベルを下げ、「ゆらぎ」検出のためのオーソドックスな、ゆらぎ表記列挙リストを作って、ひたすらループで処理するように改変。


▲処理前 Keynoteの書類上でテキストアイテムを選択


▲処理後 各テキストアイテムで、指定の記号より前の部分の文字を太くした

なお、本Scriptは書式変更ターゲット文字のピックアップ性能を向上させたものであり、欧文フォントの処理を考慮したものにはなっていません。フォントファミリー内のウェイトを上げたフォントを求めるという処理を行なっています。

fFamilyCount = 2

の場合には、「ヒラギノ角ゴProN W3」を「ヒラギノ角ゴProN W6」に変更する処理を行います。

fFamilyCount > 4

の場合には、「ヒラギノ角ゴシック Wn」のウェイトを上げています。

もしも、利用中のMacにウェイトが多数含まれているフォントをインストールして、Keynote書類上でそのフォントを指定している場合には、ウェイトを上げたフォントを求める処理で、文字を太くするよう処理されることでしょう。

AppleScript名:選択中のtext itemの冒頭のフォントを太くする(フォントのWeightを変更)v2.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/11/01
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

–セパレータリスト、表記ゆらぎ対応(ゆらぎ表記個数は可変)
property separatorList : {{":", ":"}, {"mm", "㎜"}, {"cm", "cm"}}

tell application "Keynote"
  tell front document
    set aSel to selection
    
    
    
–Keynote上の選択中のオブジェクトでループ
    
repeat with i in aSel
      set j to contents of i
      
set tmpClass to class of j
      
      
      
–選択中のオブジェクトがテキストアイテムの場合に…….
      
if tmpClass = text item then
        set objText to object text of j
        
set fontName to font of object text of j
        
set fontSize to size of object text of j
        
        
        
–フォントを太らせる(ウェイトを上げる)
        
set fFamilyCount to countFontsInItsFamily(fontName) of me
        
if fFamilyCount = 2 then
          set newFont to incrementFontWeight(fontName, 1) of me
        else if fFamilyCount > 4 then
          set newFont to incrementFontWeight(fontName, 4) of me
        end if
        
        
set aCount to 1
        
set tList to splitByLInes(objText) of me
        
        
        
–行ごとにParseした行ごとのテキストでループ
        
repeat with ii in tList
          set jj to contents of ii
          
          
set anOffset to 0
          
          
–セパレータでループ
          
repeat with iii in separatorList
            –セパレータの「ゆらぎ」表記を考慮してループ
            
repeat with iiii in iii
              set jjjj to contents of iiii
              
set anOffset to offset of jjjj in jj
              
              
if anOffset is not equal to 0 then
                exit repeat
              end if
            end repeat
            
            
if anOffset is not equal to 0 then exit repeat
            
          end repeat
          
          
if anOffset is not equal to 0 then
            try
              set font of characters 1 thru (anOffset – 1) of paragraph aCount of object text of j to newFont
            end try
          end if
          
          
set aCount to aCount + 1
          
        end repeat
      end if
    end repeat
  end tell
end tell

–テキストを行ごとにParse
on splitByLInes(someText) — free to a good home
  set theString to current application’s NSString’s stringWithString:someText
  
set theList to theString’s componentsSeparatedByCharactersInSet:(current application’s NSCharacterSet’s newlineCharacterSet())
  
return theList as list
end splitByLInes

–フォントを太らせる。欧文フォントは考慮していない(別の方法で行う)
on incrementFontWeight(psFontName, incNum)
  set aFont to current application’s NSFont’s fontWithName:psFontName |size|:9.0
  
–> (NSCTFont) "HiraginoSans-W0 9.00 pt. P [] (0x12870af00) fobj=0x11b1e90d0, spc=1.98"
  
  
set fontM to current application’s NSFontManager’s sharedFontManager()
  
  
repeat incNum times
    set aFont to fontM’s convertWeight:true ofFont:aFont
  end repeat
  
  
return (aFont’s fontName()) as string
end incrementFontWeight

–指定フォントのファミリーに属するフォント数を取得
on countFontsInItsFamily(aPSName)
  set aFont to current application’s NSFont’s fontWithName:(aPSName) |size|:9.0
  
set aFamily to aFont’s familyName()
  
set fMan to current application’s NSFontManager’s sharedFontManager()
  
set fList to fMan’s availableMembersOfFontFamily:aFamily
  
return length of (fList as list)
end countFontsInItsFamily

★Click Here to Open This Script 

Posted in Font Text | Tagged 10.15savvy 11.0savvy 12.0savvy 13.0savvy 14.0savvy 15.0savvy Keynote | Leave a comment

Keynoteで選択中のtext itemの冒頭のフォントを太くする

Posted on 10月 19, 2024 by Takaaki Naganoya

Keynote書類で選択中のテキストアイテムのうち、各行の冒頭から「:」の文字までの間を太文字にするAppleScriptです。


▲処理範囲に入っている文字列


▲処理前


▲処理後

本Scriptは、処理内容が地味な割に、処理内容(の説明)が大変です。かなり複雑な処理をやっているためです。(フォント名を文字列で組み立てるなどの)もっと乱暴な処理もできるのですが、ここはあえて丁寧な処理を行なってみました。

Keynote書類上の選択中のText item(複数の場合もある)内のObject textにアクセス。ここで、文字情報、フォント情報、フォントサイズ情報、文字色情報などが取得できます。

フォントサイズ情報を取得して(テキストアイテム内はすべて同じフォントが指定されているものと想定)、フォント名がPostScript名で返ってくるので、NSFontManagerの機能を用いて、当該フォントが所属するフォントファミリーを求めます。さらに、そのファミリーにいくつのフォントが所属しているのかを求めます。

ここで想定しているのは、ヒラギノ角ゴ W3/W6かヒラギノ角ゴシックW0〜W9です。欧文フォントでは、ボールド書体がファミリー中に存在するかをチェックし、存在すればボールド書体を指定するといったまったく別の処理が必要です。本Scriptはとりあえずやりたいことを詰め込んで動くレベルにまとめただけで、汎用性はあまりありません。

また、Keynoteのtext item中の「行」(paragraph)へのアクセスが安定していません。改行をリターンキーだけで行うか、Shift-Returnで行うか、Control-Returnで行うかといった些細な操作の違いによって行カウントできる行数に差が発生します。

安全のためには、AppleScript上でRTF(NSMutableAttributedString)を作って、そこでフォントの変更を行なってtext itemのobject textに書き戻すのが理想的です。

AppleScript名:選択中のtext itemの冒頭のフォントを太くする.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/10/19
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

tell application "Keynote"
  tell front document
    set aSel to selection
    
    
repeat with i in aSel
      set j to contents of i
      
set tmpClass to class of j
      
      
if tmpClass = text item then
        set objText to object text of j
        
set fontName to font of object text of j
        
set fontSize to size of object text of j
        
        
–フォントを太らせる(ウェイトを上げる)
        
set fFamilyCount to countFontsInItsFamily(fontName) of me
        
if fFamilyCount = 2 then
          set newFont to incrementFontWeight(fontName, 1) of me
        else if fFamilyCount > 4 then
          set newFont to incrementFontWeight(fontName, 4) of me
        end if
        
        
set aCount to 1
        
set tList to splitByLInes(objText) of me
        
        
        
repeat with ii in tList
          set jj to contents of ii
          
set anOffset1 to offset of ":" in jj
          
set anOffset2 to offset of ":" in jj
          
          
if {anOffset1, anOffset2} is not equal to {0, 0} then
            if anOffset1 = 0 then
              set offRes to anOffset2
            else if anOffset2 = 0 then
              set offRes to anOffset1
            else
              set offRes to anOffset1
            end if
            
            
try
              set font of characters 1 thru offRes of paragraph aCount of object text of j to newFont
            end try
            
            
set aCount to aCount + 1
          end if
        end repeat
      end if
    end repeat
  end tell
end tell

–テキストを行ごとにParse
on splitByLInes(someText) — free to a good home
  set theString to current application’s NSString’s stringWithString:someText
  
set theList to theString’s componentsSeparatedByCharactersInSet:(current application’s NSCharacterSet’s newlineCharacterSet())
  
return theList as list
end splitByLInes

–フォントを太らせる。欧文フォントは考慮していない(別の方法で行う)
on incrementFontWeight(psFontName, incNum)
  set aFont to current application’s NSFont’s fontWithName:psFontName |size|:9.0
  
–> (NSCTFont) "HiraginoSans-W0 9.00 pt. P [] (0x12870af00) fobj=0x11b1e90d0, spc=1.98"
  
  
set fontM to current application’s NSFontManager’s sharedFontManager()
  
  
repeat incNum times
    set aFont to fontM’s convertWeight:true ofFont:aFont
  end repeat
  
  
return (aFont’s fontName()) as string
end incrementFontWeight

–指定フォントのファミリーに属するフォント数を取得
on countFontsInItsFamily(aPSName)
  set aFont to current application’s NSFont’s fontWithName:(aPSName) |size|:9.0
  
set aFamily to aFont’s familyName()
  
set fMan to current application’s NSFontManager’s sharedFontManager()
  
set fList to fMan’s availableMembersOfFontFamily:aFamily
  
return length of (fList as list)
end countFontsInItsFamily

★Click Here to Open This Script 

Posted in Font | Tagged 13.0savvy 14.0savvy 15.0savvy Keynote | Leave a comment

PostScript名で指定したフォントのウェイトを上げるループ処理のテスト

Posted on 10月 19, 2024 by Takaaki Naganoya

NSFontManagerを用いて、指定フォントのウェイト(太さ)を上げたり下げたりする処理ができますが、実際にやってみると「見えなかったもの」が見えてきます。

macOSには「ヒラギノ角ゴシック」のW0(PostScript名:HiraginoSans-W0)からW9(PostScript名:HiraginoSans-W9)まで異なるウェイトのフォントがインストールされています。そこで、W0から順次W9までウェイトを上げる処理を行なってみると、「ヒラギノ角ゴシックW2」にウェイトが割り振られていないことがわかります。

バグなのか、意図的なものなのか……多分バグだと思うのですが……。

AppleScript名:PostScript名で指定のフォントのウェイトを上げるループ.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/10/19
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

set aName to "HiraginoSans-W0"
set aFont to current application’s NSFont’s fontWithName:aName |size|:9.0
–> (NSCTFont) "HiraginoSans-W0 9.00 pt. P [] (0x12870af00) fobj=0x11b1e90d0, spc=1.98"

set fontM to current application’s NSFontManager’s sharedFontManager()
set fRes to fontM’s weightOfFont:(aFont)
–> 2

repeat 12 times
  set fRes to fontM’s weightOfFont:(aFont)
  
log (fRes as number)
  
  
set aFontName to aFont’s fontName()
  
log aFontName
  
  
(*2*)
  
(*(NSString) "HiraginoSans-W0"*)
  
  
(*3*)
  
(*(NSString) "HiraginoSans-W1"*)
  
  
— <– W2は?????
  
  
(*4*)
  
(*(NSString) "HiraginoSans-W3"*)
  
  
(*5*)
  
(*(NSString) "HiraginoSans-W4"*)
  
  
(*6*)
  
(*(NSString) "HiraginoSans-W5"*)
  
  
(*8*)
  
(*(NSString) "HiraginoSans-W6"*)
  
  
(*9*)
  
(*(NSString) "HiraginoSans-W7"*)
  
  
(*10*)
  
(*(NSString) "HiraginoSans-W8"*)
  
  
(*12*)
  
(*(NSString) "HiraginoSans-W9"*)
  
set aFont to fontM’s convertWeight:true ofFont:aFont
end repeat

★Click Here to Open This Script 

ヒラギノ角ゴシックW2のウェイトを取得したら3が返ってきました。ウェイトがW2とW3で重なっているんですね。

AppleScript名:PostScript名で指定のフォントのウェイトを取得.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/10/19
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use framework "AppKit"
use scripting additions

property NSFont : a reference to current application’s NSFont
property NSFontManager : a reference to current application’s NSFontManager

set aName to "HiraginoSans-W2"
set aFont to current application’s NSFont’s fontWithName:aName |size|:9.0
–> (NSCTFont) "HiraginoSans-W0 9.00 pt. P [] (0x12870af00) fobj=0x11b1e90d0, spc=1.98"

set fontM to current application’s NSFontManager’s sharedFontManager()

set fRes to fontM’s weightOfFont:(aFont)
–> 3

★Click Here to Open This Script 

Posted in Bug Font | Tagged 15.0savvy NSFont NSFontManager | Leave a comment

デフォルトインストールされたフォント名を取得するAppleScript

Posted on 8月 3, 2024 by Takaaki Naganoya

macOSにインストールされているフォントの情報をsystem_profiler経由で取得し、各フォントのパス情報をもとに、/System/Library/Fonts以下に入っているものだけを抽出して、フォント名をリストアップするAppleScriptです。

Pages書類に含まれているフォントのうち、デフォルトインストールされたものではないものを抽出するために、OSにデフォルトインストールされたものだけを取得すべく、基礎情報を得るために書いてみたものです(現在執筆中の電子書籍「Pages+AppleScriptで本をつくろう!」の付録Scriptとして用意しました)。

事前に何か設定するといった必要はありません。スクリプトエディタやScript Debuggerで実行するだけです。

AppleScriptからフォントの存在するパス情報はなかなか取得しにくい、FontBook.appがAppleScript非対応になったので、ほぼ無理なのですが、system_profilerから取得すれば、それほど難しくありません。

実行所要時間は、

  M1 Mac mini (macOS 13.6):6秒
  M2 Mac mini(macOS 14.6):10秒
  M2 MacBook Air(macOS 14.6):15秒

ぐらいで、M1 Mac miniの速さが光ります。OSの違いから、macOS 13.6環境ではallFontsが1168、macOS 14.6環境では1603とフォント数がどうやら異なっているのですが(M2 miniも同じ)、フォント数を考慮してもM1 Mac miniの処理の速さが光ります。

もしくは、macOSのバージョンの違いにより、system_profilerの実行速度が大きく異なるとか? macOS 13.6環境と14.6環境にそれほど差があるものなんでしょうか。

無駄な処理も入っていますが、いろいろチェックしながら作ったもので、ベンチマーク用に作ったものではありません。

# M2 Airってなんでこんなに時間がかかるんだろう? 放熱台に乗せて処理しているのに。処理のほとんどの時間がsystem_profilerの実行で消費しています

AppleScript名:OSデフォルトインストールされたフォント名を取得.scpt
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/08/03
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.4" — Yosemite (10.10) or later
use framework "Foundation"
use scripting additions

property NSArray : a reference to current application’s NSArray
property NSString : a reference to current application’s NSString
property NSPredicate : a reference to current application’s NSPredicate
property NSMutableArray : a reference to current application’s NSMutableArray
property NSMutableDictionary : a reference to current application’s NSMutableDictionary
property NSPropertyListFormat : a reference to current application’s NSPropertyListFormat
property NSUTF8StringEncoding : a reference to current application’s NSUTF8StringEncoding
property NSPropertyListImmutable : a reference to current application’s NSPropertyListImmutable
property NSPropertyListSerialization : a reference to current application’s NSPropertyListSerialization

script spd
  property sRes : missing value
  
property aSource : missing value
  
property bRes : missing value
  
property fontNames : {}
  
property fontPath : {}
  
property outList : {}
end script

–システムにインストールされているフォントの情報を全抽出
set sRes of spd to do shell script "system_profiler -xml SPFontsDataType"
set aSource of spd to first item of (readPlistFromStr(sRes of spd) of me)

–全フォント情報から、名称とパス情報を抽出
set bRes of spd to (((aSource of spd)’s valueForKeyPath:"_items"))
set fontNames of spd to ((bRes of spd)’s valueForKeyPath:"_name") as list
set fontPath of spd to ((bRes of spd)’s valueForKeyPath:"path") as list

–ループでOSデフォルトインストールされているフォントを抽出
set outList of spd to {}
set aCount to 1

repeat with i in (fontPath of spd)
  set j to contents of i
  
  
if j begins with "/System/Library/Fonts/" then
    –指定のフォントに複数のTypefaceが含まれていることを考慮し、情報を取り出す
    
set outItem to (((item aCount of (bRes of spd)))’s valueForKeyPath:"typefaces._name") as list
    
set the end of (outList of spd) to outItem
  end if
  
  
set aCount to aCount + 1
end repeat

–すべてのTypefaceを入れた入れ子の2D Listから1D Listに変換
set allFonts to FlattenList((outList of spd)) of me

–ドット(.)ではじまるフォントを除外
set outList to {}
repeat with i in allFonts
  set j to contents of i
  
if j does not start with "." then
    set the end of outList to j
  end if
end repeat

return outList

–stringのplistを読み込んでRecordに
on readPlistFromStr(theString)
  set aSource to NSString’s stringWithString:theString
  
set pListData to aSource’s dataUsingEncoding:(NSUTF8StringEncoding)
  
set aPlist to NSPropertyListSerialization’s propertyListFromData:pListData mutabilityOption:(NSPropertyListImmutable) format:(NSPropertyListFormat) errorDescription:(missing value)
  
return aPlist
end readPlistFromStr

–リストに入れたレコードを、指定の属性ラベルの値で抽出
on filterRecListByLabel(aRecList as list, aPredicate as string)
  set aArray to NSArray’s arrayWithArray:aRecList
  
  
set aPredicate to NSPredicate’s predicateWithFormat:aPredicate
  
set filteredArray to aArray’s filteredArrayUsingPredicate:aPredicate
  
  
set bList to filteredArray as list
  
return bList
end filterRecListByLabel

–リストに入れたレコードを、指定の属性ラベルの値で抽出
on filterRecListByLabel1(aRecList, aPredicate as string)
  set aArray to current application’s NSArray’s arrayWithArray:aRecList
  
set aPredicate to current application’s NSPredicate’s predicateWithFormat:aPredicate
  
set filteredArray to aArray’s filteredArrayUsingPredicate:aPredicate
  
return filteredArray
end filterRecListByLabel1

–By Paul Berkowitz
–2009年1月27日 2:24:08:JST
–Re: Flattening Nested Lists
on FlattenList(aList)
  set oldDelims to AppleScript’s text item delimiters
  
set AppleScript’s text item delimiters to {"????"}
  
set aString to aList as text
  
set aList to text items of aString
  
set AppleScript’s text item delimiters to oldDelims
  
return aList
end FlattenList

★Click Here to Open This Script 

Posted in Font | Tagged 12.0savvy 13.0savvy 14.0savvy 15.0savvy | Leave a comment

最前面の書類中の選択中のテキストアイテムの文字サイズを、特定サイズのみ対象にして置換 v3

Posted on 2月 18, 2024 by Takaaki Naganoya

Pages書類で選択中のtext item(Pagesでこれを識別するクラスがないのでshape)内のテキストに複数の文字サイズが存在している場合に、特定の文字サイズ部分のみ異なるものに置き換えるAppleScriptです。

–> Play demo movie

ただし、本Scriptで使用している自作のdisplay text fieldsライブラリを、本ScriptをmacOS標準搭載の「スクリプトメニュー」に入れた状態で呼び出すと、ダイアログ中への文字入力ができませんでした(macOS 13.6.5)。Pagesの書類の方に文字入力フォーカスが残ってしまっています。文字サイズをポップアップメニューからの選択方式にするなど、テキスト入力「以外」の方法に差し替えることで対処できることは判明しています。

このあたりのmacOS側の挙動に対して、「ナニコレ?」と違和感をおぼえつつも……スクリプトメニューに入れて呼び出す場合には対処するしかないのでしょう。細かい機能がAppleScriptランタイム環境ごとに「使える」「使えない」といった違いを生んでいるうえに、こうしたGUIの挙動についてもAppleScriptランタイム環境ごとに違っている点について、より細かい点をチェックする必要がありそうです(メーカー側がどんどん基礎的な部品の挙動を変更しては発表もしない状況)。


▲架空の本のPages書類のうち、処理対象のtext itemを選択状態にして実行


▲どのフォントサイズを置き換えるかをダイアログ選択。リサイズ後の数値を入力するとリサイズ。空欄のままにすると、リサイズしない

AppleScript名:最前面の書類中の選択中のテキストアイテムの文字サイズを、特定サイズのみ対象にして置換 v3.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2024/02/16
—
–  Copyright © 2024 Piyomaru Software, All Rights Reserved
—

use AppleScript version "2.7" — macOS 10.13 or later
use framework "Foundation"
use scripting additions
use tfLib : script "display text fields"

tell application "Pages"
  tell front document
    set tmpList to selection
    
    
repeat with i in tmpList
      set j to contents of i
      
set tmpC to class of j
      
      
–選択中のアイテムがshape(text itemを指定したいが、PagesではこのClassは存在しない)の場合のみ処理
      
if tmpC is equal to shape then
        –最大サイズの文字のみ抽出
        
set cRes to (size of every character of object text of j)
        
set uRes to removeDuplicates(cRes) of me
        
        
set selection to {j}
        
        
–ダイアログ表示
        
set strList to stringfyListItems(uRes) of me
        
set blankList to makeBlankListByIndicatedItem(strList, "") of me
        
        
set dRes to confirm text fields main message "テキストアイテムの文字サイズ置換" sub message "置換しない場合には空欄のまま。サイズはポイント数で指定" key list strList value list blankList
        
if dRes = false then exit repeat
        
        
–文字サイズ置換
        
repeat with ii from 1 to (length of strList)
          set targSize to (contents of item ii of strList) as real —From Size
          
set repSize to contents of item ii of dRes –To Size
          
          
if repSize is not equal to "" then
            set repSizeNum to repSize as real
            
set size of (every character of object text of j whose size is targSize) to repSizeNum
          end if
        end repeat
        
      end if
    end repeat
  end tell
end tell

–指定リストの項目数によって、空白アイテムが入ったリストを返す
on makeBlankListByIndicatedItem(aList, blankItem)
  set newList to {}
  
set aLen to length of aList
  
  
repeat aLen times
    set the end of newList to blankItem
  end repeat
  
  
return newList
end makeBlankListByIndicatedItem

–リストの全項目をテキスト化
on removeDuplicates(aList)
  set newList to {}
  
repeat with i from 1 to (length of aList)
    set anItem to item 1 of aList
    
set aList to rest of aList
    
if {anItem} is not in aList then set end of newList to anItem
  end repeat
  
return newList
end removeDuplicates

–リスト内の要素をすべてテキストに変換する
on stringfyListItems(a as list)
  set newL to {}
  
repeat with i in a
    set j to contents of i
    
set j to j as string
    
set the end of newL to j
  end repeat
  
  
return newL
end stringfyListItems

★Click Here to Open This Script 

Posted in Font Object control | Tagged 13.0savvy Pages | Leave a comment

新発売:AppleScript基礎テクニック集(24)フォント指定

Posted on 8月 7, 2022 by Takaaki Naganoya

電子書籍の新刊を発売しました。「AppleScript基礎テクニック集」の第24巻、「フォント指定」です。PDF 34ページ。サンプルScriptのZipアーカイブを添付。

→ 販売ページ

macOS上でフォントは「PostScript Name」、「正式名称(Display Name)」で管理されており、どちらの指定も受け付けるアプリケーションもあれば、PostScript Nameだけを要求するアプリケーションもあるなどさまざまです。CocoaのAPIではPostScript Nameが利用されています。

また、フォント名を「ファミリー」と「スタイル」に分けて指定できるようにもなっており、個別に指定できるアプリケーションもありますが(Adobe InDesignなど)、これはごく一部です。

結局、アプリケーションごとに対応はまちまちですが、指定できることにはかわりありません。こうしたフォント指定について、フォント管理アプリケーションFont Bookを通じてさまざまなフォントの属性情報を取得する方法についてご紹介します。

目次

■AppleScriptにおけるフォント情報管理

フォント情報は「Font Book.app」で調べる
フォントを階層構造とコレクションで管理
これが、フォントの識別情報
AppleScriptに対応しているFont Book.app
Font Book上の選択中のフォントを取得
標準搭載、メニューからScriptを実行する機能

■Keynote/Pages/Numbersでフォント情報を指定

Keynote書類上のテキストアイテムのフォント指定
iWork apps全般では正式名称でもPS名でも可
Pagesでも正式名称/PostScript名でOK
Numbersでも正式名称/PostScript名でOK

■書式付きテキストをAppleScriptから生成

TextEditには特殊なオブジェクトで書式アクセス

■Font Book.app関連AppleScriptサンプル

FontBook.app自体のプロパティを取得
フォントライブラリ情報を取得
フォントコレクション情報を取得
フォントコンテナ情報を取得
選択中のアイテムを取得
フォントにアクセス①
フォントにアクセス②
フォントを削除

Posted in Books Font news PRODUCTS | Tagged 10.15savvy 11.0savvy 12.0savvy | Leave a comment

SF Symbolsを名称で指定してPNG画像化

Posted on 4月 15, 2022 by Takaaki Naganoya

SF Symbolsに収録されている文字を、名称で指定してデスクトップにPNG画像で書き出すAppleScriptです。

同フォントは、アプリ上のアイコン素材3,300個以上をフォント化し、再利用しやすくすることで、アイコンで何かの意図を示すことを規格化したいという、現代における象形文字の再発明みたいな存在です。

文化や人種を超えた、非言語コミュニケーションを促進するための基盤としてAppleが整備を行なっているものなんでしょう。文化を縦断したインフラみたいな。

アイコン素材を自分で作るのはつらいので、正直助かっています。Appleが配布しているSF Symbols 3アプリケーションを使って画面上でいろいろ探して、文字を指定できます。

一応、SF Symbols.app自体にも指定フォントを画像化する機能はついているのですが、レンダリング時の指定解像度が低すぎて、プレゼン資料や本のイラストとして利用するには不便すぎます(本来の利用目的である、タブバーのアイコンに指定するのには向いている解像度なんでしょうけれども)。

そこで、指定のフォントの文字を名称で指定するとPNG画像にレンダリングするAppleScriptを作成してみました。

文字を指定するのはできているのですが、フォントのファミリーとかマルチカラーとかの指定の方法がよくわかりません。

AppleScript名:SF Symbolsを名称で指定してPNG画像化 v1a.scptd
—
–  Created by: Takaaki Naganoya
–  Created on: 2022/04/14
—
–  Copyright © 2022 Piyomaru Software, All Rights Reserved
—
use AppleScript version "2.8" — Monterey (12) or later
use framework "Foundation"
use framework "AppKit"
use framework "QuartzCore"
use scripting additions

set aName to "paperplane.circle.fill"
set anImage to current application’s NSImage’s imageWithSystemSymbolName:(aName) accessibilityDescription:(missing value)
set resImg to resizeNSImage(anImage, 50.0) of me

set aDesktopPath to current application’s NSString’s stringWithString:(POSIX path of (path to desktop))
set savePath to aDesktopPath’s stringByAppendingString:((current application’s NSUUID’s UUID()’s UUIDString())’s stringByAppendingPathExtension:"png")

set fRes to saveNSImageAtPathAsPNG(resImg, savePath) of me

on resizeNSImage(aSourceImg, aScale)
  set aSize to aSourceImg’s |size|()
  
set newWidth to (width of aSize) * aScale
  
set newheight to (height of aSize) * aScale
  
  
set targFrame to current application’s NSMakeRect(0, 0, newWidth, newheight)
  
set targImage to current application’s NSImage’s alloc()’s initWithSize:{newWidth, newheight}
  
  
set aKey to {current application’s NSImageHintInterpolation}
  
set aObj to current application’s NSNumber’s numberWithInt:(current application’s NSImageInterpolationLow)
  
set hintRec to current application’s NSDictionary’s dictionaryWithObject:aObj forKey:aKey
  
  
targImage’s lockFocus()
  
aSourceImg’s drawInRect:targFrame fromRect:(current application’s NSZeroRect) operation:(current application’s NSCompositeCopy) fraction:1.0 respectFlipped:true hints:hintRec
  
targImage’s unlockFocus()
  
  
return targImage
end resizeNSImage

–NSImageを指定パスにPNG形式で保存
on saveNSImageAtPathAsPNG(anImage, outPath)
  set imageRep to anImage’s TIFFRepresentation()
  
set aRawimg to current application’s NSBitmapImageRep’s imageRepWithData:imageRep
  
set pathString to current application’s NSString’s stringWithString:outPath
  
set newPath to pathString’s stringByExpandingTildeInPath()
  
set myNewImageData to (aRawimg’s representationUsingType:(current application’s NSPNGFileType) |properties|:(missing value))
  
set aRes to (myNewImageData’s writeToFile:newPath atomically:true) as boolean
  
return aRes –成功ならtrue、失敗ならfalseが返る
end saveNSImageAtPathAsPNG

★Click Here to Open This Script 

Posted in Font Image | Tagged 11.0savvy 12.0savvy SF Symbols | Leave a comment

電子書籍(PDF)をオンラインストアで販売中!

Google Search

Popular posts

  • 開発機としてM2 Mac miniが来たのでガチレビュー
  • macOS 13.6.5 AS系のバグ、一切直らず
  • CotEditorで2つの書類の行単位での差分検出
  • Apple純正マウス、キーボードのバッテリー残量取得
  • macOS 15, Sequoia
  • 初心者がつまづきやすい「log」コマンド
  • 指定のWordファイルをPDFに書き出す
  • Adobe AcrobatをAppleScriptから操作してPDF圧縮
  • メキシカンハットの描画
  • 与えられた文字列の1D Listのすべての順列組み合わせパターン文字列を返す v3(ベンチマーク用)
  • Pages本執筆中に、2つの書類モード切り替えに気がついた
  • 2023年に書いた価値あるAppleScript
  • Pixelmator Pro v3.6.4でAppleScriptからの操作時の挙動に違和感が
  • AdobeがInDesign v19.4からPOSIX pathを採用
  • Safariで「プロファイル」機能を使うとAppleScriptの処理に影響
  • Cocoa Scripting Course 続刊計画
  • Numbersで選択範囲のセルの前後の空白を削除
  • macOS 14.xでScript Menuの実行速度が大幅に下がるバグ
  • NaturalLanguage.frameworkでNLEmbeddingの処理が可能な言語をチェック
  • AppleScriptによる並列処理

Tags

10.11savvy (1102) 10.12savvy (1243) 10.13savvy (1392) 10.14savvy (587) 10.15savvy (438) 11.0savvy (283) 12.0savvy (207) 13.0savvy (177) 14.0savvy (127) 15.0savvy (104) CotEditor (64) Finder (51) iTunes (19) Keynote (115) NSAlert (61) NSArray (51) NSBitmapImageRep (20) NSBundle (20) NSButton (34) NSColor (53) NSDictionary (28) NSFileManager (23) NSFont (21) NSImage (41) NSJSONSerialization (21) NSMutableArray (63) NSMutableDictionary (22) NSPredicate (36) NSRunningApplication (56) NSScreen (30) NSScrollView (22) NSString (119) NSURL (98) NSURLRequest (23) NSUTF8StringEncoding (30) NSView (33) NSWorkspace (20) Numbers (74) Pages (54) Safari (44) Script Editor (27) WKUserContentController (21) WKUserScript (20) WKWebView (23) WKWebViewConfiguration (22)

カテゴリー

  • 2D Bin Packing
  • 3D
  • AirDrop
  • AirPlay
  • Animation
  • AppleScript Application on Xcode
  • Beginner
  • Benchmark
  • beta
  • Bluetooth
  • Books
  • boolean
  • bounds
  • Bug
  • Calendar
  • call by reference
  • check sum
  • Clipboard
  • Cocoa-AppleScript Applet
  • Code Sign
  • Color
  • Custom Class
  • dialog
  • diff
  • drive
  • Droplet
  • exif
  • file
  • File path
  • filter
  • folder
  • Font
  • Font
  • GAME
  • geolocation
  • GUI
  • GUI Scripting
  • Hex
  • History
  • How To
  • iCloud
  • Icon
  • Image
  • Input Method
  • Internet
  • iOS App
  • JavaScript
  • JSON
  • JXA
  • Keychain
  • Keychain
  • Language
  • Library
  • list
  • Locale
  • Localize
  • Machine Learning
  • Map
  • Markdown
  • Menu
  • Metadata
  • MIDI
  • MIME
  • Natural Language Processing
  • Network
  • news
  • Noification
  • Notarization
  • Number
  • Object control
  • OCR
  • OSA
  • parallel processing
  • PDF
  • Peripheral
  • PRODUCTS
  • QR Code
  • Raw AppleEvent Code
  • Record
  • rectangle
  • recursive call
  • regexp
  • Release
  • Remote Control
  • Require Control-Command-R to run
  • REST API
  • Review
  • RTF
  • Sandbox
  • Screen Saver
  • Script Libraries
  • sdef
  • search
  • Security
  • selection
  • shell script
  • Shortcuts Workflow
  • Sort
  • Sound
  • Spellchecker
  • Spotlight
  • SVG
  • System
  • Tag
  • Telephony
  • Text
  • Text to Speech
  • timezone
  • Tools
  • Update
  • URL
  • UTI
  • Web Contents Control
  • WiFi
  • XML
  • XML-RPC
  • イベント(Event)
  • 未分類

アーカイブ

  • 2025年1月
  • 2024年12月
  • 2024年11月
  • 2024年10月
  • 2024年9月
  • 2024年8月
  • 2024年7月
  • 2024年6月
  • 2024年5月
  • 2024年4月
  • 2024年3月
  • 2024年2月
  • 2024年1月
  • 2023年12月
  • 2023年11月
  • 2023年10月
  • 2023年9月
  • 2023年8月
  • 2023年7月
  • 2023年6月
  • 2023年5月
  • 2023年4月
  • 2023年3月
  • 2023年2月
  • 2023年1月
  • 2022年12月
  • 2022年11月
  • 2022年10月
  • 2022年9月
  • 2022年8月
  • 2022年7月
  • 2022年6月
  • 2022年5月
  • 2022年4月
  • 2022年3月
  • 2022年2月
  • 2022年1月
  • 2021年12月
  • 2021年11月
  • 2021年10月
  • 2021年9月
  • 2021年8月
  • 2021年7月
  • 2021年6月
  • 2021年5月
  • 2021年4月
  • 2021年3月
  • 2021年2月
  • 2021年1月
  • 2020年12月
  • 2020年11月
  • 2020年10月
  • 2020年9月
  • 2020年8月
  • 2020年7月
  • 2020年6月
  • 2020年5月
  • 2020年4月
  • 2020年3月
  • 2020年2月
  • 2020年1月
  • 2019年12月
  • 2019年11月
  • 2019年10月
  • 2019年9月
  • 2019年8月
  • 2019年7月
  • 2019年6月
  • 2019年5月
  • 2019年4月
  • 2019年3月
  • 2019年2月
  • 2019年1月
  • 2018年12月
  • 2018年11月
  • 2018年10月
  • 2018年9月
  • 2018年8月
  • 2018年7月
  • 2018年6月
  • 2018年5月
  • 2018年4月
  • 2018年3月
  • 2018年2月

https://piyomarusoft.booth.pm/items/301502

メタ情報

  • ログイン
  • 投稿フィード
  • コメントフィード
  • WordPress.org

Forum Posts

  • 人気のトピック
  • 返信がないトピック

メタ情報

  • ログイン
  • 投稿フィード
  • コメントフィード
  • WordPress.org
Proudly powered by WordPress
Theme: Flint by Star Verte LLC