1 package be
.nikiroo
.fanfix
.reader
.ui
;
3 import java
.awt
.BorderLayout
;
4 import java
.awt
.EventQueue
;
5 import java
.awt
.event
.ActionEvent
;
6 import java
.awt
.event
.ActionListener
;
7 import java
.io
.IOException
;
8 import java
.lang
.reflect
.InvocationTargetException
;
9 import java
.util
.ArrayList
;
10 import java
.util
.List
;
12 import javax
.swing
.JButton
;
13 import javax
.swing
.JComboBox
;
14 import javax
.swing
.JFrame
;
15 import javax
.swing
.JPanel
;
16 import javax
.swing
.JScrollPane
;
17 import javax
.swing
.JTabbedPane
;
18 import javax
.swing
.JTextField
;
20 import be
.nikiroo
.fanfix
.Instance
;
21 import be
.nikiroo
.fanfix
.data
.MetaData
;
22 import be
.nikiroo
.fanfix
.searchable
.BasicSearchable
;
23 import be
.nikiroo
.fanfix
.searchable
.SearchableTag
;
24 import be
.nikiroo
.fanfix
.supported
.SupportType
;
27 * This frame will allow you to search through the supported websites for new
32 public class GuiReaderSearch
extends JFrame
{
33 private static final long serialVersionUID
= 1L;
35 private List
<SupportType
> supportTypes
;
36 private SupportType supportType
;
37 private List
<SearchableTag
> tags
;
38 private String keywords
;
42 private JComboBox
<SupportType
> comboSupportTypes
;
43 private JTabbedPane searchTabs
;
45 private boolean seeWordcount
;
46 private GuiReaderGroup books
;
48 public GuiReaderSearch(GuiReader reader
) {
50 super("Browse stories");
51 setLayout(new BorderLayout());
54 tags
= new ArrayList
<SearchableTag
>();
58 supportTypes
= new ArrayList
<SupportType
>();
59 for (SupportType type
: SupportType
.values()) {
60 if (BasicSearchable
.getSearchable(type
) != null) {
61 supportTypes
.add(type
);
64 supportType
= supportTypes
.isEmpty() ?
null : supportTypes
.get(0);
66 JPanel top
= new JPanel(new BorderLayout());
67 comboSupportTypes
= new JComboBox
<SupportType
>(
68 supportTypes
.toArray(new SupportType
[] {}));
69 comboSupportTypes
.addActionListener(new ActionListener() {
71 public void actionPerformed(ActionEvent e
) {
72 setSupportType((SupportType
) comboSupportTypes
76 top
.add(comboSupportTypes
, BorderLayout
.NORTH
);
79 searchTabs
= new JTabbedPane();
80 searchTabs
.addTab("By name", createByNameSearchPanel());
81 searchTabs
.addTab("By tags", createByTagSearchPanel());
83 top
.add(searchTabs
, BorderLayout
.CENTER
);
85 add(top
, BorderLayout
.NORTH
);
87 books
= new GuiReaderGroup(reader
, null, null);
88 JScrollPane scroll
= new JScrollPane(books
);
89 scroll
.getVerticalScrollBar().setUnitIncrement(16);
90 add(scroll
, BorderLayout
.CENTER
);
93 public void setSupportType(SupportType supportType
) {
94 this.supportType
= supportType
;
95 comboSupportTypes
.setSelectedItem(supportType
);
99 private JPanel
createByNameSearchPanel() {
100 JPanel byName
= new JPanel(new BorderLayout());
102 final JTextField keywordsField
= new JTextField();
103 byName
.add(keywordsField
, BorderLayout
.CENTER
);
106 JButton submit
= new JButton("Search");
107 byName
.add(submit
, BorderLayout
.EAST
);
109 // TODO: ENTER -> search
111 submit
.addActionListener(new ActionListener() {
113 public void actionPerformed(ActionEvent e
) {
114 search(supportType
, keywordsField
.getText(), page
, 0);
121 private JPanel
createByTagSearchPanel() {
122 JPanel byTag
= new JPanel();
123 JPanel searchBars
= new JPanel();
124 add(searchBars
, BorderLayout
.NORTH
);
129 // item 0 = no selction, else = default selection
130 public void search(final SupportType searchOn
, final String keywords
,
131 final int page
, final int item
) {
132 setSupportType(searchOn
);
133 this.keywords
= keywords
;
136 new Thread(new Runnable() {
139 BasicSearchable search
= BasicSearchable
140 .getSearchable(searchOn
);
145 maxPage
= search
.searchPages(keywords
);
146 } catch (IOException e
) {
147 Instance
.getTraceHandler().error(e
);
149 updateBooks(new ArrayList
<GuiReaderBookInfo
>());
150 updatePages(0, maxPage
);
152 List
<GuiReaderBookInfo
> infos
= new ArrayList
<GuiReaderBookInfo
>();
154 for (MetaData meta
: search
.search(keywords
, page
)) {
155 infos
.add(GuiReaderBookInfo
.fromMeta(meta
));
157 } catch (IOException e
) {
158 Instance
.getTraceHandler().error(e
);
162 updatePages(page
, maxPage
);
165 if (item
> 0 && item
<= books
.getBooksCount()) {
166 // TODO: "click" on item ITEM
173 private void updatePages(final int page
, final Integer maxPage
) {
174 inUi(new Runnable() {
177 GuiReaderSearch
.this.page
= page
;
178 GuiReaderSearch
.this.maxPage
= maxPage
;
180 System
.out
.println("page: " + page
);
181 System
.out
.println("max page: " + maxPage
);
186 private void updateBooks(final List
<GuiReaderBookInfo
> infos
) {
187 inUi(new Runnable() {
190 books
.refreshBooks(infos
, seeWordcount
);
195 private void searchTag(SupportType searchOn
, int page
, int item
,
196 boolean sync
, Integer
... tags
) throws IOException
{
198 BasicSearchable search
= BasicSearchable
.getSearchable(searchOn
);
199 SearchableTag stag
= search
.getTag(tags
);
203 System
.out
.println("Known tags: ");
205 for (SearchableTag s
: search
.getTags()) {
206 System
.out
.println(String
.format("%d: %s", i
, s
.getName()));
212 search
.search(stag
, 1);
213 System
.out
.println(stag
.getPages());
215 System
.out
.println(stag
.getCount());
218 List
<MetaData
> metas
= null;
219 List
<SearchableTag
> subtags
= null;
223 metas
= search
.search(stag
, page
);
224 count
= metas
.size();
226 subtags
= stag
.getChildren();
227 count
= subtags
.size();
233 MetaData meta
= metas
.get(item
- 1);
234 // displayStory(meta);
236 SearchableTag subtag
= subtags
.get(item
- 1);
237 // displayTag(subtag);
240 System
.out
.println("Invalid item: only " + count
246 System
.out
.println(String
.format("Content of %s: ",
248 // displayStories(metas);
251 System
.out
.println(String
.format("Subtags of %s: ",
253 // displayTags(subtags);
261 * Process the given action in the main Swing UI thread.
263 * The code will make sure the current thread is the main UI thread and, if
264 * not, will switch to it before executing the runnable.
266 * Synchronous operation.
271 public void inUi(final Runnable run
) {
272 if (EventQueue
.isDispatchThread()) {
276 EventQueue
.invokeAndWait(run
);
277 } catch (InterruptedException e
) {
278 Instance
.getTraceHandler().error(e
);
279 } catch (InvocationTargetException e
) {
280 Instance
.getTraceHandler().error(e
);