twterm 1.3.0 → 2.0.0.beta1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +14 -18
- data/bin/twterm +1 -1
- data/lib/twterm/app.rb +120 -30
- data/lib/twterm/client.rb +10 -13
- data/lib/twterm/completion_mamanger.rb +11 -6
- data/lib/twterm/direct_message.rb +6 -28
- data/lib/twterm/direct_message_composer.rb +10 -5
- data/lib/twterm/direct_message_manager.rb +5 -6
- data/lib/twterm/event/notification/abstract_notification.rb +27 -0
- data/lib/twterm/event/notification/error.rb +13 -0
- data/lib/twterm/event/notification/info.rb +13 -0
- data/lib/twterm/event/notification/success.rb +13 -0
- data/lib/twterm/event/notification/warning.rb +13 -0
- data/lib/twterm/event_dispatcher.rb +1 -1
- data/lib/twterm/extensions/array.rb +5 -0
- data/lib/twterm/extensions/enumerator/lazy.rb +3 -0
- data/lib/twterm/extensions/string.rb +0 -4
- data/lib/twterm/friendship.rb +1 -85
- data/lib/twterm/image/between.rb +31 -0
- data/lib/twterm/image/blank_line.rb +21 -0
- data/lib/twterm/image/bold.rb +31 -0
- data/lib/twterm/image/brackets.rb +21 -0
- data/lib/twterm/image/color.rb +45 -0
- data/lib/twterm/image/empty.rb +21 -0
- data/lib/twterm/image/horizontal_sequential_image.rb +48 -0
- data/lib/twterm/image/parens.rb +21 -0
- data/lib/twterm/image/string_image.rb +38 -0
- data/lib/twterm/image/vertical_sequential_image.rb +43 -0
- data/lib/twterm/image.rb +107 -0
- data/lib/twterm/key_mapper/abstract_key_mapper.rb +51 -0
- data/lib/twterm/key_mapper/app_key_mapper.rb +13 -0
- data/lib/twterm/key_mapper/cursor_key_mapper.rb +13 -0
- data/lib/twterm/key_mapper/general_key_mapper.rb +18 -0
- data/lib/twterm/key_mapper/no_such_command.rb +20 -0
- data/lib/twterm/key_mapper/no_such_key.rb +16 -0
- data/lib/twterm/key_mapper/status_key_mapper.rb +18 -0
- data/lib/twterm/key_mapper/tab_key_mapper.rb +31 -0
- data/lib/twterm/key_mapper.rb +127 -0
- data/lib/twterm/list.rb +0 -31
- data/lib/twterm/notifier.rb +7 -7
- data/lib/twterm/repository/abstract_entity_repository.rb +41 -0
- data/lib/twterm/repository/abstract_expirable_entity_repository.rb +35 -0
- data/lib/twterm/repository/abstract_repository.rb +64 -0
- data/lib/twterm/repository/direct_message_repository.rb +14 -0
- data/lib/twterm/repository/friendship_repository.rb +108 -0
- data/lib/twterm/repository/hashtag_repository.rb +39 -0
- data/lib/twterm/repository/list_repository.rb +14 -0
- data/lib/twterm/repository/status_repository.rb +36 -0
- data/lib/twterm/repository/user_repository.rb +22 -0
- data/lib/twterm/rest_client.rb +107 -63
- data/lib/twterm/screen.rb +21 -15
- data/lib/twterm/search_query_window.rb +139 -0
- data/lib/twterm/status.rb +14 -108
- data/lib/twterm/streaming_client.rb +13 -12
- data/lib/twterm/tab/base.rb +48 -8
- data/lib/twterm/tab/direct_message/conversation.rb +53 -52
- data/lib/twterm/tab/direct_message/conversation_list.rb +46 -45
- data/lib/twterm/tab/dumpable.rb +3 -3
- data/lib/twterm/tab/key_assignments_cheatsheet.rb +58 -57
- data/lib/twterm/tab/loadable.rb +20 -0
- data/lib/twterm/tab/new/list.rb +32 -43
- data/lib/twterm/tab/new/search.rb +31 -44
- data/lib/twterm/tab/new/start.rb +44 -55
- data/lib/twterm/tab/new/user.rb +15 -12
- data/lib/twterm/tab/rate_limit_status.rb +84 -0
- data/lib/twterm/tab/scrollable.rb +39 -19
- data/lib/twterm/tab/searchable.rb +133 -0
- data/lib/twterm/tab/statuses/base.rb +139 -129
- data/lib/twterm/tab/statuses/conversation.rb +26 -15
- data/lib/twterm/tab/statuses/favorites.rb +10 -8
- data/lib/twterm/tab/statuses/home.rb +10 -9
- data/lib/twterm/tab/statuses/list_timeline.rb +12 -8
- data/lib/twterm/tab/statuses/mentions.rb +17 -11
- data/lib/twterm/tab/statuses/search.rb +8 -5
- data/lib/twterm/tab/statuses/user_timeline.rb +11 -8
- data/lib/twterm/tab/user_list_management.rb +109 -0
- data/lib/twterm/tab/user_tab.rb +125 -126
- data/lib/twterm/tab/users/base.rb +39 -41
- data/lib/twterm/tab/users/followers.rb +9 -6
- data/lib/twterm/tab/users/friends.rb +9 -6
- data/lib/twterm/tab_manager.rb +64 -40
- data/lib/twterm/tweetbox.rb +18 -13
- data/lib/twterm/uri_opener.rb +2 -1
- data/lib/twterm/user.rb +2 -110
- data/lib/twterm/version.rb +1 -1
- data/lib/twterm/view.rb +30 -0
- data/lib/twterm.rb +3 -9
- data/spec/fixtures/status.json +107 -0
- data/spec/fixtures/user.json +102 -0
- data/spec/spec_helper.rb +7 -0
- data/spec/supports/shared_examples/abstract_key_mapper.rb +17 -0
- data/spec/twterm/extension/enumerator/lazy_spec.rb +11 -0
- data/spec/twterm/friendship_spec.rb +0 -102
- data/spec/twterm/image/blank_line_spec.rb +11 -0
- data/spec/twterm/image/brackets_spec.rb +12 -0
- data/spec/twterm/image/color_spec.rb +22 -0
- data/spec/twterm/image/empry_spec.rb +11 -0
- data/spec/twterm/image/horizontal_sequential_image_spec.rb +15 -0
- data/spec/twterm/image/parens_spec.rb +12 -0
- data/spec/twterm/image/string_image_spec.rb +12 -0
- data/spec/twterm/image/vertical_sequential_image_spec.rb +14 -0
- data/spec/twterm/image_spec.rb +65 -0
- data/spec/twterm/key_mapper/abstract_key_mapper_spec.rb +21 -0
- data/spec/twterm/key_mapper/app_key_mapper_spec.rb +7 -0
- data/spec/twterm/key_mapper/status_key_mapper_spec.rb +7 -0
- data/spec/twterm/key_mapper/tab_key_mapper_spec.rb +7 -0
- data/spec/twterm/repository/friendship_repository_spec.rb +108 -0
- data/spec/twterm/status_spec.rb +58 -0
- data/spec/twterm/user_spec.rb +94 -0
- data/twterm.gemspec +13 -10
- metadata +129 -35
- data/lib/twterm/event/notification.rb +0 -33
- data/lib/twterm/extensions/integer.rb +0 -5
- data/lib/twterm/filter_query_window.rb +0 -91
- data/lib/twterm/filterable_list.rb +0 -41
- data/lib/twterm/history/base.rb +0 -21
- data/lib/twterm/history/hashtag.rb +0 -13
- data/lib/twterm/history/savable.rb +0 -37
- data/lib/twterm/history/screen_name.rb +0 -11
- data/lib/twterm/promise.rb +0 -143
@@ -1,18 +1,21 @@
|
|
1
|
+
require 'concurrent'
|
2
|
+
|
1
3
|
require 'twterm/event/open_uri'
|
2
4
|
require 'twterm/event/status/delete'
|
3
5
|
require 'twterm/publisher'
|
4
6
|
require 'twterm/subscriber'
|
5
7
|
require 'twterm/tab/base'
|
8
|
+
require 'twterm/tab/loadable'
|
6
9
|
require 'twterm/utils'
|
7
10
|
|
8
11
|
module Twterm
|
9
12
|
module Tab
|
10
13
|
module Statuses
|
11
14
|
class Base < Tab::Base
|
12
|
-
include FilterableList
|
13
15
|
include Publisher
|
14
|
-
include
|
16
|
+
include Searchable
|
15
17
|
include Subscriber
|
18
|
+
include Loadable
|
16
19
|
include Utils
|
17
20
|
|
18
21
|
def append(status)
|
@@ -20,62 +23,81 @@ module Twterm
|
|
20
23
|
|
21
24
|
return if @status_ids.include?(status.id)
|
22
25
|
|
23
|
-
@status_ids.
|
26
|
+
@status_ids.push(status.id)
|
24
27
|
status.split(window.maxx - 4)
|
25
|
-
status.touch!
|
26
28
|
scroller.item_appended!
|
27
|
-
|
29
|
+
render
|
28
30
|
end
|
29
31
|
|
30
32
|
def delete(status_id)
|
31
|
-
|
32
|
-
|
33
|
+
app.status_repository.delete(status_id)
|
34
|
+
render
|
33
35
|
end
|
34
36
|
|
35
37
|
def destroy_status
|
36
|
-
status =
|
38
|
+
status = highlighted_original_status
|
37
39
|
|
38
|
-
|
40
|
+
client.destroy_status(status)
|
39
41
|
end
|
40
42
|
|
41
43
|
def drawable_item_count
|
42
|
-
statuses.
|
44
|
+
statuses.drop(scroller.offset).lazy
|
43
45
|
.map { |s| s.split(window.maxx - 4).count + 2 }
|
44
46
|
.scan(0, :+)
|
45
|
-
.
|
47
|
+
.each_cons(2)
|
48
|
+
.select { |_, l| l < window.maxy }
|
46
49
|
.count
|
47
50
|
end
|
48
51
|
|
49
52
|
def favorite
|
50
|
-
|
53
|
+
status = highlighted_original_status
|
54
|
+
|
55
|
+
return if status.nil?
|
51
56
|
|
52
|
-
|
53
|
-
|
54
|
-
|
57
|
+
if status.favorited?
|
58
|
+
client.unfavorite(status)
|
59
|
+
.then { status.unfavorite! }
|
60
|
+
else
|
61
|
+
client.favorite(status)
|
62
|
+
.then { status.favorite! }
|
63
|
+
end
|
64
|
+
.then { render }
|
55
65
|
end
|
56
66
|
|
57
67
|
def fetch
|
58
68
|
fail NotImplementedError, 'fetch method must be implemented'
|
59
69
|
end
|
60
70
|
|
61
|
-
def initialize
|
62
|
-
super
|
71
|
+
def initialize(app, client)
|
72
|
+
super(app, client)
|
63
73
|
|
64
|
-
@status_ids =
|
74
|
+
@status_ids = Concurrent::Array.new
|
65
75
|
|
66
76
|
subscribe(Event::Status::Delete) { |e| delete(e.status_id) }
|
67
77
|
end
|
68
78
|
|
69
79
|
def items
|
70
|
-
statuses
|
80
|
+
statuses
|
81
|
+
end
|
82
|
+
|
83
|
+
def matches?(status, query)
|
84
|
+
user = app.user_repository.find(status.user_id)
|
85
|
+
|
86
|
+
[
|
87
|
+
status.text,
|
88
|
+
user.screen_name,
|
89
|
+
user.name
|
90
|
+
].any? { |x| x.downcase.include?(query.downcase) }
|
71
91
|
end
|
72
92
|
|
73
93
|
def open_link
|
74
|
-
|
94
|
+
status = highlighted_original_status
|
95
|
+
|
96
|
+
return if status.nil?
|
75
97
|
|
76
|
-
status = highlighted_status
|
77
98
|
urls = status.urls.map(&:expanded_url) + status.media.map(&:expanded_url)
|
78
99
|
urls
|
100
|
+
.uniq
|
79
101
|
.map { |url| Event::OpenURI.new(url) }
|
80
102
|
.each { |e| publish(e) }
|
81
103
|
end
|
@@ -85,42 +107,40 @@ module Twterm
|
|
85
107
|
|
86
108
|
return if @status_ids.include?(status.id)
|
87
109
|
|
88
|
-
@status_ids
|
110
|
+
@status_ids.unshift(status.id)
|
89
111
|
status.split(window.maxx - 4)
|
90
|
-
status.touch!
|
91
112
|
scroller.item_prepended!
|
92
|
-
|
113
|
+
render
|
93
114
|
end
|
94
115
|
|
95
116
|
def reply
|
96
117
|
return if highlighted_status.nil?
|
97
|
-
|
118
|
+
|
119
|
+
app.tweetbox.compose(highlighted_original_status)
|
98
120
|
end
|
99
121
|
|
100
122
|
def respond_to_key(key)
|
101
123
|
return true if scroller.respond_to_key(key)
|
102
124
|
|
125
|
+
k = KeyMapper.instance
|
126
|
+
|
103
127
|
case key
|
104
|
-
when
|
128
|
+
when k[:status, :conversation]
|
105
129
|
show_conversation
|
106
|
-
when
|
130
|
+
when k[:status, :destroy]
|
107
131
|
destroy_status
|
108
|
-
when
|
132
|
+
when k[:status, :like]
|
109
133
|
favorite
|
110
|
-
when
|
134
|
+
when k[:status, :open_link]
|
111
135
|
open_link
|
112
|
-
when
|
136
|
+
when k[:status, :reply]
|
113
137
|
reply
|
114
|
-
when
|
138
|
+
when k[:status, :retweet]
|
115
139
|
retweet
|
116
|
-
when
|
140
|
+
when k[:tab, :reload]
|
117
141
|
fetch
|
118
|
-
when
|
142
|
+
when k[:status, :user]
|
119
143
|
show_user
|
120
|
-
when ?/
|
121
|
-
filter
|
122
|
-
when ?q
|
123
|
-
reset_filter
|
124
144
|
else
|
125
145
|
return false
|
126
146
|
end
|
@@ -128,120 +148,110 @@ module Twterm
|
|
128
148
|
end
|
129
149
|
|
130
150
|
def retweet
|
131
|
-
|
132
|
-
|
151
|
+
status = highlighted_original_status
|
152
|
+
|
153
|
+
return if status.nil?
|
154
|
+
|
155
|
+
if status.retweeted?
|
156
|
+
client.unretweet(status)
|
157
|
+
.then { status.unretweet! }
|
158
|
+
else
|
159
|
+
client.retweet(status)
|
160
|
+
.then { status.retweet! }
|
161
|
+
end
|
162
|
+
.then { render }
|
133
163
|
end
|
134
164
|
|
135
165
|
def show_conversation
|
136
|
-
|
137
|
-
|
138
|
-
|
166
|
+
status = highlighted_original_status
|
167
|
+
|
168
|
+
return if status.nil?
|
169
|
+
|
170
|
+
tab = Tab::Statuses::Conversation.new(app, client, highlighted_original_status.id)
|
171
|
+
app.tab_manager.add_and_show(tab)
|
139
172
|
end
|
140
173
|
|
141
174
|
def show_user
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
175
|
+
status = highlighted_original_status
|
176
|
+
|
177
|
+
return if status.nil?
|
178
|
+
|
179
|
+
user_id = status.user_id
|
180
|
+
user_tab = Tab::UserTab.new(app, client, user_id)
|
181
|
+
app.tab_manager.add_and_show(user_tab)
|
146
182
|
end
|
147
183
|
|
148
184
|
def statuses
|
149
|
-
statuses = @status_ids.map { |id|
|
185
|
+
statuses = @status_ids.map { |id| app.status_repository.find(id) }.compact
|
150
186
|
@status_ids = statuses.map(&:id)
|
151
187
|
|
152
|
-
|
153
|
-
statuses
|
154
|
-
else
|
155
|
-
statuses.select { |s| s.matches?(filter_query) }
|
156
|
-
end
|
157
|
-
end
|
158
|
-
|
159
|
-
def touch_statuses
|
160
|
-
statuses.reverse.take(100).each(&:touch!)
|
188
|
+
statuses
|
161
189
|
end
|
162
190
|
|
163
191
|
def total_item_count
|
164
|
-
|
165
|
-
end
|
166
|
-
|
167
|
-
def update
|
168
|
-
line = 0
|
169
|
-
|
170
|
-
scroller.drawable_items.each.with_index(0) do |status, i|
|
171
|
-
formatted_lines = status.split(window.maxx - 4).count
|
172
|
-
window.with_color(:black, :magenta) do
|
173
|
-
(formatted_lines + 1).times do |j|
|
174
|
-
window.setpos(line + j, 0)
|
175
|
-
window.addch(' ')
|
176
|
-
end
|
177
|
-
end if scroller.current_item?(i)
|
178
|
-
|
179
|
-
window.setpos(line, 2)
|
180
|
-
|
181
|
-
window.bold do
|
182
|
-
window.with_color(status.user.color) do
|
183
|
-
window.addstr(status.user.name)
|
184
|
-
end
|
185
|
-
end
|
186
|
-
|
187
|
-
window.addstr(" (@#{status.user.screen_name}) [#{status.date}] ")
|
188
|
-
|
189
|
-
unless status.retweeted_by.nil?
|
190
|
-
window.addstr('(retweeted by ')
|
191
|
-
window.bold do
|
192
|
-
window.addstr("@#{status.retweeted_by.screen_name}")
|
193
|
-
end
|
194
|
-
window.addstr(') ')
|
195
|
-
end
|
196
|
-
|
197
|
-
if status.favorited?
|
198
|
-
window.with_color(:black, :red) do
|
199
|
-
window.addch(' ')
|
200
|
-
end
|
201
|
-
|
202
|
-
window.addch(' ')
|
203
|
-
end
|
204
|
-
|
205
|
-
if status.retweeted?
|
206
|
-
window.with_color(:black, :green) do
|
207
|
-
window.addch(' ')
|
208
|
-
end
|
209
|
-
window.addch(' ')
|
210
|
-
end
|
211
|
-
|
212
|
-
if status.favorite_count > 0
|
213
|
-
window.with_color(:red) do
|
214
|
-
window.addstr("#{status.favorite_count}like#{status.favorite_count > 1 ? 's' : ''}")
|
215
|
-
end
|
216
|
-
window.addch(' ')
|
217
|
-
end
|
218
|
-
|
219
|
-
if status.retweet_count > 0
|
220
|
-
window.with_color(:green) do
|
221
|
-
window.addstr("#{status.retweet_count}RT#{status.retweet_count > 1 ? 's' : ''}")
|
222
|
-
end
|
223
|
-
window.addch(' ')
|
224
|
-
end
|
225
|
-
|
226
|
-
status.split(window.maxx - 4).each do |str|
|
227
|
-
line += 1
|
228
|
-
window.setpos(line, 2)
|
229
|
-
window.addstr(str)
|
230
|
-
end
|
231
|
-
|
232
|
-
line += 2
|
233
|
-
end
|
192
|
+
search_query.empty? ? @status_ids.count : statuses.count
|
234
193
|
end
|
235
194
|
|
236
195
|
private
|
237
196
|
|
197
|
+
def highlighted_original_status
|
198
|
+
status = highlighted_status
|
199
|
+
|
200
|
+
status.retweet? ? app.status_repository.find(status.retweeted_status_id) : status
|
201
|
+
end
|
202
|
+
|
238
203
|
def highlighted_status
|
239
|
-
statuses[scroller.
|
204
|
+
statuses[scroller.index]
|
205
|
+
end
|
206
|
+
|
207
|
+
def image
|
208
|
+
return Image.string(initially_loaded? ? 'No results found' : 'Loading...') if items.empty?
|
209
|
+
|
210
|
+
scroller.drawable_items.map.with_index(0) do |status, i|
|
211
|
+
original = status.retweet? ? app.status_repository.find(status.retweeted_status_id) : status
|
212
|
+
user = app.user_repository.find(original.user_id)
|
213
|
+
retweeted_by = app.user_repository.find(status.user_id)
|
214
|
+
|
215
|
+
header = [
|
216
|
+
!Image.string(user.name).color(user.color),
|
217
|
+
Image.string("@#{user.screen_name}").parens,
|
218
|
+
Image.string(original.date.to_s).brackets,
|
219
|
+
(Image.whitespace.color(:black, :red) if original.favorited?),
|
220
|
+
(Image.whitespace.color(:black, :green) if original.retweeted?),
|
221
|
+
((Image.string('retweeted by ') - !Image.string("@#{retweeted_by.screen_name}")).parens if status.retweet?),
|
222
|
+
((Image.number(original.favorite_count) - Image.plural(original.favorite_count, 'like')).color(:red) if original.favorite_count.positive?),
|
223
|
+
((Image.number(original.retweet_count) - Image.plural(original.retweet_count, 'RT')).color(:green) if original.retweet_count.positive?),
|
224
|
+
].compact.intersperse(Image.whitespace).reduce(Image.empty, :-)
|
225
|
+
|
226
|
+
body = original
|
227
|
+
.split(window.maxx - 4)
|
228
|
+
.map(&Image.method(:string))
|
229
|
+
.reduce(Image.empty, :|)
|
230
|
+
|
231
|
+
s = header | body
|
232
|
+
|
233
|
+
Image.cursor(s.height, scroller.current_index?(i)) - Image.whitespace - s
|
234
|
+
end
|
235
|
+
.intersperse(Image.blank_line)
|
236
|
+
.reduce(Image.empty, :|)
|
240
237
|
end
|
241
238
|
|
242
239
|
def sort
|
243
|
-
|
244
|
-
|
240
|
+
return if items.empty? || scroller.current_item.nil?
|
241
|
+
|
242
|
+
repo = app.status_repository
|
243
|
+
|
244
|
+
@status_ids &= repo.ids
|
245
|
+
@status_ids.sort_by! { |id| repo.find(id).created_at }.reverse!
|
246
|
+
|
247
|
+
formerly_selected_status_id = scroller.current_item.id
|
248
|
+
|
249
|
+
unless formerly_selected_status_id.nil?
|
250
|
+
new_index = @status_ids.index(formerly_selected_status_id)
|
251
|
+
scroller.move_to(new_index) unless new_index.nil?
|
252
|
+
end
|
253
|
+
|
254
|
+
self
|
245
255
|
end
|
246
256
|
end
|
247
257
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
require 'concurrent'
|
2
|
+
|
1
3
|
require 'twterm/tab/statuses/base'
|
2
4
|
|
3
5
|
module Twterm
|
@@ -12,37 +14,46 @@ module Twterm
|
|
12
14
|
other.is_a?(self.class) && status == other.status
|
13
15
|
end
|
14
16
|
|
15
|
-
def
|
16
|
-
status.
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
17
|
+
def fetch_ancestor(status)
|
18
|
+
in_reply_to_status_id = status.in_reply_to_status_id
|
19
|
+
|
20
|
+
if in_reply_to_status_id.nil?
|
21
|
+
Concurrent::Promise.fulfill(nil)
|
22
|
+
elsif (instance = app.status_repository.find(in_reply_to_status_id))
|
23
|
+
Concurrent::Promise.fulfill(instance)
|
24
|
+
else
|
25
|
+
client.show_status(in_reply_to_status_id)
|
21
26
|
end
|
27
|
+
.then do |in_reply_to|
|
28
|
+
next if in_reply_to.nil?
|
29
|
+
append(in_reply_to)
|
30
|
+
sort
|
31
|
+
fetch_ancestor(in_reply_to)
|
32
|
+
end
|
22
33
|
end
|
23
34
|
|
24
|
-
def
|
25
|
-
status.
|
35
|
+
def find_descendants(status)
|
36
|
+
app.status_repository.find_replies_for(status.id).each do |reply|
|
26
37
|
prepend(reply)
|
27
|
-
|
28
|
-
Thread.new { fetch_replies(reply) }
|
38
|
+
find_descendants(reply)
|
29
39
|
end
|
40
|
+
sort
|
30
41
|
end
|
31
42
|
|
32
43
|
def dump
|
33
44
|
@status.id
|
34
45
|
end
|
35
46
|
|
36
|
-
def initialize(status_id)
|
37
|
-
super()
|
47
|
+
def initialize(app, client, status_id)
|
48
|
+
super(app, client)
|
38
49
|
|
39
|
-
|
50
|
+
find_or_fetch_status(status_id).then do |status|
|
40
51
|
@status = status
|
41
52
|
|
42
53
|
append(status)
|
43
54
|
scroller.move_to_top
|
44
|
-
|
45
|
-
|
55
|
+
fetch_ancestor(status)
|
56
|
+
find_descendants(status)
|
46
57
|
end
|
47
58
|
end
|
48
59
|
|
@@ -17,23 +17,25 @@ module Twterm
|
|
17
17
|
end
|
18
18
|
|
19
19
|
def fetch
|
20
|
-
|
21
|
-
statuses.
|
20
|
+
client.favorites(@user.id).then do |statuses|
|
21
|
+
statuses.each { |s| append(s) }
|
22
22
|
sort
|
23
|
-
yield if block_given?
|
24
23
|
end
|
25
24
|
end
|
26
25
|
|
27
|
-
def initialize(user_id)
|
28
|
-
super()
|
26
|
+
def initialize(app, client, user_id)
|
27
|
+
super(app, client)
|
29
28
|
|
30
29
|
@user_id = user_id
|
31
30
|
|
32
|
-
|
31
|
+
find_or_fetch_user(user_id).then do |user|
|
33
32
|
@user = user
|
34
|
-
|
33
|
+
app.tab_manager.refresh_window
|
35
34
|
|
36
|
-
fetch
|
35
|
+
fetch.then do
|
36
|
+
initially_loaded!
|
37
|
+
scroller.move_to_top
|
38
|
+
end
|
37
39
|
end
|
38
40
|
end
|
39
41
|
|
@@ -15,21 +15,22 @@ module Twterm
|
|
15
15
|
end
|
16
16
|
|
17
17
|
def fetch
|
18
|
-
|
19
|
-
statuses.each(
|
18
|
+
client.home_timeline.then do |statuses|
|
19
|
+
statuses.each { |s| append(s) }
|
20
20
|
sort
|
21
|
-
yield if block_given?
|
22
21
|
end
|
23
22
|
end
|
24
23
|
|
25
|
-
def initialize(client)
|
26
|
-
|
24
|
+
def initialize(app, client)
|
25
|
+
super(app, client)
|
27
26
|
|
28
|
-
|
29
|
-
|
30
|
-
|
27
|
+
subscribe(Event::Status::Timeline) { |e| prepend(e.status) }
|
28
|
+
|
29
|
+
fetch.then do
|
30
|
+
initially_loaded!
|
31
|
+
scroller.move_to_top
|
32
|
+
end
|
31
33
|
|
32
|
-
fetch { scroller.move_to_top }
|
33
34
|
@auto_reloader = Scheduler.new(180) { fetch }
|
34
35
|
end
|
35
36
|
|
@@ -8,25 +8,29 @@ module Twterm
|
|
8
8
|
|
9
9
|
attr_reader :list
|
10
10
|
|
11
|
-
def initialize(list_id)
|
12
|
-
super()
|
11
|
+
def initialize(app, client, list_id)
|
12
|
+
super(app, client)
|
13
13
|
|
14
14
|
self.title = 'Loading...'.freeze
|
15
15
|
|
16
|
-
|
16
|
+
find_or_fetch_list(list_id).then do |list|
|
17
17
|
@list = list
|
18
18
|
self.title = @list.full_name
|
19
|
-
|
20
|
-
|
19
|
+
app.tab_manager.refresh_window
|
20
|
+
|
21
|
+
fetch.then do
|
22
|
+
initially_loaded!
|
23
|
+
scroller.move_to_top
|
24
|
+
end
|
25
|
+
|
21
26
|
@auto_reloader = Scheduler.new(300) { fetch }
|
22
27
|
end
|
23
28
|
end
|
24
29
|
|
25
30
|
def fetch
|
26
|
-
|
27
|
-
statuses.
|
31
|
+
client.list_timeline(@list).then do |statuses|
|
32
|
+
statuses.each { |s| append(s) }
|
28
33
|
sort
|
29
|
-
yield if block_given?
|
30
34
|
end
|
31
35
|
end
|
32
36
|
|
@@ -11,24 +11,30 @@ module Twterm
|
|
11
11
|
end
|
12
12
|
|
13
13
|
def fetch
|
14
|
-
|
15
|
-
statuses.reverse.each(&method(:prepend))
|
16
|
-
sort
|
17
|
-
yield if block_given?
|
18
|
-
end
|
14
|
+
client.mentions
|
19
15
|
end
|
20
16
|
|
21
|
-
def initialize(client)
|
17
|
+
def initialize(app, client)
|
22
18
|
fail ArgumentError, 'argument must be an instance of Client class' unless client.is_a? Client
|
23
19
|
|
24
|
-
super()
|
25
|
-
|
26
|
-
@client = client
|
20
|
+
super(app, client)
|
27
21
|
|
28
22
|
subscribe(Event::Status::Mention) { |e| prepend(e.status) }
|
29
23
|
|
30
|
-
fetch
|
31
|
-
|
24
|
+
fetch.then do |statuses|
|
25
|
+
initially_loaded!
|
26
|
+
statuses.each { |s| append(s) }
|
27
|
+
scroller.move_to_top
|
28
|
+
end
|
29
|
+
|
30
|
+
@auto_reloader = Scheduler.new(300) { reload }
|
31
|
+
end
|
32
|
+
|
33
|
+
def reload
|
34
|
+
fetch.then do |statuses|
|
35
|
+
statuses.each { |s| append(s) }
|
36
|
+
sort
|
37
|
+
end
|
32
38
|
end
|
33
39
|
|
34
40
|
def title
|
@@ -22,20 +22,23 @@ module Twterm
|
|
22
22
|
end
|
23
23
|
|
24
24
|
def fetch
|
25
|
-
|
25
|
+
client.search(@query).then do |statuses|
|
26
26
|
statuses.each(&method(:append))
|
27
27
|
sort
|
28
|
-
yield if block_given?
|
29
28
|
end
|
30
29
|
end
|
31
30
|
|
32
|
-
def initialize(query)
|
33
|
-
super()
|
31
|
+
def initialize(app, client, query)
|
32
|
+
super(app, client)
|
34
33
|
|
35
34
|
@query = query
|
36
35
|
@title = "\"#{@query}\""
|
37
36
|
|
38
|
-
fetch
|
37
|
+
fetch.then do
|
38
|
+
initially_loaded!
|
39
|
+
scroller.move_to_top
|
40
|
+
end
|
41
|
+
|
39
42
|
@auto_reloader = Scheduler.new(300) { fetch }
|
40
43
|
end
|
41
44
|
end
|
@@ -22,23 +22,26 @@ module Twterm
|
|
22
22
|
end
|
23
23
|
|
24
24
|
def fetch
|
25
|
-
|
26
|
-
statuses.
|
25
|
+
client.user_timeline(@user.id).then do |statuses|
|
26
|
+
statuses.each { |s| append(s) }
|
27
27
|
sort
|
28
|
-
yield if block_given?
|
29
28
|
end
|
30
29
|
end
|
31
30
|
|
32
|
-
def initialize(user_id)
|
33
|
-
super()
|
31
|
+
def initialize(app, client, user_id)
|
32
|
+
super(app, client)
|
34
33
|
|
35
34
|
@user_id = user_id
|
36
35
|
|
37
|
-
|
36
|
+
find_or_fetch_user(user_id).then do |user|
|
38
37
|
@user = user
|
39
|
-
|
38
|
+
app.tab_manager.refresh_window
|
39
|
+
|
40
|
+
fetch.then do
|
41
|
+
initially_loaded!
|
42
|
+
scroller.move_to_top
|
43
|
+
end
|
40
44
|
|
41
|
-
fetch { scroller.move_to_top }
|
42
45
|
@auto_reloader = Scheduler.new(120) { fetch }
|
43
46
|
end
|
44
47
|
end
|