Sync bundle with TextMate repo

This commit is contained in:
Tom Robinson
2009-09-07 18:53:59 -07:00
parent 98e18340b7
commit f7c00df9a9
28 changed files with 1178 additions and 18 deletions
@@ -0,0 +1 @@
.svn
@@ -0,0 +1,70 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>command</key>
<string>#!/usr/bin/env ruby
proto_re = /
^\s* # Start of the line and optional space
[+-]\s* # a plus or minus for method specifier
\([^)]+\) # the return type in brackets
((?:\n|[^{])*)
(?m:.*?)
\{
/x
previous_lines = STDIN.readlines[1..ENV['TM_LINE_NUMBER'].to_i - 1]
invocation_line = previous_lines[-1]
proto = previous_lines.join.scan(proto_re)[-1]
exit if proto.nil? or proto.empty?
last_proto_sel_with_types = proto[0].strip.sub(/^\s+/, '').sub(%r{\s*//.*$}, '').gsub(/\n\s*/, ' ')
params = []
params = last_proto_sel_with_types.scan(/(.+?):\((.+?)\)(\w+)/)
def format_specifier_for_type(type)
%w[int bool BOOL long].each { |t| return('%d') if type.include? t }
return '%c' if type == 'char'
return '%C' if type == 'unichar'
return '%s' if type == 'char*'
'%@'
end
def transformer_for(type, name)
return "CPStringFromRect(#{name})" if type == 'CPRect'
return "CPStringFromPoint(#{name})" if type == 'CPPoint'
return "CPStringFromSize(#{name})" if type == 'CPSize'
return "CPStringFromSelector(#{name})" if type == 'SEL'
name
end
print 'CPLog("[%@ '
if params.empty?
print last_proto_sel_with_types
else
print params.map { |param, type, name| param + ':' + format_specifier_for_type(type) }.join
end
print ']", [self class]'
print ', ' + params.map { |param, type, name| transformer_for(type, name) }.join(', ') unless params.empty?
print ");"
</string>
<key>input</key>
<string>document</string>
<key>name</key>
<string>CPLog() for Current Method</string>
<key>output</key>
<string>insertAsSnippet</string>
<key>scope</key>
<string>source.js.objj meta.scope.implementation</string>
<key>tabTrigger</key>
<string>logm</string>
<key>uuid</key>
<string>F220FEE6-6522-4281-8091-CF8C66AED44F</string>
</dict>
</plist>
@@ -0,0 +1,29 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>command</key>
<string>
. "$TM_SUPPORT_PATH/lib/webpreview.sh"
html_header "Objective-J Bundle Help" "Objective-J"
"$TM_SUPPORT_PATH/lib/markdown_to_help.rb" "$TM_BUNDLE_SUPPORT/help/help.markdown"
html_footer</string>
<key>input</key>
<string>none</string>
<key>keyEquivalent</key>
<string></string>
<key>name</key>
<string>Help</string>
<key>output</key>
<string>showAsHTML</string>
<key>scope</key>
<string>source.js.objj</string>
<key>uuid</key>
<string>AF27A8B3-C87F-410A-915B-D83271FDDC00</string>
</dict>
</plist>
@@ -0,0 +1,320 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>bundleUUID</key>
<string>4679484F-6227-11D9-BFB1-000D93589AF6</string>
<key>command</key>
<string>#!/usr/bin/env ruby
require "#{ENV['TM_SUPPORT_PATH']}/lib/escape"
require ENV['TM_SUPPORT_PATH'] + "/lib/exit_codes"
class Lexer
include Enumerable
def initialize
@label = nil
@pattern = nil
@handler = nil
@input = nil
reset
yield self if block_given?
end
def input(&amp;reader)
if @input.is_a? self.class
@input.input(&amp;reader)
else
class &lt;&lt; reader
alias_method :next, :call
end
@input = reader
end
end
def add_token(label, pattern, &amp;handler)
unless @label.nil?
@input = clone
end
@label = label
@pattern = /(#{pattern})/
@handler = handler || lambda { |label, match| [label, match] }
reset
end
def next(peek = false)
while @tokens.empty? and not @finished
new_input = @input.next
if new_input.nil? or new_input.is_a? String
@buffer += new_input unless new_input.nil?
new_tokens = @buffer.split(@pattern)
while new_tokens.size &gt; 2 or (new_input.nil? and not new_tokens.empty?)
@tokens &lt;&lt; new_tokens.shift
@tokens &lt;&lt; @handler[@label, new_tokens.shift] unless new_tokens.empty?
end
@buffer = new_tokens.join
@finished = true if new_input.nil?
else
separator, new_token = @buffer.split(@pattern)
new_token = @handler[@label, new_token] unless new_token.nil?
@tokens.push( *[ separator,
new_token,
new_input ].select { |t| not t.nil? and t != "" } )
reset(:buffer)
end
end
peek ? @tokens.first : @tokens.shift
end
def peek
self.next(true)
end
def each
while token = self.next
yield token
end
end
private
def reset(*attrs)
@buffer = String.new if attrs.empty? or attrs.include? :buffer
@tokens = Array.new if attrs.empty? or attrs.include? :tokens
@finished = false if attrs.empty? or attrs.include? :finished
end
end
class ObjcParser
attr_reader :list
def initialize(args)
@list = args
end
def get_position
return nil,nil if @list.empty?
has_message = true
a = @list.pop
endings = [:close,:post_op,:at_string,:at_selector,:identifier]
openings = [:open,:return,:control]
if a.tt == :identifier &amp;&amp; !@list.empty? &amp;&amp; endings.include?(@list[-1].tt)
insert_point = find_object_start
else
@list &lt;&lt; a
has_message = false unless methodList
insert_point = find_object_start
end
return insert_point, has_message
end
def methodList
old = Array.new(@list)
a = selector_loop(@list)
if !a.nil? &amp;&amp; a.tt == :selector
if file_contains_selector? a.text
return true
else
internal = Array.new(@list)
b = a.text
until internal.empty?
tmp = selector_loop(internal)
return true if tmp.nil?
b = tmp.text + b
if file_contains_selector? b
@list = internal
return true
end
end
end
else
end
@list = old
return false
end
def file_contains_selector?(methodName)
fileNames = ["#{ENV['TM_BUNDLE_SUPPORT']}/cocoa.txt.gz"]
userMethods = "#{ENV['TM_PROJECT_DIRECTORY']}/.methods.TM_Completions.txt.gz"
fileNames += [userMethods] if File.exists? userMethods
candidates = []
fileNames.each do |fileName|
zGrepped = %x{zgrep ^#{e_sh methodName }[[:space:]] #{e_sh fileName }}
candidates += zGrepped.split("\n")
end
return !candidates.empty?
end
def selector_loop(l)
until l.empty?
obj = l.pop
case obj.tt
when :selector
return obj
when :close
return nil if match_bracket(obj.text,l).nil?
when :open
return nil
end
end
return nil
end
def match_bracket(type,l)
partner = {"]"=&gt;"[",")"=&gt;"(","}"=&gt;"{"}[type]
up = 1
until l.empty?
obj = l.pop
case obj.text
when type
up +=1
when partner
up -=1
end
return obj.beg if up == 0
end
end
def find_object_start
openings = [:operator,:selector,:open,:return,:control]
until @list.empty? || openings.include?(@list[-1].tt)
obj = @list.pop
case obj.tt
when :close
tmp = match_bracket(obj.text, @list)
b = tmp unless tmp.nil?
when :star
b, ate = eat_star(b,obj.beg)
return b unless ate
when :nil
b = nil
else
b = obj.beg
end
end
return b
end
def eat_star(prev, curr)
openings = [:operator,:selector,:open,:return,:control,:star]
if @list.empty? || openings.include?(@list[-1].tt)
return curr, true
else
return prev, false
end
end
end
if __FILE__ == $PROGRAM_NAME
require "stringio"
line = ENV['TM_CURRENT_LINE']
caret_placement =ENV['TM_LINE_INDEX'].to_i - 1
up = 0
pat = /"(?:\\.|[^"\\])*"|\[|\]/
line.scan(pat).each do |item|
case item
when "["
up+=1
when "]"
up -=1
end
end
if caret_placement ==-1
print "]$0" + e_sn(line[caret_placement+1..-1])
TextMate.exit_insert_snippet
end
if up != 0
print e_sn(line[0..caret_placement])+"]$0"+e_sn(line[caret_placement+1..-1])
TextMate.exit_insert_snippet
end
to_parse = StringIO.new(line[0..caret_placement])
lexer = Lexer.new do |l|
l.add_token(:return, /\breturn\b/)
l.add_token(:nil, /\bnil\b/)
l.add_token(:control, /\b(?:if|while|for|do)(?:\s*)\(/)# /\bif|while|for|do(?:\s*)\(/)
l.add_token(:at_string, /"(?:\\.|[^"\\])*"/)
l.add_token(:selector, /\b[A-Za-z_0-9]+:/)
l.add_token(:identifier, /\b[A-Za-z_0-9]+\b/)
l.add_token(:bind, /(?:-&gt;)|\./)
l.add_token(:post_op, /\+\+|\-\-/)
l.add_token(:at, /@/)
l.add_token(:star, /\*/)
l.add_token(:close, /\)|\]|\}/)
l.add_token(:open, /\(|\[|\{/)
l.add_token(:operator, /[&amp;-+\/=%!:\,\?;&lt;&gt;\|\~\^]/)
l.add_token(:terminator, /;\n*|\n+/)
l.add_token(:whitespace, /\s+/)
l.add_token(:unknown, /./)
l.input { to_parse.gets }
#l.input {STDIN.read}
end
offset = 0
tokenList = []
A = Struct.new(:tt, :text, :beg)
lexer.each do |token|
tokenList &lt;&lt; A.new(*(token&lt;&lt;offset)) unless [:whitespace,:terminator].include? token[0]
offset +=token[1].length
end
if tokenList.empty?
print e_sn(line[0..caret_placement])+"]$0"+e_sn(line[caret_placement+1..-1])
TextMate.exit_insert_snippet
end
par = ObjcParser.new(tokenList)
b, has_message = par.get_position
if !line[caret_placement+1].nil? &amp;&amp; line[caret_placement+1].chr == "]"
if b.nil? || par.list.empty? || par.list[-1].text == "["
print e_sn(line[0..caret_placement])+"]$0"+e_sn(line[caret_placement+2..-1])
TextMate.exit_insert_snippet
end
end
if b.nil?
print e_sn(line[0..caret_placement])+"]$0"+e_sn(line[caret_placement+1..-1])
elsif !has_message &amp;&amp; (b &lt; caret_placement )
print e_sn(line[0..b-1]) unless b == 0
ins = (/\s/ =~ line[caret_placement].chr ? "$0]" : " $0]")
print "[" +e_sn(line[b..caret_placement]) + ins +e_sn(line[caret_placement+1..-1])
elsif b &lt; caret_placement
print e_sn(line[0..b-1]) unless b == 0
print "[" +e_sn(line[b..caret_placement]) +"]$0"+e_sn(line[caret_placement+1..-1])
else
print e_sn(line[0..caret_placement])+"]$0"+e_sn(line[caret_placement+1..-1])
end
end
</string>
<key>fallbackInput</key>
<string>line</string>
<key>input</key>
<string>selection</string>
<key>keyEquivalent</key>
<string>]</string>
<key>name</key>
<string>Insert Matching Start Bracket</string>
<key>output</key>
<string>insertAsSnippet</string>
<key>scope</key>
<string>source.js.objj</string>
<key>uuid</key>
<string>CD025B3E-36B9-4E16-A81E-8DB6E8466CD1</string>
</dict>
</plist>
@@ -0,0 +1,42 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>command</key>
<string>#!/usr/bin/env ruby
def e (str); str.gsub(/[$`\\]/, '\\\\\0'); end
line = STDIN.read
col = ENV['TM_LINE_INDEX'].to_i
left, right = line[0...col], line[col..-1]
if left =~ /(.*?)(\[)?(\w+)\s+$/ then
lead, bracket, cl = $1, $2, $3
right = line[col+1..-1] unless bracket.nil?
print "#{e lead}${1/.+/[/}[[#{e cl} alloc] init$0]"
print right.empty? ? ";" : "#{e right}"
else
# this is only if we were not able to interpret the line
print "#{e left}$0#{e right}"
end
</string>
<key>fallbackInput</key>
<string>line</string>
<key>input</key>
<string>selection</string>
<key>name</key>
<string>Insert [[… alloc] init]</string>
<key>output</key>
<string>insertAsSnippet</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>alloc</string>
<key>uuid</key>
<string>DF55A80D-E733-4CE2-A318-D56789B18406</string>
</dict>
</plist>
@@ -53,8 +53,10 @@ else
end</string>
<key>input</key>
<string>none</string>
<key>keyEquivalent</key>
<string>@R</string>
<key>name</key>
<string>Open Document in Running Browser(s)</string>
<string>Run in Browsers</string>
<key>output</key>
<string>discard</string>
<key>scope</key>
@@ -37,8 +37,6 @@ ps -xc|grep -sq Camino &amp;&amp; osascript -e 'tell app "Camino"' -e 'activate'
</string>
<key>input</key>
<string>none</string>
<key>keyEquivalent</key>
<string>@r</string>
<key>name</key>
<string>Refresh Running Browser(s)</string>
<key>output</key>
@@ -0,0 +1,60 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>saveActiveFile</string>
<key>command</key>
<string>
[[ ! -z $TM_OBJJ_MASTER_FILE ]] &amp;&amp; INDEXFILE="$TM_OBJJ_MASTER_FILE"
[[ ! -z $TM_PROJECT_DIRECTORY ]] &amp;&amp; INDEXFILE="$TM_PROJECT_DIRECTORY/index.html"
[[ ! -z $TM_DIRECTORY ]] &amp;&amp; INDEXFILE="$TM_DIRECTORY/index.html"
if [ -z "$INDEXFILE" ]; then
D=`dirname "$TM_FILEPATH"`
while [ -z `find "$D" -name index.html` ]; do
D=`dirname "$D"`
done
INDEXFILE="${D}/index.html"
fi
[[ -z $INDEXFILE ]] &amp;&amp; echo "No start file found. Please set the shell variable 'OBJJ_MASTER_FILE'" &amp;&amp; exit 206
cat &lt;&lt;-HTML
&lt;script type="text/javascript" charset="utf-8"&gt;
try {
if (TextMate.system("", function (task) { })) {
var __TM_confirm_Status;
alert = function(s){TextMate.system("\"$DIALOG\" -e -p '{messageTitle=\"JavaScript\";informativeText=\""+s.toString().replace(/\x27/g,"").replace(/\"/g,'\\\"')+"\";}'",null);};
confirm = function(s){TextMate.system("\"$DIALOG\" -e -p '{messageTitle=\"JavaScript\";informativeText=\""+s.toString().replace(/\x27/g,"").replace(/\"/g,'\\\"')+"\";buttonTitles=(\"OK\",\"Cancel\");}'",null).onreadoutput=function(s){__TM_confirm_Status = s != 1;};return(__TM_confirm_Status)};
}
} catch(e) {}
&lt;/script&gt;
&lt;base href="file://${INDEXFILE// /%20}"&gt;
HTML
cat "$INDEXFILE"
[[ ! -z $(grep 'objj_exception_setOutputStream' "$INDEXFILE") ]] &amp;&amp; exit 205
cat &lt;&lt;-JS
&lt;script type="text/javascript" charset="utf-8"&gt;
objj_exception_setOutputStream(function(aString) { console.log(aString);alert(aString) });
&lt;/script&gt;
JS
exit 205
</string>
<key>input</key>
<string>none</string>
<key>keyEquivalent</key>
<string>@r</string>
<key>name</key>
<string>Run</string>
<key>output</key>
<string>showAsTooltip</string>
<key>scope</key>
<string>source.js.objj</string>
<key>uuid</key>
<string>0C55A19B-3B2D-418F-B7FD-7E64B736F379</string>
</dict>
</plist>
@@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>command</key>
<string>cat &lt;&lt;-HTM
&lt;body onload='javascript:window.location.href="http://cappuccino.org/learn/documentation/"'&gt;
&lt;/body&gt;
HTM
exit 205
</string>
<key>input</key>
<string>none</string>
<key>keyEquivalent</key>
<string>^H</string>
<key>name</key>
<string>Show Documentation</string>
<key>output</key>
<string>showAsTooltip</string>
<key>scope</key>
<string>source.js.objj</string>
<key>uuid</key>
<string>344244D8-67A3-4F23-8270-397BD1696AC4</string>
</dict>
</plist>
@@ -0,0 +1,214 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>beforeRunningCommand</key>
<string>nop</string>
<key>command</key>
<string>[[ -z $OBJJ_HOME ]] &amp;&amp; echo "OBJJ_HOME wasn't set!" &amp;&amp; exit 206
[[ ! -d "$OBJJ_HOME/Documentation" ]] &amp;&amp; echo "Please copy the folder Documentation to $OBJJ_HOME" &amp;&amp; exit 206
function showUpClassPage {
cat &lt;&lt;-HTM
&lt;body onload='javascript:window.location.href="tm-file://$OBJJ_HOME/Documentation/class$1"'&gt;
&lt;/body&gt;
HTM
exit 205
}
function showUpPage {
cat &lt;&lt;-HTM
&lt;body onload='javascript:window.location.href="tm-file://$1"'&gt;
&lt;/body&gt;
HTM
exit 205
}
DOCHEAD=$(perl -e '
#$line_nr = defined($ENV{"TM_INPUT_START_LINE"}) ? $ENV{"TM_INPUT_START_LINE"} : 1;
$line_nr = 1;
$cur_line_nr = $ENV{"TM_LINE_NUMBER"};
$header = "";
while($cur_line_nr--&gt;$line_nr) {$header.=&lt;&gt;;}
$tail = &lt;&gt;;
$header .= substr($tail,0,$ENV{"TM_LINE_INDEX"});
print $header;
')
# caret is inside of a class name
if [ `echo $TM_SCOPE | grep -c 'support.class.cappuccino'` -gt 0 ]; then
n=$(echo $TM_CURRENT_WORD | perl -pe 's/(.)(.)(.*)/_$1_$2_$3/;s/(?&lt;!_)([A-Z])(?!_)/_$1/g;s/_{2,}/_/g')
showUpClassPage "$n.html"
fi
# caret is inside of a foundation class name
if [ `echo $TM_SCOPE | grep -c 'support.variable.cappuccino.foundation'` -gt 0 ]; then
[[ "$TM_CURRENT_WORD" == "CPApp" ]] &amp;&amp; showUpClassPage "_C_P_Application.html"
fi
# caret is inside of a objj function
if [ `echo $TM_SCOPE | grep -c 'support.function.cappuccino'` -gt 0 ]; then
FILE=$(ruby -e '
require File.join(ENV["TM_SUPPORT_PATH"], "lib/ui.rb")
require File.join(ENV["TM_SUPPORT_PATH"], "lib/exit_codes.rb")
cur_word = ""
cur_word &lt;&lt; ENV["TM_CURRENT_WORD"]
cur_word.sub!("CG", "C[GP]") if cur_word[0..1] == "CG" or cur_word[0..1] == "CP"
lg = %x{egrep -rl "C[GP]RectMake" '$OBJJ_HOME/Documentation'}
urls = lg.split(/\n/).sort
if urls.length == 1
print urls.first
else
display = urls.map{|x| x.split("/").last.sub!(".html","")}
index=TextMate::UI.menu(display)
if index != nil
print urls[index]
else
TextMate.exit_discard()
end
end
')
FUNC=$(echo -en $TM_CURRENT_WORD | perl -pe 's/^(C[PG])(.*)/C[PG]$2/')
ANKER=`cat "$FILE" | egrep -o "\"#$FUNC.*?\"" | sed -e 's/^"//;s/".*//' | head -n 1`
[[ ! -z "$ANKER" ]] &amp;&amp; showUpPage "$FILE$ANKER"
[[ ! -z $FILE ]] &amp;&amp; showUpPage "$FILE" &amp;&amp; exit 206
fi
# caret is inside of a constant
if [ `echo $TM_SCOPE | grep -c 'support.constant.cappuccino'` -gt 0 ]; then
FILE=$(ruby -e '
require File.join(ENV["TM_SUPPORT_PATH"], "lib/ui.rb")
require File.join(ENV["TM_SUPPORT_PATH"], "lib/exit_codes.rb")
lg = %x{egrep -rl #{ENV["TM_CURRENT_WORD"]} '$OBJJ_HOME/Documentation'}
urls = lg.split(/\n/).sort
if urls.length == 1
print urls.first
else
display = urls.map{|x| x.split("/").last.sub!(".html","")}
index=TextMate::UI.menu(display)
if index != nil
print urls[index]
else
TextMate.exit_discard()
end
end
')
[[ ! -z $FILE ]] &amp;&amp; showUpPage "$FILE" &amp;&amp; exit 206
fi
# caret is inside of [method]
if [ `echo $TM_SCOPE | grep -c 'meta.bracketed.js.objj'` -gt 0 ]; then
# find []
DECL=$(echo -en "$DOCHEAD" | perl -e '
undef $/;
$header = &lt;&gt;;
$header=~s/\n/ /g;
@arr=split(//,$header);$c=0;
for($i=$#arr;$i&gt;-1;$i--){$c-- if($arr[$i] eq "]");$c++ if($arr[$i] eq "[");last if $c&gt;0;}
if($i==-1) {
print "";
} else {
print substr($header,$i+1);
}
')
# find the class for a method
CLASS=$(echo -en "$DECL" | perl -e '
undef $/;
$header = &lt;&gt;;
substr($header,0) =~ m/^\s*(\w+).*/;
$f = $1;
if (defined($f)) {
if($f=~m/CPApp/) {
print "CPApplication";
} else {
print $f;
}
} else {
substr($header,1) =~ m/^\s*(\w+).*/;
$f = $1;
if(defined($f)) {
if($f=~m/CPApp/) {
print "CPApplication";
} else {
print $f;
}
}
}
')
if [ ! -e "$OBJJ_HOME/Documentation/classes/$CLASS.html" ]; then
CLASS=$(echo -en "$DOCHEAD" | ruby -e '
require File.join(ENV["TM_SUPPORT_PATH"], "lib/ui.rb")
require File.join(ENV["TM_SUPPORT_PATH"], "lib/exit_codes.rb")
known_classes = []
classes = []
lg = %x{cd '$OBJJ_HOME/Documentation/classes'; egrep -rl #{ENV["TM_CURRENT_WORD"]} .}
known_classes = lg.split(/\n/).map{|x| x.sub("\.html","").sub("./","") }.sort
if known_classes.empty?
lg = %x{ls '$OBJJ_HOME/Documentation/classes'}
known_classes = lg.split(/\n/).map{|x| x.sub("\.html","").sub("./","") }.sort
end
STDIN.read().scan(/\b[_]{0,2}[NC][APS]\w+(?=[^\.])\b/) {|c| classes &lt;&lt; c if ! classes.include?(c) &amp;&amp; known_classes.include?(c)}
classes.sort!
if classes != known_classes
classes &lt;&lt; "--"
classes += known_classes
end
if classes.length == 1
if classes.first != "--"
print classes.first
else
TextMate.exit_discard()
end
else
index=TextMate::UI.menu(classes)
if index != nil
print classes[index]
else
TextMate.exit_discard()
end
end
')
fi
[[ -z $CLASS ]] &amp;&amp; exit 200
[[ ! -e "$OBJJ_HOME/Documentation/classes/$CLASS.html" ]] &amp;&amp; echo "Nothing for '$CLASS'!" &amp;&amp; exit 206
# tries to find only the first method for 'method1: method2: etc'
FIRSTMETHOD=$(echo -en "$DECL" | perl -e '
undef $/;$d = &lt;&gt;;
$d=~m/\s*(\w+):/m;
print $1;
')
METHOD=${FIRSTMETHOD:-$TM_CURRENT_WORD}
# find the correct anker within CLASS.html
ANKER=`cat "$OBJJ_HOME/Documentation/classes/$CLASS.html" | egrep -o "\"#$METHOD.*?\"" | sed -e 's/^"//;s/".*//' | head -n 1`
[[ ! -z "$ANKER" ]] &amp;&amp; showUpClassPage "$CLASS.html$ANKER"
# check for inherited methods
ANKER=`cat "$OBJJ_HOME/Documentation/classes/$CLASS.html" | egrep -o "[^#\"]+?html#$METHOD" | head -n 1`
# echo $CLASS; echo $METHOD; echo $ANKER; exit 206
CLASS=$(echo -en "$ANKER" | perl -pe 's/(.*?)\.html.*/$1/;')
# find the correct anker within the new CLASS.html
ANKER=`cat "$OBJJ_HOME/Documentation/classes/$CLASS.html" | egrep -o "\"#$METHOD.*?\"" | sed -e 's/^"//;s/".*//' | head -n 1`
[[ ! -z "$ANKER" ]] &amp;&amp; showUpClassPage "$CLASS.html$ANKER"
# [[ ! -z "$ANKER" ]] &amp;&amp; showUpClassPage "$ANKER"
fi
exit 205</string>
<key>input</key>
<string>selection</string>
<key>keyEquivalent</key>
<string>^h</string>
<key>name</key>
<string>Documentation for Word</string>
<key>output</key>
<string>replaceSelectedText</string>
<key>scope</key>
<string>support.class.cappuccino, support.variable.cappuccino.foundation, meta.bracketed.js.objj, support.function.cappuccino</string>
<key>uuid</key>
<string>2D05A28A-2ED7-4A9A-9A5C-8625466BC77C</string>
</dict>
</plist>
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>name</key>
@@ -18,6 +18,6 @@
</string>
</dict>
<key>uuid</key>
<string>85A46AFC-5552-4CE5-BDA0-ED34F0398399</string>
<string>E65A721C-192D-4BCC-AD35-5ED5CB0DA5BE</string>
</dict>
</plist>
@@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@selector(${1:method}:)</string>
<key>name</key>
<string>@selector(…)</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>sel</string>
<key>uuid</key>
<string>13D9F280-A78F-4A4C-BE99-0DE13235738D</string>
</dict>
</plist>
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
@@ -0,0 +1,31 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@implementation ${1:CLASS} (CPCoding)
- (id)initWithCoder:(CPCoder)aCoder
{
if (self = [super initWithCoder:aCoder])
{
${2:IVAR} = [aCoder decodeObjectForKey:${3:KEY}];
}
return self;
}
- (void)encodeWithCoder:(CPCoder)aCoder
{
[super encodeWithCoder:aCoder];
[aCoder encodeObject:${2:IVAR} forKey:${3:KEY}];
}
@end
</string>
<key>name</key>
<string>Archiving</string>
<key>uuid</key>
<string>A840A98A-0C5B-49CB-8235-2CCD1BF7AFC1</string>
</dict>
</plist>
@@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>CPLog("$1"${1/[^%]*(%)?.*/(?1:, :\);)/}$2${1/[^%]*(%)?.*/(?1:\);)/}</string>
<key>name</key>
<string>CPLog(…)</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>log</string>
<key>uuid</key>
<string>C268A928-5C8E-4284-9BAB-4FDFB07B983A</string>
</dict>
</plist>
@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@interface ${1:NSObject} (${2:Category})
@end
@implementation ${1:NSObject} (${2:Category})
$0
@end</string>
<key>name</key>
<string>Category</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>cat</string>
<key>uuid</key>
<string>8C001067-8A50-4BAB-9A88-BA957A84E8CF</string>
</dict>
</plist>
@@ -22,7 +22,7 @@
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>cla</string>
<string>objj</string>
<key>uuid</key>
<string>96C39647-4346-4750-9F96-58070F24EDE6</string>
</dict>
@@ -0,0 +1,18 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>if([${1:[self delegate]} respondsToSelector:@selector(${2:selfDidSomething:})])
[$1 ${3:${2/((^\s*([A-Za-z0-9_]*:)\s*)|(:\s*$)|(:\s*))/(?2:$2self :\:&lt;&gt;)(?4::)(?5: :)/g}}];
</string>
<key>name</key>
<string>Delegate Responds to Selector</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>delegate</string>
<key>uuid</key>
<string>3B5B858C-645E-499C-813B-BBEEED943E9B</string>
</dict>
</plist>
@@ -0,0 +1,24 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>- (id)delegate
{
return $1;
}
- (void)setDelegate:(id)aDelegate
{
${1:delegate} = aDelegate;
}</string>
<key>name</key>
<string>Delegate</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>delacc</string>
<key>uuid</key>
<string>0B3D4C4C-7D75-49E6-9CEC-E4BF4069223A</string>
</dict>
</plist>
@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>${1:name} = [[CPTextField alloc] initWithFrame:CGRectMakeZero()];
[$1 setStringValue:${2:@"${3:string}"}];
${4:[$1 setEditable:${5:YES}];
}${6:[$1 setFont:[CPFont systemFontOfSize:${7:12.0}]];
}${8:[$1 sizeToFit];
}${0:}</string>
<key>name</key>
<string>New CPTextField</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>textf</string>
<key>uuid</key>
<string>C7340B17-F9EC-403F-9781-E2487023ED01</string>
</dict>
</plist>
@@ -0,0 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>${TM_COMMENT_START} ${4:Send $2 to $1, if $1 supports it}${TM_COMMENT_END}
if ([${1:self} respondsToSelector:@selector(${2:someSelector:})])
{
[$1 ${3:${2/((:\s*$)|(:\s*))/:&lt;&gt;(?3: )/g}}];
}</string>
<key>name</key>
<string>Responds to Selector</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>responds</string>
<key>uuid</key>
<string>D79EC699-9839-406E-AF60-DE51F78153CB</string>
</dict>
</plist>
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@import &lt;${1:`"$DIALOG" -u -p "{menuItems=({title=Foundation;},{title=AppKit;});}" | perl -e 'undef $/;$a=&lt;&gt;;$a=~m/&lt;key&gt;title(.|\n)+?&lt;string&gt;(.*?)&lt;/;print $2;'`}/${2:CP}$3.j&gt;
</string>
<key>name</key>
<string>import &lt;…&gt;</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>Imp</string>
<key>uuid</key>
<string>BE0553C0-B73B-4160-814C-840FC2B84C32</string>
</dict>
</plist>
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@import "${1:`"$TM_BUNDLE_SUPPORT/bin/import_FileMenu.sh" ".j"`}"
</string>
<key>name</key>
<string>import "…" (with File Menu)</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>impp</string>
<key>uuid</key>
<string>9BABD784-3DBE-4DA3-8A70-4E32FC7FDBB8</string>
</dict>
</plist>
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>content</key>
<string>@import "${1:}"
</string>
<key>name</key>
<string>import "…"</string>
<key>scope</key>
<string>source.js.objj</string>
<key>tabTrigger</key>
<string>imp</string>
<key>uuid</key>
<string>686B995F-3183-418B-A15F-CA517DFEFE2E</string>
</dict>
</plist>
@@ -0,0 +1,36 @@
EXTENSION="$1"
CURRENTDIR=`dirname $TM_FILEPATH`
if [ -z $TM_PROJECT_DIRECTORY ]; then
L=$((${#CURRENTDIR}+1))
MENUITEMS=$(find -s "$CURRENTDIR" -name "*$EXTENSION" | perl -pe "s/^.{$L}(.*?)$/{title=\"\$1\";}/" | paste -sd ',' -)
[[ -z $MENUITEMS ]] && exit 200
"$DIALOG" -u -p "{menuItems=($MENUITEMS);}" | perl -e 'undef $/;$a=<>;$a=~m/<key>title(.|\n)+?<string>(.*?)</;print $2;'
else
FILES=$(find -s "$TM_PROJECT_DIRECTORY" -name "*$EXTENSION")
FILES=$(echo "$FILES" | perl -pe "s!$CURRENTDIR/!!")
if [ "$CURRENTDIR" != "$TM_PROJECT_DIRECTORY" ]; then
CURRENTDIR=$(dirname $CURRENTDIR)
REPLACE=""
while [ "$CURRENTDIR" != "$TM_PROJECT_DIRECTORY" ]; do
REPLACE="$REPLACE../"
FILES=$(echo "$FILES" | perl -pe "s!$CURRENTDIR/!$REPLACE!")
CURRENTDIR=$(dirname $CURRENTDIR)
done
REPLACE="$REPLACE../"
FILES=$(echo "$FILES" | perl -pe "s!$CURRENTDIR/!$REPLACE!")
fi
MENUITEMS=$(echo "$FILES" | perl -pe "s/^(.*?)$/{title=\"\$1\";}/" | paste -sd ',' -)
[[ -z $MENUITEMS ]] && exit 200
"$DIALOG" -u -p "{menuItems=($MENUITEMS);}" | perl -e 'undef $/;$a=<>;$a=~m/<key>title(.|\n)+?<string>(.*?)</;print $2;'
fi
@@ -0,0 +1,41 @@
<center><font color=red>Any feedback about bugs or improvements is highly welcomed!</font></center>
# Introduction
Cappuccino <a href="http://cappuccino.org">cappuccino.org</a> is an open source framework that makes it easy to build desktop-caliber applications that run in a web browser.
# Commands
## Run
<button>&#x2318;R&nbsp;</button>
Run the current cappuccino web application in TextMate's HTML output window.
If you are inside of an Objective-J file (file extension .j) this command will look for a file `index.html` starting at the current folder and upwards within the file hierarchy or if you are working with a project it will look for it at the project's root path.
If the start HTML site differs you can set the shell variable `TM_OBJJ_MASTER_FILE` within a project.
## Run in Browser
<button>&#x21E7;&#x2318;R&nbsp;</button>
Run the current cappuccino web application in the default web browser.
If you are inside of an Objective-J file (file extension .j) this command will look for a file `index.html` starting at the current folder and upwards within the file hierarchy or if you are working with a project it will look for it at the project's root path.
If the start HTML site differs you can set the shell variable `TM_OBJJ_MASTER_FILE` within a project.
# Shell Variables #
## TM&#95;OBJJ&#95;MASTER&#95;FILE ##
This variable contains the path to the application's start HTML site.
# Main Bundle Maintainer
***Date: Sep 7 2009***
<pre>
- Tom Robinson&nbsp;<a href="mailto:tom@280north.com">tom@280north.com</a>
- Hans-Jörg Bibiko&nbsp;&nbsp;<a href="mailto:bibiko@eva.mpg.de">bibiko@eva.mpg.de</a>
</pre>
@@ -6,33 +6,135 @@
<string>gbz@280abegu.pbz</string>
<key>contactName</key>
<string>Tom Robinson</string>
<key>deleted</key>
<array>
<string>4689ADD7-C88A-4235-B69A-84C720034296</string>
</array>
<key>description</key>
<string>&lt;a href="http://cappuccino.org/"&gt;Cappuccino&lt;/a&gt; is an open source framework that makes it easy to build desktop-caliber applications that run in a web browser.</string>
<key>mainMenu</key>
<dict>
<key>excludedItems</key>
<array>
<string>CD025B3E-36B9-4E16-A81E-8DB6E8466CD1</string>
<string>2D05A28A-2ED7-4A9A-9A5C-8625466BC77C</string>
</array>
<key>items</key>
<array>
<string>96C39647-4346-4750-9F96-58070F24EDE6</string>
<string>AA41BEF8-5F81-4A5A-85DE-2E81A112778B</string>
<string>85B0746B-AE1C-47B3-8B9A-2B9A95F4C71E</string>
<string>------------------------------------</string>
<string>0C55A19B-3B2D-418F-B7FD-7E64B736F379</string>
<string>36FD3695-1051-401E-8536-89FB9CEEEAB4</string>
<string>033BC36A-97DA-4F48-9ACB-B58C80D1A689</string>
<string>------------------------------------</string>
<string>------------------------------------</string>
<string>AF27A8B3-C87F-410A-915B-D83271FDDC00</string>
<string>344244D8-67A3-4F23-8270-397BD1696AC4</string>
<string>------------------------------------</string>
<string>9BC0151E-82E8-4F2C-8AC1-7D4E6EC8FC80</string>
<string>3ABE883F-3236-4876-91E0-E899F5DE9B29</string>
<string>B226514A-4024-49EA-B4BD-4307C72F7EE3</string>
<string>A4BB7CC7-B06B-4034-B125-A646A22C0813</string>
<string>94B213AC-4DB1-400F-B78A-8FBCF3F93E44</string>
<string>28C6F02F-13D0-4B5B-AB6A-6F23E2CFBD5B</string>
<string>------------------------------------</string>
</array>
<key>submenus</key>
<dict/>
<dict>
<key>28C6F02F-13D0-4B5B-AB6A-6F23E2CFBD5B</key>
<dict>
<key>items</key>
<array>
<string>C7340B17-F9EC-403F-9781-E2487023ED01</string>
</array>
<key>name</key>
<string>UI</string>
</dict>
<key>3ABE883F-3236-4876-91E0-E899F5DE9B29</key>
<dict>
<key>items</key>
<array>
<string>AA41BEF8-5F81-4A5A-85DE-2E81A112778B</string>
<string>85B0746B-AE1C-47B3-8B9A-2B9A95F4C71E</string>
<string>0B3D4C4C-7D75-49E6-9CEC-E4BF4069223A</string>
</array>
<key>name</key>
<string>Accessor Methods For</string>
</dict>
<key>94B213AC-4DB1-400F-B78A-8FBCF3F93E44</key>
<dict>
<key>items</key>
<array>
<string>13D9F280-A78F-4A4C-BE99-0DE13235738D</string>
<string>DF55A80D-E733-4CE2-A318-D56789B18406</string>
</array>
<key>name</key>
<string>Misc</string>
</dict>
<key>9BC0151E-82E8-4F2C-8AC1-7D4E6EC8FC80</key>
<dict>
<key>items</key>
<array>
<string>BE0553C0-B73B-4160-814C-840FC2B84C32</string>
<string>686B995F-3183-418B-A15F-CA517DFEFE2E</string>
<string>9BABD784-3DBE-4DA3-8A70-4E32FC7FDBB8</string>
<string>------------------------------------</string>
<string>96C39647-4346-4750-9F96-58070F24EDE6</string>
<string>8C001067-8A50-4BAB-9A88-BA957A84E8CF</string>
<string>A840A98A-0C5B-49CB-8235-2CCD1BF7AFC1</string>
</array>
<key>name</key>
<string>Language Boilerplate</string>
</dict>
<key>A4BB7CC7-B06B-4034-B125-A646A22C0813</key>
<dict>
<key>items</key>
<array>
<string>D79EC699-9839-406E-AF60-DE51F78153CB</string>
<string>3B5B858C-645E-499C-813B-BBEEED943E9B</string>
</array>
<key>name</key>
<string>Idioms</string>
</dict>
<key>B226514A-4024-49EA-B4BD-4307C72F7EE3</key>
<dict>
<key>items</key>
<array>
<string>C268A928-5C8E-4284-9BAB-4FDFB07B983A</string>
<string>F220FEE6-6522-4281-8091-CF8C66AED44F</string>
</array>
<key>name</key>
<string>Common Method Calls</string>
</dict>
</dict>
</dict>
<key>name</key>
<string>JavaScript Objective-J</string>
<key>ordering</key>
<array>
<string>58D4B98A-2110-423E-9C80-CC9E202816E7</string>
<string>85A46AFC-5552-4CE5-BDA0-ED34F0398399</string>
<string>96C39647-4346-4750-9F96-58070F24EDE6</string>
<string>AA41BEF8-5F81-4A5A-85DE-2E81A112778B</string>
<string>85B0746B-AE1C-47B3-8B9A-2B9A95F4C71E</string>
<string>0C55A19B-3B2D-418F-B7FD-7E64B736F379</string>
<string>36FD3695-1051-401E-8536-89FB9CEEEAB4</string>
<string>033BC36A-97DA-4F48-9ACB-B58C80D1A689</string>
<string>AF27A8B3-C87F-410A-915B-D83271FDDC00</string>
<string>344244D8-67A3-4F23-8270-397BD1696AC4</string>
<string>2D05A28A-2ED7-4A9A-9A5C-8625466BC77C</string>
<string>BE0553C0-B73B-4160-814C-840FC2B84C32</string>
<string>686B995F-3183-418B-A15F-CA517DFEFE2E</string>
<string>9BABD784-3DBE-4DA3-8A70-4E32FC7FDBB8</string>
<string>96C39647-4346-4750-9F96-58070F24EDE6</string>
<string>8C001067-8A50-4BAB-9A88-BA957A84E8CF</string>
<string>AA41BEF8-5F81-4A5A-85DE-2E81A112778B</string>
<string>85B0746B-AE1C-47B3-8B9A-2B9A95F4C71E</string>
<string>0B3D4C4C-7D75-49E6-9CEC-E4BF4069223A</string>
<string>A840A98A-0C5B-49CB-8235-2CCD1BF7AFC1</string>
<string>C268A928-5C8E-4284-9BAB-4FDFB07B983A</string>
<string>F220FEE6-6522-4281-8091-CF8C66AED44F</string>
<string>D79EC699-9839-406E-AF60-DE51F78153CB</string>
<string>3B5B858C-645E-499C-813B-BBEEED943E9B</string>
<string>C7340B17-F9EC-403F-9781-E2487023ED01</string>
<string>13D9F280-A78F-4A4C-BE99-0DE13235738D</string>
<string>CD025B3E-36B9-4E16-A81E-8DB6E8466CD1</string>
<string>DF55A80D-E733-4CE2-A318-D56789B18406</string>
<string>58D4B98A-2110-423E-9C80-CC9E202816E7</string>
<string>E65A721C-192D-4BCC-AD35-5ED5CB0DA5BE</string>
</array>
<key>uuid</key>
<string>1FB3D538-84E1-4002-AA46-5705529A27E1</string>