タイニー番組ナビゲータ本体
Révision | 0838e9b02ee01ef49f9accfade7a86366d6c5580 (tree) |
---|---|
l'heure | 2019-12-27 19:11:44 |
Auteur | Masahiko Kimura <mkimura@u01....> |
Commiter | Masahiko Kimura |
Ver.1.12.8 (2019/12/27)
@@ -15,6 +15,8 @@ import java.awt.event.KeyEvent; | ||
15 | 15 | import java.awt.event.MouseAdapter; |
16 | 16 | import java.awt.event.MouseEvent; |
17 | 17 | import java.awt.event.MouseListener; |
18 | +import java.beans.PropertyChangeEvent; | |
19 | +import java.beans.PropertyChangeListener; | |
18 | 20 | import java.io.File; |
19 | 21 | import java.io.IOException; |
20 | 22 | import java.net.URI; |
@@ -382,6 +384,7 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
382 | 384 | |
383 | 385 | // コンポーネント |
384 | 386 | |
387 | + private JSplitPane jSplitPane_main = null; | |
385 | 388 | private JDetailPanel jTextPane_detail = null; |
386 | 389 | private JSplitPane jSplitPane_view = null; |
387 | 390 | private JPanel jPanel_tree = null; |
@@ -442,8 +445,7 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
442 | 445 | |
443 | 446 | // コンポーネントを追加 |
444 | 447 | this.setLayout(new BorderLayout()); |
445 | - this.add(getJTextPane_detail(), BorderLayout.PAGE_START); | |
446 | - this.add(getJSplitPane_view(), BorderLayout.CENTER); | |
448 | + this.add(getJSplitPane_main(), BorderLayout.CENTER); | |
447 | 449 | |
448 | 450 | // バグ対応 |
449 | 451 | if ( bounds.getListedColumnSize() == null ) { |
@@ -1526,6 +1528,9 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
1526 | 1528 | */ |
1527 | 1529 | public void setDetailVisible(boolean aFlag) { |
1528 | 1530 | jTextPane_detail.setVisible(aFlag); |
1531 | + | |
1532 | + if (aFlag) | |
1533 | + jSplitPane_main.setDividerLocation(bounds.getListedDetailHeight()); | |
1529 | 1534 | } |
1530 | 1535 | |
1531 | 1536 | /** |
@@ -3845,7 +3850,48 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
3845 | 3850 | pop.show(jTree_tree, x, y); |
3846 | 3851 | } |
3847 | 3852 | |
3853 | + /* | |
3854 | + * 詳細欄関係 | |
3855 | + */ | |
3856 | + /* | |
3857 | + * 詳細欄の高さを初期化する | |
3858 | + */ | |
3859 | + private void initDetailHeight(){ | |
3860 | + if (bounds.getDetailRows() > 0){ | |
3861 | + resetDetailHeight(); | |
3862 | + } | |
3863 | + else{ | |
3864 | + int dh = bounds.getListedDetailHeight(); | |
3865 | + if (dh > 1) | |
3866 | + setDetailHeight(dh); | |
3867 | + else | |
3868 | + resetDetailHeight(); | |
3869 | + } | |
3870 | + } | |
3871 | + | |
3872 | + /* | |
3873 | + * 詳細欄の高さをセットする | |
3874 | + */ | |
3875 | + private void setDetailHeight(int height){ | |
3876 | + if (jTextPane_detail == null) | |
3877 | + return; | |
3878 | + | |
3879 | + jSplitPane_main.setDividerLocation(height); | |
3880 | + bounds.setListedDetailHeight(height); | |
3881 | + } | |
3882 | + | |
3883 | + /* | |
3884 | + * 詳細欄の高さをリセットする | |
3885 | + */ | |
3886 | + private void resetDetailHeight(){ | |
3887 | + if (jTextPane_detail == null) | |
3888 | + return; | |
3889 | + | |
3890 | + int rows = bounds.getDetailRows(); | |
3891 | + int height = jTextPane_detail.getHeightFromRows(rows > 0 ? rows : 4); | |
3848 | 3892 | |
3893 | + setDetailHeight(height); | |
3894 | + } | |
3849 | 3895 | |
3850 | 3896 | /******************************************************************************* |
3851 | 3897 | * コンポーネント |
@@ -3885,6 +3931,31 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
3885 | 3931 | * 部品 |
3886 | 3932 | */ |
3887 | 3933 | |
3934 | + /* | |
3935 | + * 詳細欄とツリー+リストを分割するペインを生成する | |
3936 | + */ | |
3937 | + private JSplitPane getJSplitPane_main() { | |
3938 | + if ( jSplitPane_main == null ) { | |
3939 | + | |
3940 | + jSplitPane_main = new JSplitPane(JSplitPane.VERTICAL_SPLIT); | |
3941 | + | |
3942 | + jSplitPane_main.setTopComponent(getJTextPane_detail()); | |
3943 | + jSplitPane_main.setBottomComponent(getJSplitPane_view()); | |
3944 | + | |
3945 | + initDetailHeight(); | |
3946 | + | |
3947 | + jSplitPane_main.addPropertyChangeListener(JSplitPane.DIVIDER_LOCATION_PROPERTY, new PropertyChangeListener() { | |
3948 | + @Override | |
3949 | + public void propertyChange(PropertyChangeEvent pce) { | |
3950 | + if (jTextPane_detail.isVisible()) | |
3951 | + bounds.setListedDetailHeight(jSplitPane_main.getDividerLocation()); | |
3952 | + } | |
3953 | + }); | |
3954 | + } | |
3955 | + | |
3956 | + return jSplitPane_main; | |
3957 | + } | |
3958 | + | |
3888 | 3959 | private JSplitPane getJSplitPane_view() { |
3889 | 3960 | if ( jSplitPane_view == null ) { |
3890 | 3961 | jSplitPane_view = new JSplitPane() { |
@@ -4278,7 +4349,8 @@ public abstract class AbsListedView extends JPanel implements TickTimerListener | ||
4278 | 4349 | |
4279 | 4350 | // 列ヘッダーの表示・非表示 |
4280 | 4351 | setRowHeaderVisible(env.getRowHeaderVisible()); |
4281 | - jTextPane_detail.setRows(bounds.getDetailRows()); | |
4352 | + | |
4353 | + initDetailHeight(); | |
4282 | 4354 | |
4283 | 4355 | // マーク表示分離の有無 |
4284 | 4356 | setMarkColumnVisible(env.getSplitMarkAndTitle()); |
@@ -24,6 +24,8 @@ import java.awt.event.MouseWheelListener; | ||
24 | 24 | import java.awt.font.TextAttribute; |
25 | 25 | import java.awt.geom.Rectangle2D; |
26 | 26 | import java.awt.image.BufferedImage; |
27 | +import java.beans.PropertyChangeEvent; | |
28 | +import java.beans.PropertyChangeListener; | |
27 | 29 | import java.io.File; |
28 | 30 | import java.text.AttributedCharacterIterator; |
29 | 31 | import java.text.AttributedString; |
@@ -212,6 +214,7 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
212 | 214 | |
213 | 215 | // コンポーネント |
214 | 216 | |
217 | + private JSplitPane jSplitPane_main = null; | |
215 | 218 | private JDetailPanel jTextPane_detail = null; |
216 | 219 | private JSplitPane jSplitPane_view = null; |
217 | 220 | private JPanel jPanel_tree = null; |
@@ -275,6 +278,7 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
275 | 278 | private float paperHeightZoom = 1.0F; |
276 | 279 | |
277 | 280 | private boolean byCenterMode = false; // 1放送局の1週間分を表示するモード化か |
281 | + private String startDate = CommonUtils.getDate529(0, true); // 放送局別の場合の開始日 | |
278 | 282 | |
279 | 283 | /* |
280 | 284 | * ページャーのEnable/Disableを更新する |
@@ -287,7 +291,7 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
287 | 291 | * Envの内容を反映する |
288 | 292 | */ |
289 | 293 | public void reflectEnv(){ |
290 | - jTextPane_detail.setRows(bounds.getDetailRows()); | |
294 | + initDetailHeight(); | |
291 | 295 | } |
292 | 296 | |
293 | 297 | /** |
@@ -428,8 +432,7 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
428 | 432 | super(); |
429 | 433 | |
430 | 434 | this.setLayout(new BorderLayout()); |
431 | - this.add(getJTextPane_detail(), BorderLayout.PAGE_START); | |
432 | - this.add(getJSplitPane_view(), BorderLayout.CENTER); | |
435 | + this.add(getJSplitPane_main(), BorderLayout.CENTER); | |
433 | 436 | |
434 | 437 | // タブが開いたり閉じたりしたときの処理 |
435 | 438 | this.addComponentListener(cl_shownhidden); |
@@ -1076,6 +1079,9 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
1076 | 1079 | */ |
1077 | 1080 | public void setDetailVisible(boolean aFlag) { |
1078 | 1081 | jTextPane_detail.setVisible(aFlag); |
1082 | + | |
1083 | + if (aFlag) | |
1084 | + jSplitPane_main.setDividerLocation(bounds.getPaperDetailHeight()); | |
1079 | 1085 | } |
1080 | 1086 | |
1081 | 1087 | /** |
@@ -1736,8 +1742,32 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
1736 | 1742 | clearPanel(); |
1737 | 1743 | selectMainView(null); |
1738 | 1744 | |
1739 | - jPanel_space_top_view.setLayout(null); | |
1745 | + TreePath path = jTree_tree.getSelectionPath(); | |
1746 | + if (path == null || path.getPathCount() != 3) | |
1747 | + return; | |
1748 | + | |
1749 | + String today = CommonUtils.getDate529(0, true); | |
1750 | + // 開始日が当日以降であれば現在の表を作成する | |
1751 | + if (startDate.compareTo(today) >= 0){ | |
1752 | + startDate = today; | |
1753 | + redrawByCenterCurrent(center); | |
1754 | + } | |
1755 | + // 開始日が過去日であれば過去ログから表作成する | |
1756 | + else{ | |
1757 | + redrawByCenterPassed(center); | |
1758 | + } | |
1759 | + | |
1760 | + // 番組枠描画バッファサイズの上限を確認する | |
1761 | + if (framebuffersize < frameUsed.size()) { | |
1762 | + framebuffersize = frameUsed.size(); | |
1763 | + StdAppendMessage(MSGID+"番組枠描画バッファの上限を変更: "+frameUsed.size()+"/"+framebuffersize); | |
1764 | + } | |
1765 | + } | |
1740 | 1766 | |
1767 | + /* | |
1768 | + * 放送局別に現在の表を作成する | |
1769 | + */ | |
1770 | + private void redrawByCenterCurrent(String center){ | |
1741 | 1771 | for (int a=0; a<tvprograms.size(); a++) { |
1742 | 1772 | // |
1743 | 1773 | TVProgram tvp = tvprograms.get(a); |
@@ -1803,13 +1833,56 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
1803 | 1833 | // 時間線をひく |
1804 | 1834 | redrawTimeline(false, false); |
1805 | 1835 | |
1806 | - // 番組枠描画バッファサイズの上限を確認する | |
1807 | - if (framebuffersize < frameUsed.size()) { | |
1808 | - framebuffersize = frameUsed.size(); | |
1809 | - StdAppendMessage(MSGID+"番組枠描画バッファの上限を変更: "+frameUsed.size()+"/"+framebuffersize); | |
1810 | - } | |
1811 | 1836 | } |
1812 | 1837 | |
1838 | + /* | |
1839 | + * 放送局別に過去ログから表を作成する | |
1840 | + */ | |
1841 | + private void redrawByCenterPassed(String center){ | |
1842 | + // 過去ログの取得 | |
1843 | + PassedProgram tvp = tvprograms.getPassed(); | |
1844 | + | |
1845 | + // 開始日以降で指定日数分の番組情報を取得する | |
1846 | + ProgList pl = tvp.loadByCenterDates(startDate, env.getDatePerPassedPage(), center); | |
1847 | + if (pl == null) | |
1848 | + return; | |
1849 | + | |
1850 | + // 日付ヘッダを描画する | |
1851 | + for (int centerid=0; centerid<pl.pdate.size(); centerid++) { | |
1852 | + ProgDateList pcl = pl.pdate.get(centerid); | |
1853 | + | |
1854 | + JTXTLabel b1 = new JTXTLabel(); | |
1855 | + GregorianCalendar c = CommonUtils.getCalendar(pcl.Date); | |
1856 | + if ( c != null ) { | |
1857 | + String date = CommonUtils.getDate(c); | |
1858 | + b1.setValue(date); | |
1859 | + b1.setText(date.substring(5)); | |
1860 | + b1.setOpaque(true); | |
1861 | + if ( c.get(Calendar.DAY_OF_WEEK) == Calendar.SATURDAY ) { | |
1862 | + b1.setBackground(new Color(90,90,255)); | |
1863 | + } | |
1864 | + else if ( c.get(Calendar.DAY_OF_WEEK) == Calendar.SUNDAY ) { | |
1865 | + b1.setBackground(new Color(255,90,90)); | |
1866 | + } | |
1867 | + else { | |
1868 | + b1.setBackground(new Color(180,180,180)); | |
1869 | + } | |
1870 | + } | |
1871 | + b1.setBorder(lborder); | |
1872 | + b1.setHorizontalAlignment(JLabel.CENTER); | |
1873 | + b1.setBounds(bounds.getBangumiColumnWidth()*centerid, 0, bounds.getBangumiColumnWidth(), bounds.getBangumiColumnHeight()); | |
1874 | + b1.addMouseListener(tbMouseAdapter); | |
1875 | + jPanel_space_top_view.add(b1); | |
1876 | + } | |
1877 | + | |
1878 | + jPanel_space_top_view.setPreferredSize(new Dimension(bounds.getBangumiColumnWidth()*pl.pdate.size(),bounds.getBangumiColumnHeight())); | |
1879 | + jPanel_space_top_view.updateUI(); | |
1880 | + | |
1881 | + putBangumiColumns(pl, -1, null); | |
1882 | + | |
1883 | + jLayeredPane_space_main_view.setPreferredSize(new Dimension(pl.pdate.size()*bounds.getBangumiColumnWidth(),Math.round(24*60*bounds.getPaperHeightMultiplier()*paperHeightZoom))); | |
1884 | + //jScrollPane_space_main.updateUI(); | |
1885 | + } | |
1813 | 1886 | |
1814 | 1887 | /** |
1815 | 1888 | * 予約待機赤枠の描画(個々の枠) |
@@ -2335,6 +2408,114 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
2335 | 2408 | } |
2336 | 2409 | } |
2337 | 2410 | |
2411 | + /* | |
2412 | + * 詳細欄関係 | |
2413 | + */ | |
2414 | + /* | |
2415 | + * 詳細欄の高さを初期化する | |
2416 | + */ | |
2417 | + private void initDetailHeight(){ | |
2418 | + if (bounds.getDetailRows() > 0){ | |
2419 | + resetDetailHeight(); | |
2420 | + } | |
2421 | + else{ | |
2422 | + int dh = bounds.getPaperDetailHeight(); | |
2423 | + if (dh > 1) | |
2424 | + setDetailHeight(dh); | |
2425 | + else | |
2426 | + resetDetailHeight(); | |
2427 | + } | |
2428 | + } | |
2429 | + | |
2430 | + /* | |
2431 | + * 詳細欄の高さを設定する | |
2432 | + */ | |
2433 | + private void setDetailHeight(int height){ | |
2434 | + if (jTextPane_detail == null) | |
2435 | + return; | |
2436 | + | |
2437 | + jSplitPane_main.setDividerLocation(height); | |
2438 | + bounds.setPaperDetailHeight(height); | |
2439 | + } | |
2440 | + | |
2441 | + /* | |
2442 | + * 詳細欄の高さをリセットする | |
2443 | + */ | |
2444 | + private void resetDetailHeight(){ | |
2445 | + if (jTextPane_detail == null) | |
2446 | + return; | |
2447 | + | |
2448 | + int rows = bounds.getDetailRows(); | |
2449 | + int height = jTextPane_detail.getHeightFromRows(rows > 0 ? rows : 4); | |
2450 | + | |
2451 | + setDetailHeight(height); | |
2452 | + } | |
2453 | + | |
2454 | + /* | |
2455 | + * 放送局別で前のページに移動する | |
2456 | + */ | |
2457 | + public void moveToPrevDatePage(){ | |
2458 | + PassedProgram passed = tvprograms.getPassed(); | |
2459 | + | |
2460 | + String date = passed.getPrevDate(startDate, env.getDatePerPassedPage()); | |
2461 | + if (date == null) | |
2462 | + return; | |
2463 | + | |
2464 | + startDate = date; | |
2465 | + | |
2466 | + // 表を描画し直す | |
2467 | + redrawByCurrentSelection(); | |
2468 | + } | |
2469 | + | |
2470 | + /* | |
2471 | + * 放送局別で前のページに移動可能かを返す | |
2472 | + */ | |
2473 | + public boolean isPrevDatePageEnabled(){ | |
2474 | + PassedProgram passed = tvprograms.getPassed(); | |
2475 | + | |
2476 | + String date = passed.getPrevDate(startDate, env.getDatePerPassedPage()); | |
2477 | + | |
2478 | + return date != null; | |
2479 | + } | |
2480 | + | |
2481 | + /* | |
2482 | + * 放送局別で次のページに移動する | |
2483 | + */ | |
2484 | + public void moveToNextDatePage(){ | |
2485 | + if (!isNextDatePageEnabled()) | |
2486 | + return; | |
2487 | + | |
2488 | + PassedProgram passed = tvprograms.getPassed(); | |
2489 | + | |
2490 | + String date = passed.getNextDate(startDate, env.getDatePerPassedPage()); | |
2491 | + if (date == null) | |
2492 | + date = CommonUtils.getDate529(0, true); | |
2493 | + | |
2494 | + startDate = date; | |
2495 | + | |
2496 | + // 表を描画し直す | |
2497 | + redrawByCurrentSelection(); | |
2498 | + } | |
2499 | + | |
2500 | + /* | |
2501 | + * 放送局別で次のページに移動可能かを返す | |
2502 | + */ | |
2503 | + public boolean isNextDatePageEnabled(){ | |
2504 | + String today = CommonUtils.getDate529(0, true); | |
2505 | + | |
2506 | + return startDate.compareTo(today) < 0; | |
2507 | + } | |
2508 | + | |
2509 | + /* | |
2510 | + * 放送局別の表示モードかを返す | |
2511 | + */ | |
2512 | + public boolean isByCenterMode(){ | |
2513 | + TreePath path = jTree_tree.getSelectionPath(); | |
2514 | + if (path == null || path.getPathCount() < 2) | |
2515 | + return false; | |
2516 | + | |
2517 | + return path.getPathComponent(1) == centerNode; | |
2518 | + } | |
2338 | 2519 | |
2339 | 2520 | /******************************************************************************* |
2340 | 2521 | * ハンドラ―メソッド |
@@ -2837,10 +3018,15 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
2837 | 3018 | public void mouseClicked(MouseEvent e) { |
2838 | 3019 | if (e.getButton() == MouseEvent.BUTTON1) { |
2839 | 3020 | if (e.getClickCount() == 2) { |
2840 | - if ( cur_tuner == IterationType.PASSED ) { | |
2841 | - MWin.appendMessage(MSGID+"過去ログでは一局表示に切り替えられません"); | |
3021 | + TreePath path = jTree_tree.getSelectionPath(); | |
3022 | + if (path == null || path.getPathCount() != 3) | |
2842 | 3023 | return; |
2843 | - } | |
3024 | + | |
3025 | + // 過去ログノードの場合、選択されているノードを開始日とする | |
3026 | + if (path.getPathComponent(1) == passedNode) | |
3027 | + startDate = path.getPathComponent(2).toString(); | |
3028 | + else | |
3029 | + startDate = CommonUtils.getDate529(0, true); | |
2844 | 3030 | |
2845 | 3031 | // 右ダブルクリックで局表示に切り替え |
2846 | 3032 | String center = ((JLabel)e.getSource()).getText(); |
@@ -2874,8 +3060,20 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
2874 | 3060 | // 右ダブルクリックで日付表示に切り替え |
2875 | 3061 | String date = ((JTXTLabel)e.getSource()).getValue(); |
2876 | 3062 | StdAppendMessage(MSGID+"日付表示に切り替え:"+date); |
2877 | - //redrawByDate(date, -1); | |
2878 | - jLabel_tree.setView(JTreeLabel.Nodes.DATE, date); | |
3063 | + | |
3064 | + String today = CommonUtils.getDate529(0, true); | |
3065 | + | |
3066 | + // 過去日の場合、過去ログの日付を選択する | |
3067 | + if (date.compareTo(today) < 0){ | |
3068 | + // 指定した日付のノードがツリーになければ作成する | |
3069 | + addPassedNodeIfNotExist(date); | |
3070 | + | |
3071 | + jLabel_tree.setView(JTreeLabel.Nodes.PASSED, date); | |
3072 | + } | |
3073 | + // 未来日の場合、日付別の日付を選択する | |
3074 | + else | |
3075 | + jLabel_tree.setView(JTreeLabel.Nodes.DATE, date); | |
3076 | + | |
2879 | 3077 | reselectTree(); |
2880 | 3078 | } |
2881 | 3079 | } |
@@ -2891,18 +3089,34 @@ public abstract class AbsPaperView extends JPanel implements TickTimerListener,H | ||
2891 | 3089 | private JDetailPanel getJTextPane_detail() { |
2892 | 3090 | if (jTextPane_detail == null) { |
2893 | 3091 | jTextPane_detail = new JDetailPanel(); |
2894 | - jTextPane_detail.setRows(bounds.getDetailRows()); | |
2895 | 3092 | jTextPane_detail.setBorder(detailInfoFreeBorder); |
2896 | 3093 | jTextPane_detail.addMouseListener(ml_detailInfoClick); |
2897 | - //Dimension d = jTextPane_detail.getMaximumSize(); | |
2898 | - //d.height = bounds.getDetailAreaHeight(); | |
2899 | - //jTextPane_detail.setPreferredSize(d); | |
2900 | - //jTextPane_detail.setVerticalAlignment(JLabel.TOP); | |
2901 | - //jTextPane_detail.setHorizontalAlignment(JLabel.LEFT); | |
2902 | 3094 | } |
2903 | 3095 | return jTextPane_detail; |
2904 | 3096 | } |
2905 | 3097 | |
3098 | + private JSplitPane getJSplitPane_main() { | |
3099 | + if ( jSplitPane_main == null ) { | |
3100 | + | |
3101 | + jSplitPane_main = new JSplitPane(JSplitPane.VERTICAL_SPLIT); | |
3102 | + | |
3103 | + jSplitPane_main.setTopComponent(getJTextPane_detail()); | |
3104 | + jSplitPane_main.setBottomComponent(getJSplitPane_view()); | |
3105 | + | |
3106 | + initDetailHeight(); | |
3107 | + | |
3108 | + jSplitPane_main.addPropertyChangeListener(JSplitPane.DIVIDER_LOCATION_PROPERTY, new PropertyChangeListener() { | |
3109 | + @Override | |
3110 | + public void propertyChange(PropertyChangeEvent pce) { | |
3111 | + if (jTextPane_detail.isVisible()) | |
3112 | + bounds.setPaperDetailHeight(jSplitPane_main.getDividerLocation()); | |
3113 | + } | |
3114 | + }); | |
3115 | + } | |
3116 | + | |
3117 | + return jSplitPane_main; | |
3118 | + } | |
3119 | + | |
2906 | 3120 | private JSplitPane getJSplitPane_view() { |
2907 | 3121 | if ( jSplitPane_view == null ) { |
2908 | 3122 |
@@ -217,6 +217,7 @@ public abstract class AbsSettingView extends JScrollPane { | ||
217 | 217 | private JSliderPanel jSP_tooltipDismissDelay = null; |
218 | 218 | private JCheckBoxPanel jCBP_timerbarScrollEnable = null; |
219 | 219 | private JSliderPanel jSP_passedLogLimit = null; |
220 | + private JSliderPanel jSP_datePerPage = null; | |
220 | 221 | private JCheckBoxPanel jCBP_effectComboToPaper = null; |
221 | 222 | private JComboBoxPanel jCBX_snapshotFmt = null; |
222 | 223 | private JCheckBoxPanel jCBP_printSnapshot = null; |
@@ -674,6 +675,11 @@ public abstract class AbsSettingView extends JScrollPane { | ||
674 | 675 | // RELOADリスナー不要 |
675 | 676 | y+=(PARTS_HEIGHT+SEP_HEIGHT); |
676 | 677 | |
678 | + CommonSwingUtils.putComponentOn(jPanel_setting, jSP_datePerPage = new JSliderPanel("過去ログのページ当たりの日数",LABEL_WIDTH,7,28,200), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); | |
679 | + jSP_datePerPage.setValue(env.getDatePerPassedPage()); | |
680 | + // RELOADリスナー不要 | |
681 | + y+=(PARTS_HEIGHT+SEP_HEIGHT); | |
682 | + | |
677 | 683 | CommonSwingUtils.putComponentOn(jPanel_setting, jCBP_effectComboToPaper = new JCheckBoxPanel("レコーダコンボボックスを新聞形式でも有効に",LABEL_WIDTH), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); |
678 | 684 | jCBP_effectComboToPaper.setSelected(env.getEffectComboToPaper()); |
679 | 685 | // RELOADリスナー不要 |
@@ -1158,11 +1164,11 @@ public abstract class AbsSettingView extends JScrollPane { | ||
1158 | 1164 | // RELOADリスナー不要 |
1159 | 1165 | y+=(PARTS_HEIGHT+SEP_HEIGHT); |
1160 | 1166 | |
1161 | - CommonSwingUtils.putComponentOn(jPanel_setting, jSP_detailRows = new JSliderPanel("詳細情報欄の行数",LABEL_WIDTH,0,10,200), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); | |
1167 | + CommonSwingUtils.putComponentOn(jPanel_setting, jSP_detailRows = new JSliderPanel("詳細情報欄の行数(0:前回終了時の高さ)",LABEL_WIDTH,0,10,200), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); | |
1162 | 1168 | jSP_detailRows.setValue(bounds.getDetailRows()); |
1163 | 1169 | y+=(PARTS_HEIGHT+SEP_HEIGHT); |
1164 | 1170 | |
1165 | - CommonSwingUtils.putComponentOn(jPanel_setting, jSP_statusRows = new JSliderPanel("ステータス欄の行数",LABEL_WIDTH,0,10,200), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); | |
1171 | + CommonSwingUtils.putComponentOn(jPanel_setting, jSP_statusRows = new JSliderPanel("ステータス欄の行数(0:前回終了時の高さ)",LABEL_WIDTH,0,10,200), PARTS_WIDTH, PARTS_HEIGHT, SEP_WIDTH, y); | |
1166 | 1172 | jSP_statusRows.setValue(bounds.getStatusRows()); |
1167 | 1173 | y+=(PARTS_HEIGHT+SEP_HEIGHT); |
1168 | 1174 |
@@ -1364,6 +1370,7 @@ public abstract class AbsSettingView extends JScrollPane { | ||
1364 | 1370 | env.setTooltipDismissDelay(jSP_tooltipDismissDelay.getValue()); |
1365 | 1371 | env.setTimerbarScrollEnable(jCBP_timerbarScrollEnable.isSelected()); |
1366 | 1372 | env.setPassedLogLimit(jSP_passedLogLimit.getValue()); |
1373 | + env.setDatePerPassedPage(jSP_datePerPage.getValue()); | |
1367 | 1374 | env.setEffectComboToPaper(jCBP_effectComboToPaper.isSelected()); |
1368 | 1375 | env.setSnapshotFmt((SnapshotFmt) jCBX_snapshotFmt.getSelectedItem()); |
1369 | 1376 | env.setPrintSnapshot(jCBP_printSnapshot.isSelected()); |
@@ -1419,6 +1419,8 @@ public abstract class AbsTitleListView extends JPanel { | ||
1419 | 1419 | if (ttlIds != null) |
1420 | 1420 | pop.add(getMultiTitleDetailMenuItem(title, chnam, devId, ttlIds, recId)); |
1421 | 1421 | |
1422 | + appendSelectFolderMenuItem(pop, ttlId); | |
1423 | + | |
1422 | 1424 | pop.addSeparator(); |
1423 | 1425 | pop.add(getStartStopPlayTitleMenuItem(true, title, chnam, devId, ttlId, recId)); |
1424 | 1426 | pop.add(getStartStopPlayTitleMenuItem(false, title, chnam, devId, ttlId, recId)); |
@@ -1939,4 +1941,50 @@ public abstract class AbsTitleListView extends JPanel { | ||
1939 | 1941 | } |
1940 | 1942 | return(""); |
1941 | 1943 | } |
1944 | + | |
1945 | + /** | |
1946 | + * フォルダー絞り込みのメニューアイテムを追加する | |
1947 | + */ | |
1948 | + protected void appendSelectFolderMenuItem(final JPopupMenu pop, final String ttlId){ | |
1949 | + HDDRecorder rec = getSelectedRecorder(); | |
1950 | + TitleInfo ttl = rec.getTitleInfo(ttlId); | |
1951 | + | |
1952 | + if (ttl == null) | |
1953 | + return; | |
1954 | + | |
1955 | + ArrayList<TextValueSet> folders = ttl.getRec_folder(); | |
1956 | + if (folders == null || folders.isEmpty()) | |
1957 | + return; | |
1958 | + | |
1959 | + String deviceId = ttl.getRec_device(); | |
1960 | + String folderName = folders.get(0).getText(); | |
1961 | + | |
1962 | + pop.addSeparator(); | |
1963 | + | |
1964 | + int idx = jCBXPanel_folder.getSelectedIndex(); | |
1965 | + if (idx == 0){ | |
1966 | + JMenuItem menuItem = new JMenuItem("フォルダを選択する【"+folderName+"】"); | |
1967 | + menuItem.addActionListener(new ActionListener() { | |
1968 | + public void actionPerformed(ActionEvent e) { | |
1969 | + updateFolderList(folderName); | |
1970 | + updateFolderButtons(); | |
1971 | + updateTitleList(false, false, false, false, false, false); | |
1972 | + } | |
1973 | + }); | |
1974 | + | |
1975 | + pop.add(menuItem); | |
1976 | + } | |
1977 | + else{ | |
1978 | + JMenuItem menuItem = new JMenuItem("フォルダの選択を解除する"); | |
1979 | + menuItem.addActionListener(new ActionListener() { | |
1980 | + public void actionPerformed(ActionEvent e) { | |
1981 | + jCBXPanel_folder.setSelectedIndex(0); | |
1982 | + updateTitleList(false, false, false, false, false, false); | |
1983 | + } | |
1984 | + }); | |
1985 | + | |
1986 | + pop.add(menuItem); | |
1987 | + } | |
1988 | + } | |
1989 | + | |
1942 | 1990 | } |
@@ -82,6 +82,16 @@ public abstract class AbsToolBar extends JToolBar implements HDDRecorderSelectab | ||
82 | 82 | |
83 | 83 | protected abstract ToolBarIconInfoList getTbIconEnv(); |
84 | 84 | |
85 | + // 前のページに移動する | |
86 | + protected abstract void moveToPrevPage(); | |
87 | + // 前のページに移動可能かを返す | |
88 | + protected abstract boolean isPrevPageEnabled(); | |
89 | + | |
90 | + // 次のページに移動する | |
91 | + protected abstract void moveToNextPage(); | |
92 | + // 次のページに移動可能かを返す | |
93 | + protected abstract boolean isNextPageEnabled(); | |
94 | + | |
85 | 95 | // 親に依頼 |
86 | 96 | |
87 | 97 | // リスト形式 |
@@ -813,9 +823,9 @@ public abstract class AbsToolBar extends JToolBar implements HDDRecorderSelectab | ||
813 | 823 | } |
814 | 824 | |
815 | 825 | /* |
816 | - * 前のページへ | |
826 | + * 前の放送局ページに移動する | |
817 | 827 | */ |
818 | - public void moveToPrevPage(){ | |
828 | + public void moveToPrevCenterPage(){ | |
819 | 829 | int pno = getSelectedPagerIndex(); |
820 | 830 | if (pno <= 0) |
821 | 831 | return; |
@@ -824,7 +834,10 @@ public abstract class AbsToolBar extends JToolBar implements HDDRecorderSelectab | ||
824 | 834 | redrawByPager(); |
825 | 835 | } |
826 | 836 | |
827 | - public boolean isPrevPageEnabled(){ | |
837 | + /* | |
838 | + * 前の放送局ページに移動可能かを返す | |
839 | + */ | |
840 | + public boolean isPrevCenterPageEnabled(){ | |
828 | 841 | if (jComboBox_pager == null || jButton_prevpage == null) |
829 | 842 | return false; |
830 | 843 | if (!jComboBox_pager.isEnabled() || !isTabSelected(MWinTab.PAPER) || !env.isPagerEnabled()) |
@@ -835,9 +848,9 @@ public abstract class AbsToolBar extends JToolBar implements HDDRecorderSelectab | ||
835 | 848 | } |
836 | 849 | |
837 | 850 | /* |
838 | - * 次のページへ | |
851 | + * 次の放送局ページに移動する | |
839 | 852 | */ |
840 | - public void moveToNextPage(){ | |
853 | + public void moveToNextCenterPage(){ | |
841 | 854 | int pno = getSelectedPagerIndex(); |
842 | 855 | int pnum = getPagerCount(); |
843 | 856 | if (pno >= pnum-1) |
@@ -847,7 +860,10 @@ public abstract class AbsToolBar extends JToolBar implements HDDRecorderSelectab | ||
847 | 860 | redrawByPager(); |
848 | 861 | } |
849 | 862 | |
850 | - public boolean isNextPageEnabled(){ | |
863 | + /* | |
864 | + * 次の放送局ページに移動可能かを返す | |
865 | + */ | |
866 | + public boolean isNextCenterPageEnabled(){ | |
851 | 867 | if (jComboBox_pager == null || jButton_prevpage == null) |
852 | 868 | return false; |
853 | 869 | if (!jComboBox_pager.isEnabled() || !isTabSelected(MWinTab.PAPER) || !env.isPagerEnabled()) |
@@ -225,6 +225,21 @@ public class Bounds { | ||
225 | 225 | public int getSearchBoxAreaWidth(){ return searchBoxAreaWidth; } |
226 | 226 | public void setSearchBoxAreaWidth(int n){ searchBoxAreaWidth = n; } |
227 | 227 | |
228 | + // リスト形式の詳細欄の高さ | |
229 | + private int listedDetailHeight; | |
230 | + public int getListedDetailHeight(){ return listedDetailHeight; } | |
231 | + public void setListedDetailHeight(int n){ listedDetailHeight = n; } | |
232 | + | |
233 | + // 新聞形式の詳細欄の高さ | |
234 | + private int paperDetailHeight; | |
235 | + public int getPaperDetailHeight(){ return paperDetailHeight; } | |
236 | + public void setPaperDetailHeight(int n){ paperDetailHeight = n; } | |
237 | + | |
238 | + // ステータスウインドウの高さ | |
239 | + private int statusWindowHeight; | |
240 | + public int getStatusWindowHeight(){ return statusWindowHeight; } | |
241 | + public void setStatusWindowHeight(int n){ statusWindowHeight = n; } | |
242 | + | |
228 | 243 | // |
229 | 244 | private static boolean loaded; |
230 | 245 | public boolean isLoaded() { return loaded; } |
@@ -1112,6 +1112,17 @@ public class CommonUtils { | ||
1112 | 1112 | } |
1113 | 1113 | |
1114 | 1114 | /******************************************************************************* |
1115 | + * ウインドウ関連 | |
1116 | + ******************************************************************************/ | |
1117 | + /* | |
1118 | + * ポイント数からピクセル数を計算する | |
1119 | + */ | |
1120 | + public static int getPixelFromPoint(int point){ | |
1121 | + int pixelPerInch=java.awt.Toolkit.getDefaultToolkit().getScreenResolution(); | |
1122 | + return (int)((double)point/72.0*(double)pixelPerInch); | |
1123 | + } | |
1124 | + | |
1125 | + /******************************************************************************* | |
1115 | 1126 | * オブジェクト操作関連 |
1116 | 1127 | ******************************************************************************/ |
1117 | 1128 |
@@ -365,6 +365,12 @@ public class Env { | ||
365 | 365 | public int getCenterPerPage() { return centerPerPage; } |
366 | 366 | public void setCenterPerPage(int c) { centerPerPage = c; } |
367 | 367 | public boolean isPagerEnabled() { return ( ! drawcacheEnable) && (centerPerPage > 0); } |
368 | + | |
369 | + // 新聞形式での、過去日の放送局別表示の1ページあたりの日数 | |
370 | + public int getDatePerPassedPage(){ return datePerPassedPage; } | |
371 | + public void setDatePerPassedPage(int n) { datePerPassedPage = n; } | |
372 | + private int datePerPassedPage = 14; | |
373 | + | |
368 | 374 | /** |
369 | 375 | * indexなので、0から始まる |
370 | 376 | */ |
@@ -16,38 +16,43 @@ public class JDetailPanel extends JPanel { | ||
16 | 16 | private static final long serialVersionUID = 1L; |
17 | 17 | |
18 | 18 | JScrollPane jscrollpane = null; |
19 | + private JPanel jpanel_title = null; | |
19 | 20 | private JTextAreaWithPopup jta = null; |
20 | 21 | private JLabel jlabel_time = null; |
21 | 22 | private JLabel jlabel_title = null; |
22 | - | |
23 | + | |
23 | 24 | private final int titleFontSize = 20; |
24 | 25 | //private int textAreaRows = 4; |
25 | - | |
26 | + | |
26 | 27 | public JDetailPanel() { |
27 | - | |
28 | + | |
28 | 29 | this.setLayout(new BorderLayout()); |
29 | - | |
30 | + | |
31 | + jpanel_title = new JPanel(); | |
32 | + jpanel_title.setLayout(new BorderLayout()); | |
33 | + this.add(jpanel_title, BorderLayout.PAGE_START); | |
34 | + | |
30 | 35 | Font f = null; |
31 | - | |
36 | + | |
32 | 37 | jlabel_time = new JLabel(); |
33 | 38 | f = jlabel_time.getFont(); |
34 | 39 | jlabel_time.setFont(f.deriveFont(f.getStyle() | Font.BOLD, titleFontSize)); |
35 | - this.add(jlabel_time,BorderLayout.LINE_START); | |
36 | - | |
40 | + jpanel_title.add(jlabel_time,BorderLayout.LINE_START); | |
41 | + | |
37 | 42 | jlabel_title = new JLabel(); |
38 | 43 | f = jlabel_title.getFont(); |
39 | 44 | jlabel_title.setFont(f.deriveFont(f.getStyle() | Font.BOLD, titleFontSize)); |
40 | 45 | jlabel_title.setForeground(Color.BLUE); |
41 | - this.add(jlabel_title,BorderLayout.CENTER); | |
46 | + jpanel_title.add(jlabel_title,BorderLayout.CENTER); | |
42 | 47 | jlabel_title.setText(" "); |
43 | - | |
48 | + | |
44 | 49 | jta = CommonSwingUtils.getJta(this,4,0); |
45 | - | |
50 | + | |
46 | 51 | jscrollpane = new JScrollPane(jta,JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,JScrollPane.HORIZONTAL_SCROLLBAR_NEVER); |
47 | 52 | jscrollpane.setBorder(new EmptyBorder(0,0,0,0)); |
48 | - this.add(jscrollpane,BorderLayout.PAGE_END); | |
53 | + this.add(jscrollpane,BorderLayout.CENTER); | |
49 | 54 | } |
50 | - | |
55 | + | |
51 | 56 | public void setLabel(String s, String e, String t) { |
52 | 57 | if (s == null || s.length() == 0 || e == null || e.length() == 0) { |
53 | 58 | jlabel_time.setText(" "); |
@@ -73,9 +78,18 @@ public class JDetailPanel extends JPanel { | ||
73 | 78 | public int getRows() { |
74 | 79 | return jta.getRows(); |
75 | 80 | } |
76 | - | |
81 | + | |
77 | 82 | public void setRows(int rows) { |
78 | - jta.setRows(rows); | |
83 | +// jta.setRows(rows); | |
84 | + } | |
85 | + | |
86 | + /* | |
87 | + * 行数を指定して高さを取得する | |
88 | + */ | |
89 | + public int getHeightFromRows(int rows){ | |
90 | + int hl = jta.getFont().getSize(); | |
91 | + | |
92 | + return CommonUtils.getPixelFromPoint(hl*rows+titleFontSize); | |
79 | 93 | } |
80 | 94 | |
81 | 95 | @Override |
@@ -84,7 +98,7 @@ public class JDetailPanel extends JPanel { | ||
84 | 98 | jlabel_title.addMouseListener(l); |
85 | 99 | jta.addMouseListener(l); |
86 | 100 | } |
87 | - | |
101 | + | |
88 | 102 | @Override |
89 | 103 | public void removeMouseListener(MouseListener l) { |
90 | 104 | jlabel_time.removeMouseListener(l); |
@@ -12,7 +12,7 @@ public class MarkChar { | ||
12 | 12 | /******************************************************************************* |
13 | 13 | * 定数 |
14 | 14 | ******************************************************************************/ |
15 | - | |
15 | + | |
16 | 16 | public static enum MarkItem { |
17 | 17 | EXTENTION ( "★延長注意★" ), |
18 | 18 | EXTENTION_S ( "(延)" ), |
@@ -36,48 +36,51 @@ public class MarkChar { | ||
36 | 36 | MULTIVOICE ( "[多]" ), |
37 | 37 | STANDIN ( "[吹]" ), |
38 | 38 | DATA ( "[デ]" ), |
39 | - SORRUND ( "[5.1]" ), | |
39 | + SURROUND ( "[5.1]" ), | |
40 | 40 | PRECEDING ( "【先】" ), |
41 | - | |
41 | + | |
42 | 42 | REPEATED ( "[再]" ), |
43 | + | |
44 | + BS4K ( "[4K]"), | |
45 | + BS8K ( "[8K]"), | |
43 | 46 | ; |
44 | - | |
47 | + | |
45 | 48 | private String name; |
46 | - | |
49 | + | |
47 | 50 | private MarkItem(String name) { |
48 | 51 | this.name = name; |
49 | 52 | } |
50 | - | |
53 | + | |
51 | 54 | public String getName() { |
52 | 55 | return name; |
53 | 56 | } |
54 | 57 | } |
55 | - | |
58 | + | |
56 | 59 | /******************************************************************************* |
57 | 60 | * 部品 |
58 | 61 | ******************************************************************************/ |
59 | - | |
62 | + | |
60 | 63 | private Env env; |
61 | - | |
64 | + | |
62 | 65 | /******************************************************************************* |
63 | 66 | * コンストラクタ |
64 | 67 | ******************************************************************************/ |
65 | - | |
68 | + | |
66 | 69 | public MarkChar(Env env) { |
67 | 70 | this.env = env; |
68 | 71 | } |
69 | - | |
72 | + | |
70 | 73 | /******************************************************************************* |
71 | 74 | * アクション |
72 | 75 | ******************************************************************************/ |
73 | - | |
76 | + | |
74 | 77 | /** |
75 | 78 | * 延長警告マークの取得 |
76 | 79 | */ |
77 | 80 | public String getExtensionMark(ProgDetailList tvd) { |
78 | 81 | return ((tvd.extension) ? ((env.getShortExtMark())?(MarkItem.EXTENTION_S.getName()):(MarkItem.EXTENTION.getName())) : ("")); |
79 | 82 | } |
80 | - | |
83 | + | |
81 | 84 | /** |
82 | 85 | * 新番組と最終回だけわける |
83 | 86 | */ |
@@ -90,19 +93,19 @@ public class MarkChar { | ||
90 | 93 | } |
91 | 94 | return ""; |
92 | 95 | } |
93 | - | |
96 | + | |
94 | 97 | /** |
95 | 98 | * 普通のマークの取得 |
96 | 99 | */ |
97 | 100 | public String getOptionMark(ProgDetailList tvd) { |
98 | - | |
101 | + | |
99 | 102 | String mkNewArr = ""; |
100 | 103 | String mkModified = ""; |
101 | 104 | String mkNoscr = ""; |
102 | 105 | String mkSpecial = ""; |
103 | 106 | String mkNoSyobo = ""; |
104 | 107 | String mkRating = ""; |
105 | - | |
108 | + | |
106 | 109 | String mkFirst = ""; |
107 | 110 | String mkLive = ""; |
108 | 111 | String mkSubtitle = ""; |
@@ -116,11 +119,13 @@ public class MarkChar { | ||
116 | 119 | String mkNonrepeated = ""; |
117 | 120 | String mkMoved = ""; |
118 | 121 | String mkPrec = ""; |
119 | - | |
122 | + String mk4k = ""; | |
123 | + String mk8k = ""; | |
124 | + | |
120 | 125 | if (tvd.noscrumble == ProgScrumble.NOSCRUMBLE && env.getOptMarks().get(ProgOption.HIDDEN_NOSCRUMBLE) == Boolean.TRUE) { |
121 | 126 | mkNoscr = MarkItem.NOSCRUMBLE.getName(); |
122 | 127 | } |
123 | - | |
128 | + | |
124 | 129 | if ( tvd.newarrival && env.getOptMarks().get(ProgOption.NEWARRIVAL) == Boolean.TRUE ) { |
125 | 130 | mkNewArr = ((env.getShortExtMark())?(MarkItem.NEWARRIVAL_S.getName()):(MarkItem.NEWARRIVAL.getName())); |
126 | 131 | } |
@@ -147,11 +152,11 @@ public class MarkChar { | ||
147 | 152 | // 初回放送 |
148 | 153 | mkFirst = MarkItem.FIRST.getName(); |
149 | 154 | break; |
150 | - | |
155 | + | |
151 | 156 | case NOSYOBO: |
152 | 157 | mkNoSyobo = MarkItem.NOSYOBO.getName(); |
153 | 158 | break; |
154 | - | |
159 | + | |
155 | 160 | case LIVE: |
156 | 161 | // 生放送 |
157 | 162 | mkLive = MarkItem.LIVE.getName(); |
@@ -182,7 +187,7 @@ public class MarkChar { | ||
182 | 187 | break; |
183 | 188 | case SURROUND: |
184 | 189 | // 5.1chサラウンド |
185 | - mkSurround = MarkItem.SORRUND.getName(); | |
190 | + mkSurround = MarkItem.SURROUND.getName(); | |
186 | 191 | break; |
187 | 192 | case MOVED: |
188 | 193 | // 先週無かったか時間が違う |
@@ -192,21 +197,28 @@ public class MarkChar { | ||
192 | 197 | // 先行放送 |
193 | 198 | mkPrec = MarkItem.PRECEDING.getName(); |
194 | 199 | break; |
200 | + case BS4K: | |
201 | + mk4k = MarkItem.BS4K.getName(); | |
202 | + break; | |
203 | + case BS8K: | |
204 | + mk8k = MarkItem.BS8K.getName(); | |
205 | + break; | |
195 | 206 | default: |
196 | 207 | break; |
197 | 208 | } |
198 | 209 | } |
199 | - | |
200 | - return(mkNewArr+mkNoSyobo+mkMoved+mkModified+mkFirst+mkNonrepeated+mkNoscr+mkSpecial+mkRating+mkPrec+mkLive+mkPv+mkSubtitle+mkBilingual+mkTextbc+mkMultivoice+mkStandin+mkData+mkSurround); | |
210 | + | |
211 | + return(mkNewArr+mkNoSyobo+mkMoved+mkModified+mkFirst+mkNonrepeated+mkNoscr+mkSpecial+mkRating+mkPrec+mkLive+ | |
212 | + mkPv+mkSubtitle+mkBilingual+mkTextbc+mkMultivoice+mkStandin+mkData+mkSurround+mk4k+mk8k); | |
201 | 213 | } |
202 | - | |
214 | + | |
203 | 215 | /** |
204 | 216 | * タイトルの後ろにつくマークの取得 |
205 | 217 | */ |
206 | 218 | public String getPostfixMark(ProgDetailList tvd) { |
207 | - | |
219 | + | |
208 | 220 | String mkRep = ""; |
209 | - | |
221 | + | |
210 | 222 | for ( ProgOption opt : tvd.getOption() ) { |
211 | 223 | switch (opt) { |
212 | 224 | case REPEAT: |
@@ -216,7 +228,7 @@ public class MarkChar { | ||
216 | 228 | break; |
217 | 229 | } |
218 | 230 | } |
219 | - | |
231 | + | |
220 | 232 | return(mkRep); |
221 | 233 | } |
222 | 234 |
@@ -128,6 +128,43 @@ public class PassedProgram extends TVProgramUtils implements TVProgram,Cloneable | ||
128 | 128 | final String expr_a = "^(\\d)_(\\d+)_(.+)\\."; |
129 | 129 | final String expr_z = "(xml|txt)$"; |
130 | 130 | |
131 | + /* | |
132 | + * 指定した放送局の期間分の番組情報を読み込む | |
133 | + */ | |
134 | + public ProgList loadByCenterDates(String startDate, int max, String center){ | |
135 | + ProgList pl = new ProgList(); | |
136 | + pl.Center = center; | |
137 | + pl.enabled = true; | |
138 | + | |
139 | + String today = CommonUtils.getDate529(0, true); | |
140 | + GregorianCalendar c = CommonUtils.getCalendar(startDate); | |
141 | + | |
142 | + // 日数分ループする | |
143 | + for (int n=0; n<max; n++){ | |
144 | + String date = CommonUtils.getDate(c); | |
145 | + // 当日以降になったらループを抜ける | |
146 | + if (date.compareTo(today) >= 0) | |
147 | + break; | |
148 | + | |
149 | + // 1日分をロードする | |
150 | + if (loadByCenter(date, center) && pcenter.size() > 0 && pcenter.get(0).pdate.size() > 0){ | |
151 | + // 成功したら追加する | |
152 | + pl.pdate.add(pcenter.get(0).pdate.get(0)); | |
153 | + } | |
154 | + else{ | |
155 | + // 失敗したら空の番組情報を追加する | |
156 | + ProgDateList pcl = new ProgDateList(); | |
157 | + pcl.Date = date; | |
158 | + pl.pdate.add(pcl); | |
159 | + } | |
160 | + | |
161 | + // 日付を1日ずらす | |
162 | + c.add(GregorianCalendar.DAY_OF_MONTH, 1); | |
163 | + } | |
164 | + | |
165 | + return pl; | |
166 | + } | |
167 | + | |
131 | 168 | /** |
132 | 169 | * 指定の日付の指定の放送局の過去ログを取得する |
133 | 170 | * @param date |
@@ -582,11 +619,13 @@ public class PassedProgram extends TVProgramUtils implements TVProgram,Cloneable | ||
582 | 619 | // @see #getDateList() |
583 | 620 | private static String pregetdate = "1999/12/31"; |
584 | 621 | private static String[] dd = new String[0]; |
622 | + private static final int maxCntDef = 720; // 放送局別過去日表示のための最大カウント | |
585 | 623 | |
586 | 624 | /** |
587 | 625 | * ディレクトリ一覧を取得する(日に一回しか検索しない) |
588 | 626 | */ |
589 | - public String[] getDateList(int maxCnt) { | |
627 | + public String[] getDateList(int maxCntArg) { | |
628 | + int maxCnt = maxCntDef > maxCntArg ? maxCntDef : maxCntArg; | |
590 | 629 | |
591 | 630 | String getdate = CommonUtils.getDate529(0,true); |
592 | 631 | if ( getdate.compareTo(pregetdate) <= 0 ) |
@@ -662,6 +701,49 @@ public class PassedProgram extends TVProgramUtils implements TVProgram,Cloneable | ||
662 | 701 | return dd; |
663 | 702 | } |
664 | 703 | |
704 | + /* | |
705 | + * 次の日付を取得する | |
706 | + */ | |
707 | + public String getNextDate(String dateArg, int count){ | |
708 | + int num = dd.length; | |
709 | + | |
710 | + for (int n=0; n<num; n++){ | |
711 | + String date = dd[num-1-n]; | |
712 | + | |
713 | + if (date.compareTo(dateArg) <= 0) | |
714 | + continue; | |
715 | + | |
716 | + count--; | |
717 | + if (count <= 0) | |
718 | + return date; | |
719 | + } | |
720 | + | |
721 | + return null; | |
722 | + } | |
723 | + | |
724 | + /* | |
725 | + * 前の日付を取得する | |
726 | + */ | |
727 | + public String getPrevDate(String dateArg, int count){ | |
728 | + int num = dd.length; | |
729 | + String dateLast = null; | |
730 | + | |
731 | + for (int n=0; n<num; n++){ | |
732 | + String date = dd[n]; | |
733 | + | |
734 | + if (date.compareTo(dateArg) >= 0) | |
735 | + continue; | |
736 | + | |
737 | + count--; | |
738 | + if (count <= 0) | |
739 | + return date; | |
740 | + | |
741 | + dateLast = date; | |
742 | + } | |
743 | + | |
744 | + // 指定したカウント前の日付がなければ最古の日付を返す | |
745 | + return dateLast; | |
746 | + } | |
665 | 747 | /* ここまで */ |
666 | 748 | |
667 | 749 |
@@ -19,7 +19,31 @@ public interface TVProgram { | ||
19 | 19 | /** |
20 | 20 | * NOSCRUMBLEは間違って(?)ProgScrumbleを使うこととなってしまったのだ。ここにあるのはマーク表示のための一覧用なのだ。 |
21 | 21 | */ |
22 | - public enum ProgOption { HIDDEN_NEW, HIDDEN_LAST, HIDDEN_NOSCRUMBLE, FIRST, REPEAT, LIVE, SPECIAL, NOSYOBO, SUBTITLE, BILINGUAL, STANDIN, PV, MULTIVOICE, DATA, SURROUND, NEWARRIVAL, MODIFIED, NONREPEATED, MOVED, PRECEDING, RATING }; | |
22 | + public enum ProgOption { | |
23 | + HIDDEN_NEW, | |
24 | + HIDDEN_LAST, | |
25 | + HIDDEN_NOSCRUMBLE, | |
26 | + FIRST, | |
27 | + REPEAT, | |
28 | + LIVE, | |
29 | + SPECIAL, | |
30 | + NOSYOBO, | |
31 | + SUBTITLE, | |
32 | + BILINGUAL, | |
33 | + STANDIN, | |
34 | + PV, | |
35 | + MULTIVOICE, | |
36 | + DATA, | |
37 | + SURROUND, | |
38 | + NEWARRIVAL, | |
39 | + MODIFIED, | |
40 | + NONREPEATED, | |
41 | + MOVED, | |
42 | + PRECEDING, | |
43 | + RATING, | |
44 | + BS4K, | |
45 | + BS8K | |
46 | + }; | |
23 | 47 | |
24 | 48 | public static enum ProgGenre { |
25 | 49 | NEWS ("ニュース/報道", "0"), |
@@ -289,6 +313,8 @@ public interface TVProgram { | ||
289 | 313 | { ProgOption.NEWARRIVAL, "[NEW]予約待機の新着" }, |
290 | 314 | { ProgOption.MODIFIED, "(更)番組詳細に更新あり - 予約待機分のみ" }, |
291 | 315 | { ProgOption.MOVED, "(移)先週無かったか時間が違う" }, |
316 | + { ProgOption.BS4K, "[4K]BS/CS 4K放送"}, | |
317 | + { ProgOption.BS8K, "[8K]BS 8K放送"}, | |
292 | 318 | }; |
293 | 319 | |
294 | 320 | public static final String[] OKINIIRI = {"★★★★★","★★★★","★★★","★★","★",""}; |
@@ -152,6 +152,12 @@ public class TVProgramUtils implements Cloneable { | ||
152 | 152 | public static boolean getUseProgCache(){ return useProgCache; } |
153 | 153 | private static boolean useProgCache = true; |
154 | 154 | |
155 | + /* | |
156 | + * 高速キャッシュファイルの読み込みを無効化する | |
157 | + */ | |
158 | + public static void invalidateProgCache(boolean b){ invalidProgCache = b; } | |
159 | + private static boolean invalidProgCache = false; | |
160 | + | |
155 | 161 | /******************************************************************************* |
156 | 162 | * オプション確認 |
157 | 163 | ******************************************************************************/ |
@@ -1121,6 +1127,12 @@ public class TVProgramUtils implements Cloneable { | ||
1121 | 1127 | //pdl.addOption(ProgOption.NOSCRUMBLE); |
1122 | 1128 | pdl.noscrumble = ProgScrumble.NOSCRUMBLE; |
1123 | 1129 | } |
1130 | + else if (mx.group(1).equals("4K")) { | |
1131 | + pdl.addOption(ProgOption.BS4K); | |
1132 | + } | |
1133 | + else if (mx.group(1).equals("8K")) { | |
1134 | + pdl.addOption(ProgOption.BS8K); | |
1135 | + } | |
1124 | 1136 | |
1125 | 1137 | else if (mx.group(1).matches("^(S|N|B|映|双|解|手|天|英|日|録|HV)$")) { |
1126 | 1138 | // 無視するフラグ |
@@ -1571,7 +1583,7 @@ public class TVProgramUtils implements Cloneable { | ||
1571 | 1583 | public boolean loadFromProgCache(String prefix){ |
1572 | 1584 | TatCount tc = new TatCount(); |
1573 | 1585 | |
1574 | - if (!useProgCache){ | |
1586 | + if (!useProgCache || invalidProgCache){ | |
1575 | 1587 | System.out.println("高速キャッシュファイルは使用しません"); |
1576 | 1588 | return false; |
1577 | 1589 | } |
@@ -1614,6 +1626,16 @@ public class TVProgramUtils implements Cloneable { | ||
1614 | 1626 | |
1615 | 1627 | // 1放送局分を文字列から生成する |
1616 | 1628 | ProgList pl = new ProgList(txt.substring(index, le)); |
1629 | + | |
1630 | + for ( Center cr : crlist ) { | |
1631 | + if ( pl.Area.equals(cr.getAreaCode()) && pl.CenterId.equals(cr.getLink()) ) { | |
1632 | + pl.SubArea = cr.getType(); | |
1633 | + pl.Center = cr.getCenter(); | |
1634 | + pl.BgColor = cr.getBgColor(); | |
1635 | + break; | |
1636 | + } | |
1637 | + } | |
1638 | + | |
1617 | 1639 | pcl.add(pl); |
1618 | 1640 | |
1619 | 1641 | if (le == -1) |
@@ -2,8 +2,11 @@ package tainavi; | ||
2 | 2 | |
3 | 3 | import java.awt.BorderLayout; |
4 | 4 | import java.awt.Component; |
5 | +import java.beans.PropertyChangeEvent; | |
6 | +import java.beans.PropertyChangeListener; | |
5 | 7 | |
6 | 8 | import javax.swing.JPanel; |
9 | +import javax.swing.JSplitPane; | |
7 | 10 | import javax.swing.JTabbedPane; |
8 | 11 | |
9 | 12 |
@@ -28,21 +31,21 @@ public class VWMainWindow extends JPanel { | ||
28 | 31 | CHCONV ("CHコンバート設定"), |
29 | 32 | CHDAT ("CHコード設定"), |
30 | 33 | ; |
31 | - | |
34 | + | |
32 | 35 | String name; |
33 | - | |
36 | + | |
34 | 37 | private MWinTab(String name) { |
35 | 38 | this.name = name; |
36 | 39 | } |
37 | - | |
40 | + | |
38 | 41 | public String getName() { |
39 | 42 | return name; |
40 | 43 | } |
41 | - | |
44 | + | |
42 | 45 | public int getIndex() { |
43 | 46 | return ordinal(); |
44 | 47 | } |
45 | - | |
48 | + | |
46 | 49 | public static MWinTab getAt(int index) { |
47 | 50 | for ( MWinTab tab : MWinTab.values() ) { |
48 | 51 | if ( tab.ordinal() == index ) { |
@@ -51,28 +54,36 @@ public class VWMainWindow extends JPanel { | ||
51 | 54 | } |
52 | 55 | return null; |
53 | 56 | } |
54 | - | |
57 | + | |
55 | 58 | public static int size() { return MWinTab.values().length; } |
56 | - | |
59 | + | |
57 | 60 | } |
58 | 61 | |
59 | 62 | private final String SETTING_LIST = "設定一覧"; |
60 | 63 | |
64 | + private Bounds bounds = null; | |
65 | + | |
61 | 66 | /* |
62 | 67 | * 部品 |
63 | 68 | */ |
64 | - | |
69 | + | |
70 | + private JSplitPane jSplitPane = null; | |
65 | 71 | private JTabbedPane jTabbedPane = null; |
66 | 72 | private JTabbedPane jTabbedPane_settings = null; |
73 | + private VWStatusTextArea statusArea = null; | |
74 | + | |
67 | 75 | |
68 | - | |
69 | 76 | /* |
70 | 77 | * コンストラクタ |
71 | 78 | */ |
72 | - | |
73 | - public VWMainWindow() { | |
79 | + | |
80 | + public VWMainWindow(Viewer v) { | |
81 | + bounds = v.getBoundsEnv(); | |
82 | + | |
74 | 83 | this.setLayout(new BorderLayout()); |
75 | - this.add(getJTabbedPane(), BorderLayout.CENTER); | |
84 | + this.add(getJSplitPane(), BorderLayout.CENTER); | |
85 | + | |
86 | + jSplitPane.setTopComponent(getJTabbedPane()); | |
76 | 87 | getJTabbedPane_settings(); |
77 | 88 | |
78 | 89 | // タブを全部準備する |
@@ -83,22 +94,95 @@ public class VWMainWindow extends JPanel { | ||
83 | 94 | addTab(null, tab); |
84 | 95 | } |
85 | 96 | } |
86 | - | |
87 | - | |
97 | + | |
98 | + | |
88 | 99 | /* |
89 | 100 | * 公開メソッド |
90 | 101 | */ |
91 | - | |
102 | + | |
92 | 103 | // ツールバーを追加する |
93 | 104 | public void addToolBar(Component comp){ |
94 | 105 | this.add(comp, BorderLayout.PAGE_START); |
95 | 106 | } |
96 | - | |
97 | - | |
98 | - public void addStatusArea(Component comp) { | |
99 | - this.add(comp, BorderLayout.PAGE_END); | |
107 | + | |
108 | + /* | |
109 | + * ステータスエリア | |
110 | + */ | |
111 | + public void addStatusArea(VWStatusTextArea comp) { | |
112 | + statusArea = comp; | |
113 | + jSplitPane.setBottomComponent(comp); | |
114 | + } | |
115 | + | |
116 | + /* | |
117 | + * ステータスエリアの行数を設定する | |
118 | + */ | |
119 | + public void setStatusAreaRows(int rows){ | |
120 | + setStatusAreaHeight(statusArea.getHeightFromRows(rows)); | |
121 | + } | |
122 | + | |
123 | + /* | |
124 | + * ステータスエリアの高さを初期化する | |
125 | + */ | |
126 | + public void initStatusAreaHeight(){ | |
127 | + if (bounds.getStatusRows() > 0){ | |
128 | + resetStatusAreaHeight(); | |
129 | + } | |
130 | + else{ | |
131 | + int sh = bounds.getStatusWindowHeight(); | |
132 | + if (sh <= 1) | |
133 | + resetStatusAreaHeight(); | |
134 | + else | |
135 | + setStatusAreaHeight(sh); | |
136 | + } | |
137 | + } | |
138 | + | |
139 | + /* | |
140 | + * ステータス絵アリアの高さを設定する | |
141 | + */ | |
142 | + public void setStatusAreaHeight(int sh){ | |
143 | + int h = jSplitPane.getHeight(); | |
144 | + jSplitPane.setDividerLocation(h-sh); | |
145 | + bounds.setStatusWindowHeight(sh); | |
100 | 146 | } |
101 | - | |
147 | + | |
148 | + /* | |
149 | + * ステータスエリアの高さをリセットする | |
150 | + */ | |
151 | + public void resetStatusAreaHeight(){ | |
152 | + int rows = bounds.getStatusRows(); | |
153 | + int sh = statusArea.getHeightFromRows(rows > 0 ? rows : 5); | |
154 | + bounds.setStatusWindowHeight(sh); | |
155 | + | |
156 | + setStatusAreaHeight(sh); | |
157 | + } | |
158 | + | |
159 | + /* | |
160 | + * ステータスエリアの表示・非表示を設定する | |
161 | + */ | |
162 | + public void setStatusAreaVisible(boolean b){ | |
163 | + statusArea.setVisible(b); | |
164 | + | |
165 | + if (b) | |
166 | + initStatusAreaHeight(); | |
167 | + } | |
168 | + | |
169 | + /* | |
170 | + * ジオメトリ情報を初期化する | |
171 | + */ | |
172 | + public void initBounds(){ | |
173 | + initStatusAreaHeight(); | |
174 | + | |
175 | + jSplitPane.addPropertyChangeListener(JSplitPane.DIVIDER_LOCATION_PROPERTY, new PropertyChangeListener() { | |
176 | + @Override | |
177 | + public void propertyChange(PropertyChangeEvent pce) { | |
178 | + if (statusArea.isVisible()){ | |
179 | + int h = jSplitPane.getHeight(); | |
180 | + bounds.setStatusWindowHeight(h-jSplitPane.getDividerLocation()); | |
181 | + } | |
182 | + } | |
183 | + }); | |
184 | + } | |
185 | + | |
102 | 186 | // タブを追加する |
103 | 187 | public boolean addTab(Component comp, MWinTab tab) { |
104 | 188 | if ( jTabbedPane.getTabCount() + jTabbedPane_settings.getTabCount() < tab.getIndex() ) { |
@@ -132,7 +216,7 @@ public class VWMainWindow extends JPanel { | ||
132 | 216 | } |
133 | 217 | jTabbedPane.setSelectedIndex(tab.getIndex()); |
134 | 218 | } |
135 | - | |
219 | + | |
136 | 220 | // |
137 | 221 | public Component getTab(MWinTab tab) { |
138 | 222 | if ( tab.getIndex() >= MWinTab.SETTING.getIndex() ) { |
@@ -140,7 +224,7 @@ public class VWMainWindow extends JPanel { | ||
140 | 224 | } |
141 | 225 | return jTabbedPane.getComponent(tab.getIndex()); |
142 | 226 | } |
143 | - | |
227 | + | |
144 | 228 | // タブが選択されているか確認する |
145 | 229 | public boolean isTabSelected(MWinTab tab) { |
146 | 230 | if ( tab.getIndex() >= MWinTab.SETTING.getIndex() ) { |
@@ -148,7 +232,7 @@ public class VWMainWindow extends JPanel { | ||
148 | 232 | } |
149 | 233 | return (jTabbedPane.getSelectedIndex() == tab.getIndex()); |
150 | 234 | } |
151 | - | |
235 | + | |
152 | 236 | // どのタブが選択されているのやら |
153 | 237 | public MWinTab getSelectedTab() { |
154 | 238 | if ( jTabbedPane.getSelectedIndex() == MWinTab.SETTING.getIndex() ) { |
@@ -156,7 +240,7 @@ public class VWMainWindow extends JPanel { | ||
156 | 240 | } |
157 | 241 | return MWinTab.getAt(jTabbedPane.getSelectedIndex()); |
158 | 242 | } |
159 | - | |
243 | + | |
160 | 244 | // 設定タブをトグル切り替え |
161 | 245 | private final int firstSettingTab = MWinTab.SETTING.ordinal(); |
162 | 246 | private final int countSettingTab = MWinTab.size()-firstSettingTab; |
@@ -165,18 +249,27 @@ public class VWMainWindow extends JPanel { | ||
165 | 249 | public boolean toggleShowSettingTabs() { |
166 | 250 | return true; |
167 | 251 | } |
168 | - | |
252 | + | |
169 | 253 | public boolean getShowSettingTabs() { |
170 | 254 | return true; |
171 | 255 | } |
172 | 256 | public void setShowSettingTabs(boolean b) { |
173 | 257 | } |
174 | - | |
175 | - | |
258 | + | |
259 | + | |
176 | 260 | /* |
177 | - * | |
261 | + * | |
178 | 262 | */ |
179 | - | |
263 | + | |
264 | + private JSplitPane getJSplitPane() { | |
265 | + if (jSplitPane == null){ | |
266 | + jSplitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT); | |
267 | + jSplitPane.setResizeWeight(1.0); | |
268 | + } | |
269 | + | |
270 | + return jSplitPane; | |
271 | + } | |
272 | + | |
180 | 273 | private JTabbedPane getJTabbedPane() { |
181 | 274 | if (jTabbedPane == null) { |
182 | 275 | jTabbedPane = new JTabbedPane(); |
@@ -190,14 +283,14 @@ public class VWMainWindow extends JPanel { | ||
190 | 283 | } |
191 | 284 | return jTabbedPane_settings; |
192 | 285 | } |
193 | - | |
286 | + | |
194 | 287 | /** |
195 | 288 | * @deprecated |
196 | 289 | */ |
197 | 290 | public void appendStatusMessage(String s) { |
198 | 291 | throw new UnsupportedOperationException(); |
199 | 292 | } |
200 | - | |
293 | + | |
201 | 294 | /** |
202 | 295 | * @deprecated |
203 | 296 | * @see Viewer#setStatusVisible(boolean) |
@@ -205,5 +298,5 @@ public class VWMainWindow extends JPanel { | ||
205 | 298 | public void setStatusVisible(boolean b) { |
206 | 299 | throw new UnsupportedOperationException(); |
207 | 300 | } |
208 | - | |
301 | + | |
209 | 302 | } |
@@ -37,6 +37,14 @@ public class VWStatusTextArea extends JPanel implements StatusTextArea { | ||
37 | 37 | |
38 | 38 | } |
39 | 39 | |
40 | + /* | |
41 | + * 行数から高さを計算する | |
42 | + */ | |
43 | + public int getHeightFromRows(int rows){ | |
44 | + int hl = jtp.getFont().getSize(); | |
45 | + return CommonUtils.getPixelFromPoint(hl*rows)+8; | |
46 | + } | |
47 | + | |
40 | 48 | private JScrollPane getJScrollPane_statusarea() { |
41 | 49 | if (jsp == null) { |
42 | 50 | jsp = new JScrollPane(getJTextPane_statusarea(),JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,JScrollPane.HORIZONTAL_SCROLLBAR_NEVER); |
@@ -102,8 +110,7 @@ public class VWStatusTextArea extends JPanel implements StatusTextArea { | ||
102 | 110 | if (jsp == null) |
103 | 111 | return; |
104 | 112 | Dimension dim = jsp.getPreferredSize(); |
105 | - double fh = (double)jtp.getFont().getSize()*1.35; | |
106 | - dim.height = (int)(fh*(float)rows); | |
113 | + dim.height = getHeightFromRows(rows); | |
107 | 114 | jsp.setPreferredSize(dim); |
108 | 115 | } |
109 | 116 | } |
@@ -5,7 +5,7 @@ import java.util.regex.Pattern; | ||
5 | 5 | |
6 | 6 | |
7 | 7 | public class VersionInfo { |
8 | - private static final String Version = "タイニー番組ナビゲータ for DBR-T2007 3.22.18β+1.12.7"; | |
8 | + private static final String Version = "タイニー番組ナビゲータ for DBR-T2007 3.22.18β+1.12.8"; | |
9 | 9 | |
10 | 10 | private static final String OSname = System.getProperty("os.name"); |
11 | 11 | private static final String OSvers = System.getProperty("os.version"); |
@@ -97,7 +97,7 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
97 | 97 | private void StdAppendMessage(String message) { System.out.println(CommonUtils.getNow() + message); } |
98 | 98 | private void StdAppendError(String message) { System.err.println(CommonUtils.getNow() + message); } |
99 | 99 | // |
100 | - private void MWinSetVisible(boolean b) { mwin.setVisible(b); } | |
100 | + private void MWinSetVisible(boolean b) { mainWindow.setStatusAreaVisible(b); } | |
101 | 101 | // |
102 | 102 | private void StWinClear() { stwin.clear(); } |
103 | 103 | private void StWinSetVisible(boolean b) { stwin.setVisible(b); } |
@@ -374,7 +374,10 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
374 | 374 | |
375 | 375 | private TrayIcon trayicon = null; |
376 | 376 | |
377 | - | |
377 | + /******************************************************************************* | |
378 | + * パブリック関数 | |
379 | + ******************************************************************************/ | |
380 | + public Bounds getBoundsEnv(){ return bounds; } | |
378 | 381 | |
379 | 382 | /******************************************************************************* |
380 | 383 | * タブやダイアログのインスタンス作成用クラス定義 |
@@ -1534,7 +1537,9 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
1534 | 1537 | chdatsetting.updateChannelDatTable(); |
1535 | 1538 | |
1536 | 1539 | // 番組情報の再取得 |
1540 | + TVProgramUtils.invalidateProgCache(true); | |
1537 | 1541 | loadTVProgram(false,LoadFor.ALL, false); // 部品呼び出し |
1542 | + TVProgramUtils.invalidateProgCache(false); | |
1538 | 1543 | |
1539 | 1544 | // ツールバーに反映 |
1540 | 1545 | toolBar.setPagerItems(); |
@@ -1839,6 +1844,66 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
1839 | 1844 | @Override |
1840 | 1845 | protected void ringBeep() { Viewer.this.ringBeep(); } |
1841 | 1846 | |
1847 | + /* | |
1848 | + * 前のページに移動する | |
1849 | + * @see tainavi.AbsToolBar#moveToPrevPage() | |
1850 | + */ | |
1851 | + @Override | |
1852 | + protected void moveToPrevPage(){ | |
1853 | + if (!isPrevPageEnabled()) | |
1854 | + return; | |
1855 | + | |
1856 | + if (paper.isByCenterMode()) | |
1857 | + paper.moveToPrevDatePage(); | |
1858 | + else | |
1859 | + moveToPrevCenterPage(); | |
1860 | + } | |
1861 | + | |
1862 | + /* | |
1863 | + * 前のページに移動可能かを返す | |
1864 | + * @see tainavi.AbsToolBar#isPrevPageEnabled() | |
1865 | + */ | |
1866 | + @Override | |
1867 | + protected boolean isPrevPageEnabled(){ | |
1868 | + if (!mainWindow.isTabSelected(MWinTab.PAPER)) | |
1869 | + return false; | |
1870 | + | |
1871 | + if (paper.isByCenterMode()) | |
1872 | + return paper.isPrevDatePageEnabled(); | |
1873 | + else | |
1874 | + return isPrevCenterPageEnabled(); | |
1875 | + } | |
1876 | + | |
1877 | + /* | |
1878 | + * 次のページに移動する | |
1879 | + * @see tainavi.AbsToolBar#moveToNextPage() | |
1880 | + */ | |
1881 | + @Override | |
1882 | + protected void moveToNextPage(){ | |
1883 | + if (!isNextPageEnabled()) | |
1884 | + return; | |
1885 | + | |
1886 | + if (paper.isByCenterMode()) | |
1887 | + paper.moveToNextDatePage(); | |
1888 | + else | |
1889 | + moveToNextCenterPage(); | |
1890 | + } | |
1891 | + | |
1892 | + /* | |
1893 | + * 次のページに移動可能かを返す | |
1894 | + * @see tainavi.AbsToolBar#isNextPageEnabled() | |
1895 | + */ | |
1896 | + @Override | |
1897 | + protected boolean isNextPageEnabled(){ | |
1898 | + if (!mainWindow.isTabSelected(MWinTab.PAPER)) | |
1899 | + return false; | |
1900 | + | |
1901 | + if (paper.isByCenterMode()) | |
1902 | + return paper.isNextDatePageEnabled(); | |
1903 | + else | |
1904 | + return isNextCenterPageEnabled(); | |
1905 | + } | |
1906 | + | |
1842 | 1907 | @Override |
1843 | 1908 | protected boolean doKeywordSerach(SearchKey search, String kStr, String sStr, boolean doFilter) { |
1844 | 1909 |
@@ -4717,8 +4782,8 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
4717 | 4782 | mpList.setHistoryOnlyUpdateOnce(env.getHistoryOnlyUpdateOnce()); |
4718 | 4783 | mpList.setShowOnlyNonrepeated(env.getShowOnlyNonrepeated()); |
4719 | 4784 | |
4720 | - mwin.setRows(bounds.getStatusRows()); | |
4721 | 4785 | setStatusVisible(false); |
4786 | + mainWindow.initStatusAreaHeight(); | |
4722 | 4787 | if (bounds.getShowStatus()) |
4723 | 4788 | setStatusVisible(true); |
4724 | 4789 |
@@ -5530,7 +5595,7 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
5530 | 5595 | // コンポーネント作成 |
5531 | 5596 | { |
5532 | 5597 | // メインウィンドウの作成 |
5533 | - mainWindow = new VWMainWindow(); | |
5598 | + mainWindow = new VWMainWindow(this); | |
5534 | 5599 | |
5535 | 5600 | // 内部クラスのインスタンス生成 |
5536 | 5601 | toolBar = new VWToolBar(); |
@@ -5564,7 +5629,6 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
5564 | 5629 | // ツールバーなど |
5565 | 5630 | mainWindow.addToolBar(toolBar); |
5566 | 5631 | mainWindow.addStatusArea(mwin); |
5567 | - mwin.setRows(bounds.getStatusRows()); | |
5568 | 5632 | |
5569 | 5633 | // タブ群 |
5570 | 5634 | mainWindow.addTab(listed, MWinTab.LISTED); |
@@ -6069,6 +6133,8 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
6069 | 6133 | |
6070 | 6134 | sca.add(new ShortCut(SCROLL_ACTION_PREV_PAPERNODE, KeyEvent.VK_F5, 0, sc_prev_papernode)); |
6071 | 6135 | sca.add(new ShortCut(SCROLL_ACTION_NEXT_PAPERNODE, KeyEvent.VK_F6, 0, sc_next_papernode)); |
6136 | + sca.add(new ShortCut(SCROLL_ACTION_PREV_PAPERNODE, KeyEvent.VK_UP, KeyEvent.ALT_DOWN_MASK, sc_prev_papernode)); | |
6137 | + sca.add(new ShortCut(SCROLL_ACTION_NEXT_PAPERNODE, KeyEvent.VK_DOWN, KeyEvent.ALT_DOWN_MASK, sc_next_papernode)); | |
6072 | 6138 | |
6073 | 6139 | sca.add(new ShortCut(SCROLL_ACTION_PREV_PAGE, KeyEvent.VK_F7, 0, sc_prev_page)); |
6074 | 6140 | sca.add(new ShortCut(SCROLL_ACTION_NEXT_PAGE, KeyEvent.VK_F8, 0, sc_next_page)); |
@@ -6449,6 +6515,8 @@ public class Viewer extends JFrame implements ChangeListener,TickTimerListener,H | ||
6449 | 6515 | setInitBounds(); |
6450 | 6516 | this.setVisible(true); |
6451 | 6517 | |
6518 | + mainWindow.initBounds(); | |
6519 | + | |
6452 | 6520 | setTitleBar(); // タイトルバー更新 |
6453 | 6521 | |
6454 | 6522 | ShowInitTab(); // 前回開いていたタブを開く |
@@ -74,6 +74,13 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
74 | 74 | |
75 | 75 | protected String getCenterInfoId() { return "ChannelTypeDB"; } |
76 | 76 | protected String getChType() { return "6"; } |
77 | + | |
78 | + protected String getCenterInfoId4K(){ return "m_ChannelTypeUhd"; } | |
79 | + protected String getChType4K() { return "96"; } | |
80 | + | |
81 | + protected String getSiteUrl(){ return "https://www.dimora.jp/"; } | |
82 | + protected String getUrl(){ return "https://www.dimora.jp/dc/pc/P4501.do"; } | |
83 | + | |
77 | 84 | protected String getCenterCode(String id, String code) { return id.matches("^3.*$")?(bsCode):(code); } |
78 | 85 | |
79 | 86 | protected String getProgCacheFile(String areacode, String adate) { return String.format(getProgDir()+File.separator+"Dimora_%s_%s.html", areacode, adate.substring(6,8)); } |
@@ -87,7 +94,6 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
87 | 94 | /******************************************************************************* |
88 | 95 | * 番組情報を取得する |
89 | 96 | ******************************************************************************/ |
90 | - | |
91 | 97 | @Override |
92 | 98 | public boolean loadProgram(String areaCode, boolean force) { |
93 | 99 | setCacheFileOnly(true); |
@@ -159,6 +165,8 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
159 | 165 | } |
160 | 166 | |
161 | 167 | // 参照する総ページ数を計算 |
168 | + boolean has4k = hasBS4K(); | |
169 | + | |
162 | 170 | int counterMax = 0; |
163 | 171 | for ( String ac : pages.keySet() ) { |
164 | 172 | if ( ac.equals(bsCode) ) { |
@@ -166,6 +174,8 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
166 | 174 | } |
167 | 175 | counterMax += pages.get(ac)*getDogDays(); |
168 | 176 | } |
177 | + if (has4k) | |
178 | + counterMax += getDogDays(); | |
169 | 179 | |
170 | 180 | clrCookie(); |
171 | 181 |
@@ -193,6 +203,26 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
193 | 203 | } |
194 | 204 | } |
195 | 205 | |
206 | + // 4K/8Kの放送局を含む場合別途番組情報を取得する | |
207 | + if (has4k){ | |
208 | + cale = (GregorianCalendar) cal.clone(); | |
209 | + for ( int i=0; i<getDogDays(); i++ ) { | |
210 | + String adate = CommonUtils.getDateYMD(cale); | |
211 | + cale.add(Calendar.DATE, 1); | |
212 | + String edate = CommonUtils.getDateYMD(cale); | |
213 | + if (!_loadProgram4K(adate, edate, force, i, counter++, counterMax)){ | |
214 | + newplist = null; | |
215 | + return false; | |
216 | + } | |
217 | + | |
218 | + if (isCancelRequested()){ | |
219 | + newplist = null; | |
220 | + reportProgress(ERRID+"中止要求があったので番組表の取得にを中止します。"); | |
221 | + return false; | |
222 | + } | |
223 | + } | |
224 | + } | |
225 | + | |
196 | 226 | // 開始・終了日時を正しい値に計算しなおす |
197 | 227 | for ( ProgList pl : newplist ) { |
198 | 228 | setAccurateDate(pl.pdate); |
@@ -241,7 +271,7 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
241 | 271 | |
242 | 272 | String hh = String.valueOf(CommonUtils.getCalendar(0).get(Calendar.HOUR_OF_DAY)); |
243 | 273 | String tvParam = "1%2C1%2C1%2CDR%2C10%2C1%2C1%2C1%2C1%2C1%2C1"; |
244 | - String url = "http://www.dimora.jp/dc/pc/P4501.do"; | |
274 | + String url = getUrl(); | |
245 | 275 | String pstr = String.format("c_time=%s&win_id=P4501&isLogin=1&start_time=%s0500&end_time=%s0500&ch_type=%s&args=%s0500%s%s%s", |
246 | 276 | CommonUtils.getDateTimeYMD(c), |
247 | 277 | adate, |
@@ -317,6 +347,98 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
317 | 347 | return true; |
318 | 348 | } |
319 | 349 | |
350 | + /* | |
351 | + * BS 4K/8Kの番組情報を取得する | |
352 | + */ | |
353 | + protected boolean _loadProgram4K(String adate, String edate, boolean force, int wdaycol, int counter, int counterMax) { | |
354 | + // | |
355 | + String areacode = "bs4k"; | |
356 | + String aname = "BS4K"; | |
357 | + final String progCacheFile = getProgCacheFile(areacode,adate); | |
358 | + String dt = adate.substring(6,8); | |
359 | + String targetCache = "["+dt+"日/"+aname+"]: ("+counter+"/"+counterMax+") "+progCacheFile; | |
360 | + // | |
361 | + try { | |
362 | + // | |
363 | + String response = null; | |
364 | + File f = new File(progCacheFile); | |
365 | + if (force == true || f.exists() == false || isCacheOld(progCacheFile)){ | |
366 | + GregorianCalendar c = new GregorianCalendar(); | |
367 | + c.setTime(new Date()); | |
368 | + | |
369 | + String hh = String.valueOf(CommonUtils.getCalendar(0).get(Calendar.HOUR_OF_DAY)); | |
370 | + String tvParam = "1%2C1%2C1%2CDR%2C10%2C1%2C1%2C1%2C1%2C1%2C1"; | |
371 | + String url = getUrl(); | |
372 | + String pstr = String.format("c_time=%s&win_id=P4501&isLogin=1&start_time=%s0500&end_time=%s0500&ch_type=%s&args=%s0500%s%s%s", | |
373 | + CommonUtils.getDateTimeYMD(c), | |
374 | + adate, | |
375 | + edate, | |
376 | + getChType4K(), | |
377 | + adate, | |
378 | + "%2C"+hh+"%2C", | |
379 | + getChType4K(), | |
380 | + "%2C0%2C"+tvParam); | |
381 | + | |
382 | + // 本体 | |
383 | + //clrCookie(); -> もっと上に | |
384 | + addCookie("tvParam", tvParam); | |
385 | + response = webToBuffer( | |
386 | + url, | |
387 | + pstr, | |
388 | + null, | |
389 | + url, | |
390 | + thisEncoding, | |
391 | + false); | |
392 | + | |
393 | + String targetOnline = "["+dt+"日/"+aname+"]: ("+counter+"/"+counterMax+") "+url+"?"+pstr+"("+areacode+")"; | |
394 | + if ( response != null ){ | |
395 | + if ( CommonUtils.write2file(progCacheFile, "<!-- "+url+"?"+pstr+" -->\n"+response) ) { | |
396 | + reportProgress(MSGID+"番組表(オンライン)を取得しました" + targetOnline); | |
397 | + } | |
398 | + else{ | |
399 | + reportProgress(ERRID+"番組表(キャッシュ)の保存に失敗しました: "+targetCache); | |
400 | + } | |
401 | + | |
402 | + setCacheFileOnly(false); | |
403 | + } | |
404 | + else{ | |
405 | + reportProgress(ERRID+"番組表(オンライン)の取得に失敗しました" + targetOnline); | |
406 | + if (f.exists() == false) | |
407 | + return false; | |
408 | + else | |
409 | + reportProgress(MSGID+"番組表(キャッシュ)を代わりに使用します: "+targetCache); | |
410 | + } | |
411 | + | |
412 | + } | |
413 | + | |
414 | + if (response == null){ | |
415 | + if (CommonUtils.isFileAvailable(f,10)) { | |
416 | + // キャッシュファイルの読み込み | |
417 | + response = CommonUtils.read4file(progCacheFile, false); | |
418 | + if ( response == null ) { | |
419 | + reportProgress(ERRID+"番組表(キャッシュ)の取得に失敗しました"+targetCache); | |
420 | + return false; | |
421 | + } | |
422 | + reportProgress(MSGID+"番組表(キャッシュ)を取得しました"+targetCache); | |
423 | + } | |
424 | + else { | |
425 | + reportProgress(ERRID+"番組表(キャッシュ)がみつかりません"+targetCache); | |
426 | + return false; | |
427 | + } | |
428 | + } | |
429 | + | |
430 | + // 番組リストの追加 | |
431 | + getPrograms(bsCode, wdaycol, response); | |
432 | + } | |
433 | + catch (Exception e) { | |
434 | + reportProgress(ERRID+"番組表の取得で例外が発生しました: "+e.toString()); | |
435 | + e.printStackTrace(); | |
436 | + return false; | |
437 | + } | |
438 | + | |
439 | + return true; | |
440 | + } | |
441 | + | |
320 | 442 | // |
321 | 443 | private void getPrograms(String areacode, int wdaycol, String src) { |
322 | 444 |
@@ -458,6 +580,22 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
458 | 580 | } |
459 | 581 | } |
460 | 582 | |
583 | + /* | |
584 | + * BS4K/8Kの放送局が選択されているか | |
585 | + */ | |
586 | + private boolean hasBS4K(){ | |
587 | + for (Center c : crlist){ | |
588 | + if (!c.getAreaCode().equals(bsCode)) | |
589 | + continue; | |
590 | + if (c.getOrder() <= 0) | |
591 | + continue; | |
592 | + | |
593 | + if (c.getLink().startsWith("2")) | |
594 | + return true; | |
595 | + } | |
596 | + | |
597 | + return false; | |
598 | + } | |
461 | 599 | |
462 | 600 | /******************************************************************************* |
463 | 601 | * 地域情報を取得する |
@@ -487,7 +625,7 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
487 | 625 | } |
488 | 626 | |
489 | 627 | // 存在していなければWeb上から |
490 | - String uri = "http://www.dimora.jp/"; | |
628 | + String uri = getSiteUrl(); | |
491 | 629 | String response = webToBuffer(uri, thisEncoding, true);; |
492 | 630 | if ( response == null ) { |
493 | 631 | System.err.println(ERRID+"地域情報の取得に失敗しました: "+uri); |
@@ -589,6 +727,9 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
589 | 727 | cnt++; |
590 | 728 | } |
591 | 729 | |
730 | + _loadCenter4K(newcrlist); | |
731 | + reportProgress(MSGID+"BS4K/8K放送局情報を取得しました"); | |
732 | + | |
592 | 733 | if ( newcrlist.size() == 0 ) { |
593 | 734 | System.err.println(ERRID+"放送局情報の取得結果が0件だったため情報を更新しません"); |
594 | 735 | return; |
@@ -601,7 +742,7 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
601 | 742 | |
602 | 743 | private boolean _loadCenter(ArrayList<Center> newcrlist, String code, boolean bsexist) { |
603 | 744 | // 本体 |
604 | - String uri = "http://www.dimora.jp/dc/pc/P4501.do"; | |
745 | + String uri = getUrl(); | |
605 | 746 | |
606 | 747 | GregorianCalendar c = CommonUtils.getCalendar(0); |
607 | 748 | String cdate = CommonUtils.getDateTimeYMD(c); |
@@ -623,7 +764,7 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
623 | 764 | getChType(), |
624 | 765 | "%2C0%2C0%2C1%2C1%2CDR%2C10%2C1%2C1%2C1%2C1%2C1%2C1"), |
625 | 766 | null, |
626 | - "http://www.dimora.jp/dc/pc/P4501.do", | |
767 | + getUrl(), | |
627 | 768 | thisEncoding, |
628 | 769 | true); |
629 | 770 | if ( response == null ) { |
@@ -702,4 +843,81 @@ public class PlugIn_TVPDimora extends TVProgramUtils implements TVProgram,Clonea | ||
702 | 843 | return true; |
703 | 844 | } |
704 | 845 | |
846 | + /* | |
847 | + * BS4K/8Kの放送局を取得する | |
848 | + */ | |
849 | + private boolean _loadCenter4K(ArrayList<Center> newcrlist) { | |
850 | + // 本体 | |
851 | + String uri = getUrl(); | |
852 | + String areacode = bsCode; | |
853 | + | |
854 | + GregorianCalendar c = CommonUtils.getCalendar(0); | |
855 | + String cdate = CommonUtils.getDateTimeYMD(c); | |
856 | + String adate = CommonUtils.getDateYMD(c); | |
857 | + c.add(Calendar.DAY_OF_MONTH, 1); | |
858 | + String edate = CommonUtils.getDateYMD(c); | |
859 | + | |
860 | + clrCookie(); | |
861 | + String response = webToBuffer( | |
862 | + uri, | |
863 | + String.format("c_time=%s&win_id=P4501&isLogin=1&start_time=%s0500&end_time=%s0500&ch_type=%s&args=%s0500%s%s%s", | |
864 | + cdate, | |
865 | + adate, | |
866 | + edate, | |
867 | + getChType4K(), | |
868 | + adate, | |
869 | + "%2C3%2C", | |
870 | + getChType4K(), | |
871 | + "%2C0%2C1%2C1%2C1%2CDR%2C10%2C1%2C1%2C1%2C1%2C1%2C1"), | |
872 | + null, | |
873 | + getUrl(), | |
874 | + thisEncoding, | |
875 | + true); | |
876 | + if ( response == null ) { | |
877 | + reportProgress(ERRID+"番組表の取得に失敗しました: "+uri); | |
878 | + return false; | |
879 | + } | |
880 | + | |
881 | + //CommonUtils.write2file("TMP.htm", response); | |
882 | + | |
883 | + String expr = String.format("<div\\s+id=\"%s\"\\s*>(.+?)</div>", getCenterInfoId4K()); | |
884 | + Matcher ma = Pattern.compile(expr).matcher(response); | |
885 | + if ( ma.find() ) { | |
886 | + Matcher mb = Pattern.compile("(.+?),.+?,.+?,(.+?),(.+?),.+?\\|").matcher(ma.group(1)); | |
887 | + while ( mb.find() ) { | |
888 | + String centerName = CommonUtils.unEscape(mb.group(3)); | |
889 | +// String chNo = mb.group(2); | |
890 | + String centerId = mb.group(1); | |
891 | + | |
892 | + // 一部の放送局がBSと同じ名前のため、4K/8Kが必ず付くようにする | |
893 | + Matcher mc = Pattern.compile("(4K|8K|4K|8K)").matcher(centerName); | |
894 | + if (!mc.find()){ | |
895 | + centerName += " 4K"; | |
896 | + } | |
897 | + | |
898 | + // 重複する放送局は追加しない | |
899 | + boolean found=false; | |
900 | + for (Center cr2 : newcrlist){ | |
901 | + if (areacode.equals(cr2.getAreaCode()) && centerName.equals(cr2.getCenterOrig())){ | |
902 | + found = true; | |
903 | + break; | |
904 | + } | |
905 | + } | |
906 | + if (found) | |
907 | + continue; | |
908 | + | |
909 | + Center cr = new Center(); | |
910 | + cr.setAreaCode(areacode); | |
911 | + cr.setCenterOrig(centerName); | |
912 | + cr.setLink(centerId); | |
913 | + cr.setType(""); | |
914 | + cr.setEnabled(true); | |
915 | + if ( response.matches(String.format(".*<div\\s+id=\"%s\">.*",centerId)) ) { | |
916 | + newcrlist.add(cr); | |
917 | + } | |
918 | + } | |
919 | + } | |
920 | + | |
921 | + return true; | |
922 | + } | |
705 | 923 | } |