-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathMyDocument.rb
174 lines (144 loc) · 4.04 KB
/
MyDocument.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
#
# MyDocument.rb
# sqlite
#
# Created by Brad Wilson on 19/04/08.
# Copyright (c) 2008 __MyCompanyName__. All rights reserved.
#
require 'rubygems'
require 'pathname'
require 'sqlite3'
require 'TableViewMethods'
require 'OutlineViewMethods'
class MyDocument < NSDocument
ib_outlets :tableView
ib_outlets :tableContentView
include TableViewMethods
include OutlineViewMethods
def windowNibName
# Override returning the nib file name of the document If you need
# to use a subclass of NSWindowController or if your document
# supports multiple NSWindowControllers, you should remove this
# method and override makeWindowControllers instead.
return "MyDocument"
end
def windowControllerDidLoadNib(aController)
super_windowControllerDidLoadNib(aController)
# Add any code here that need to be executed once the
# windowController has loaded the document's window.
@mutex = Mutex.new
watch_for_changes
reload
end
###
# Receives the filename to load the db from
###
def readFromURL_ofType_error(url, type, error)
@file = url.to_s.gsub("file://localhost", '')
error = nil
return true
end
def isDocumentEdited
# can't edit documents yet, so always no
return false
end
###
# action to handle table select
###
def showTable(sender)
new_table = @table_names[sender.selectedRow]
if new_table != @table
@table = new_table
load_rows_and_columns
setup_table_columns
#clear the sort descriptors because we're on a new table now
@tableContentView.setSortDescriptors(NSArray.alloc.init)
@tableContentView.reloadData
end
end
ib_action :showTable
###
# Loads the db from file and populates the ui
###
def reload
load_table_names
load_rows_and_columns
@tableView.reloadData
@tableContentView.reloadData
end
###
# Calls reload if the db file has been modified since last reload
###
def conditional_reload
return if !File.exists?(@file)
new_mtime = File.new(@file).mtime
if @mtime.nil? || @mtime < new_mtime
@mtime = new_mtime
reload
end
end
private
###
# Loads all data for the current table into instance variables:
# @rows and @columns
###
def load_rows_and_columns
if @table
begin
db = SQLite3::Database.new(@file, :results_as_hash => false, :type_translation => false)
db.busy_timeout(100)
sql = "select * from #{ @table }"
sql += " order by #{ @order }" if @order and @order.strip != ''
result = db.execute2(sql)
@columns = result.shift
@rows = result
rescue SQLite3::SQLException => e
puts e
end
db.close
end
end
###
# Return all tables in the current db
###
def load_table_names
begin
db = SQLite3::Database.new(@file, :results_as_hash => false, :type_translation => false)
db.busy_timeout(100)
result = db.execute2("select name from sqlite_master where type in ('table', 'view') and name not like 'sqlite_%' order by name")
result.shift # throw away columns
@table_names = result.inject([]) do |array, row|
name = row.first
str = NSMutableString.alloc.initWithCapacity(name.length)
str.setString(name)
array << str
end
rescue SQLite3::SQLException => e
puts e
end
db.close
end
###
# Sets up the table content viewer to have the columns
# named in the current table
###
def setup_table_columns
while !(columns = @tableContentView.tableColumns).empty?
@tableContentView.removeTableColumn(columns.first)
end
@columns.each_with_index do |name, i|
column = NSTableColumn.alloc.initWithIdentifier(i)
column.headerCell.setStringValue(name)
column.setEditable(false)
sort = NSSortDescriptor.alloc.initWithKey_ascending_selector(name, true, "localizedCaseInsensitiveCompare:")
column.setSortDescriptorPrototype(sort)
@tableContentView.addTableColumn(column)
end
end
###
# Keeps an eye on the filesytem and reloads the db when there are changes to the db
###
def watch_for_changes
NSTimer.scheduledTimerWithTimeInterval_target_selector_userInfo_repeats(1.0, self, 'conditional_reload:', nil, true).retain
end
end