7 Commits

Author SHA1 Message Date
Tosencen eafc53e8b2 chore: update release APK to 3.0.3 2025-07-08 12:36:14 +08:00
Tosencen 9c7a0fd40e chore: bump version to 3.0.3 2025-07-08 12:31:32 +08:00
Tosencen b847ff23dd 更新设置图标:使用更简洁的线性风格设计 2025-07-07 21:43:15 +08:00
Tosencen 8579905949 feat: 1. 修改版本号为3.0.2 2. 优化历史记录复制功能 3. 调整Toast显示时间为1秒 2025-07-03 20:00:03 +08:00
Tosencen 6d6239e602 release: 发布v3.0.1版本 2025-07-03 11:25:41 +08:00
Tosencen 81832a055e release: 发布v3.0.1版本 2025-07-03 11:25:39 +08:00
Tochen 4ec3c434b2 Update README.md 2025-07-03 11:22:16 +08:00
20 changed files with 141 additions and 15 deletions
-5
View File
@@ -26,11 +26,6 @@
- 支持 TV 和手机双平台 - 支持 TV 和手机双平台
- Material Design 界面设计 - Material Design 界面设计
## 应用截图
- 视频列表
- 播放界面
- 设置中心
## 开发说明 ## 开发说明
本项目仅用于学习 Android 开发,代码改自 [FongMi/TV](https://github.com/FongMi/TV)。 本项目仅用于学习 Android 开发,代码改自 [FongMi/TV](https://github.com/FongMi/TV)。
Binary file not shown.
+5
View File
@@ -0,0 +1,5 @@
{
"name": "v3.0.1",
"code": 301,
"desc": "1. 优化项目结构,重新组织各功能模块\n2. 更新移动端界面,优化用户体验\n3. 强制使用深色模式,提供更好的观看体验"
}
Binary file not shown.
+5
View File
@@ -0,0 +1,5 @@
{
"name": "v3.0.1",
"code": 301,
"desc": "1. 优化项目结构,重新组织各功能模块\n2. 更新移动端界面,优化用户体验\n3. 强制使用深色模式,提供更好的观看体验"
}
View File
+3 -2
View File
@@ -22,8 +22,8 @@ android {
minSdk 21 minSdk 21
//noinspection ExpiredTargetSdkVersion //noinspection ExpiredTargetSdkVersion
targetSdk 28 targetSdk 28
versionCode 300 versionCode 303
versionName "3.0.0" versionName "3.0.3"
javaCompileOptions { javaCompileOptions {
annotationProcessorOptions { annotationProcessorOptions {
arguments = ["room.schemaLocation": "$projectDir/schemas".toString(), "eventBusIndex": "com.fongmi.android.tv.event.EventIndex"] arguments = ["room.schemaLocation": "$projectDir/schemas".toString(), "eventBusIndex": "com.fongmi.android.tv.event.EventIndex"]
@@ -150,4 +150,5 @@ dependencies {
annotationProcessor 'com.github.bumptech.glide:compiler:4.16.0' annotationProcessor 'com.github.bumptech.glide:compiler:4.16.0'
annotationProcessor 'org.greenrobot:eventbus-annotation-processor:3.3.1' annotationProcessor 'org.greenrobot:eventbus-annotation-processor:3.3.1'
coreLibraryDesugaring 'com.android.tools:desugar_jdk_libs_nio:2.1.4' coreLibraryDesugaring 'com.android.tools:desugar_jdk_libs_nio:2.1.4'
implementation 'io.noties.markwon:core:4.6.2'
} }
@@ -4,8 +4,11 @@ import android.Manifest;
import android.app.Notification; import android.app.Notification;
import android.content.Context; import android.content.Context;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.os.Handler;
import android.os.Looper;
import android.text.TextUtils; import android.text.TextUtils;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.Gravity;
import android.widget.TextView; import android.widget.TextView;
import android.widget.Toast; import android.widget.Toast;
@@ -25,6 +28,7 @@ public class Notify {
public static final int ID = 9527; public static final int ID = 9527;
private AlertDialog mDialog; private AlertDialog mDialog;
private Toast mToast; private Toast mToast;
private Handler mHandler;
private static class Loader { private static class Loader {
static volatile Notify INSTANCE = new Notify(); static volatile Notify INSTANCE = new Notify();
@@ -57,6 +61,14 @@ public class Notify {
get().makeText(text); get().makeText(text);
} }
public static void showCenter(int resId) {
if (resId != 0) showCenter(ResUtil.getString(resId));
}
public static void showCenter(String text) {
get().makeTextCenter(text);
}
public static void progress(Context context) { public static void progress(Context context) {
dismiss(); dismiss();
get().create(context); get().create(context);
@@ -86,4 +98,23 @@ public class Notify {
mToast.setDuration(Toast.LENGTH_LONG); mToast.setDuration(Toast.LENGTH_LONG);
mToast.show(); mToast.show();
} }
private void makeTextCenter(String message) {
if (mToast != null) mToast.cancel();
if (mHandler == null) mHandler = new Handler(Looper.getMainLooper());
if (TextUtils.isEmpty(message)) return;
mToast = new Toast(App.get());
TextView view = (TextView) LayoutInflater.from(App.get()).inflate(R.layout.view_toast, null);
view.setText(message);
mToast.setView(view);
mToast.setDuration(Toast.LENGTH_SHORT);
mToast.setGravity(Gravity.CENTER, 0, 0);
mToast.show();
// 1秒后取消Toast
mHandler.removeCallbacksAndMessages(null);
mHandler.postDelayed(() -> {
if (mToast != null) mToast.cancel();
}, 1000); // 1000毫秒 = 1秒
}
} }
@@ -0,0 +1,54 @@
package com.fongmi.android.tv.ui.dialog;
import android.content.Intent;
import android.net.Uri;
import android.view.LayoutInflater;
import android.view.ViewGroup;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
import androidx.viewbinding.ViewBinding;
import com.fongmi.android.tv.databinding.DialogAboutBinding;
public class AboutDialog extends BaseDialog {
private DialogAboutBinding binding;
public static void show(FragmentActivity activity) {
new AboutDialog().show(activity.getSupportFragmentManager(), "AboutDialog");
}
public static void show(Fragment fragment) {
new AboutDialog().show(fragment.getChildFragmentManager(), "AboutDialog");
}
@Override
protected ViewBinding getBinding(@NonNull LayoutInflater inflater, @Nullable ViewGroup container) {
binding = DialogAboutBinding.inflate(inflater, container, false);
return binding;
}
@Override
protected void initEvent() {
binding.github.setOnClickListener(v -> openGitHub());
}
private void openGitHub() {
try {
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setData(Uri.parse("https://github.com/Tosencen/XMBOX/releases/tag/v3.0.3"));
startActivity(intent);
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public void onDestroyView() {
super.onDestroyView();
binding = null;
}
}
@@ -1,15 +1,20 @@
package com.fongmi.android.tv.ui.dialog; package com.fongmi.android.tv.ui.dialog;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import androidx.appcompat.app.AlertDialog; import androidx.appcompat.app.AlertDialog;
import androidx.fragment.app.Fragment; import androidx.fragment.app.Fragment;
import com.fongmi.android.tv.App;
import com.fongmi.android.tv.bean.Config; import com.fongmi.android.tv.bean.Config;
import com.fongmi.android.tv.databinding.DialogHistoryBinding; import com.fongmi.android.tv.databinding.DialogHistoryBinding;
import com.fongmi.android.tv.impl.ConfigCallback; import com.fongmi.android.tv.impl.ConfigCallback;
import com.fongmi.android.tv.ui.adapter.ConfigAdapter; import com.fongmi.android.tv.ui.adapter.ConfigAdapter;
import com.fongmi.android.tv.ui.custom.SpaceItemDecoration; import com.fongmi.android.tv.ui.custom.SpaceItemDecoration;
import com.fongmi.android.tv.utils.Notify;
import com.google.android.material.dialog.MaterialAlertDialogBuilder; import com.google.android.material.dialog.MaterialAlertDialogBuilder;
public class HistoryDialog implements ConfigAdapter.OnClickListener { public class HistoryDialog implements ConfigAdapter.OnClickListener {
@@ -45,7 +50,6 @@ public class HistoryDialog implements ConfigAdapter.OnClickListener {
binding.recycler.setHasFixedSize(true); binding.recycler.setHasFixedSize(true);
binding.recycler.setAdapter(adapter.addAll(type)); binding.recycler.setAdapter(adapter.addAll(type));
binding.recycler.addItemDecoration(new SpaceItemDecoration(1, 8)); binding.recycler.addItemDecoration(new SpaceItemDecoration(1, 8));
binding.recycler.post(() -> binding.recycler.scrollToPosition(0));
} }
private void setDialog() { private void setDialog() {
@@ -60,6 +64,13 @@ public class HistoryDialog implements ConfigAdapter.OnClickListener {
dialog.dismiss(); dialog.dismiss();
} }
@Override
public void onCopyClick(Config item) {
ClipboardManager manager = (ClipboardManager) App.get().getSystemService(Context.CLIPBOARD_SERVICE);
manager.setPrimaryClip(ClipData.newPlainText("url", item.getUrl()));
Notify.showCenter("复制成功");
}
@Override @Override
public void onDeleteClick(Config item) { public void onDeleteClick(Config item) {
if (adapter.remove(item) == 0) dialog.dismiss(); if (adapter.remove(item) == 0) dialog.dismiss();
+15 -7
View File
@@ -1,10 +1,18 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android" <vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="48dp" android:width="24dp"
android:height="48dp" android:height="24dp"
android:tint="?attr/colorControlNormal" android:viewportWidth="24"
android:viewportWidth="960" android:viewportHeight="24">
android:viewportHeight="960">
<path <path
android:fillColor="@android:color/white" android:fillColor="#FF000000"
android:pathData="M546,880L414,880Q403,880 394.5,873Q386,866 384,855L368,754Q349,747 328,735Q307,723 291,710L198,753Q187,758 176,754.5Q165,751 159,740L93,623Q87,613 90,602Q93,591 102,584L188,521Q186,512 185.5,500.5Q185,489 185,480Q185,471 185.5,459.5Q186,448 188,439L102,376Q93,369 90,358Q87,347 93,337L159,220Q165,209 176,205.5Q187,202 198,207L291,250Q307,237 328,225Q349,213 368,207L384,105Q386,94 394.5,87Q403,80 414,80L546,80Q557,80 565.5,87Q574,94 576,105L592,206Q611,213 632.5,224.5Q654,236 669,250L762,207Q773,202 784,205.5Q795,209 801,220L867,336Q873,346 870.5,357.5Q868,369 858,376L772,437Q774,447 774.5,458.5Q775,470 775,480Q775,490 774.5,501Q774,512 772,522L858,584Q867,591 870,602Q873,613 867,623L801,740Q795,751 784,754.5Q773,758 762,753L669,710Q653,723 632.5,735.5Q612,748 592,754L576,855Q574,866 565.5,873Q557,880 546,880ZM480,610Q534,610 572,572Q610,534 610,480Q610,426 572,388Q534,350 480,350Q426,350 388,388Q350,426 350,480Q350,534 388,572Q426,610 480,610ZM480,550Q451,550 430.5,529.5Q410,509 410,480Q410,451 430.5,430.5Q451,410 480,410Q509,410 529.5,430.5Q550,451 550,480Q550,509 529.5,529.5Q509,550 480,550ZM480,480L480,480L480,480Q480,480 480,480Q480,480 480,480L480,480L480,480L480,480Q480,480 480,480Q480,480 480,480Q480,480 480,480Q480,480 480,480L480,480L480,480L480,480Q480,480 480,480Q480,480 480,480L480,480L480,480L480,480Q480,480 480,480Q480,480 480,480L480,480L480,480L480,480Q480,480 480,480Q480,480 480,480Q480,480 480,480Q480,480 480,480L480,480L480,480L480,480Q480,480 480,480Q480,480 480,480L480,480ZM436,820L524,820L538,708Q571,700 600.5,683Q630,666 654,642L760,688L800,616L706,547Q710,530 712.5,513.5Q715,497 715,480Q715,463 713,446.5Q711,430 706,413L800,344L760,272L654,318Q631,292 602,274.5Q573,257 538,252L524,140L436,140L422,252Q388,259 358.5,276Q329,293 306,318L200,272L160,344L254,413Q250,430 247.5,446.5Q245,463 245,480Q245,497 247.5,513.5Q250,530 254,547L160,616L200,688L306,642Q330,666 359.5,683Q389,700 422,708L436,820Z" /> android:fillAlpha="0"
android:strokeWidth="1.5"
android:strokeColor="#FF000000"
android:pathData="M12,12m-2,0a2,2 0,1 1,4 0a2,2 0,1 1,-4 0"/>
<path
android:fillColor="#FF000000"
android:fillAlpha="0"
android:strokeWidth="1.5"
android:strokeColor="#FF000000"
android:pathData="M19.14,12.94C19.18,12.64 19.2,12.32 19.2,12C19.2,11.68 19.18,11.36 19.14,11.06L21.16,9.48C21.34,9.34 21.4,9.08 21.28,8.88L19.36,5.52C19.24,5.32 18.98,5.24 18.76,5.32L16.36,6.34C15.84,5.94 15.28,5.62 14.66,5.38L14.3,2.8C14.26,2.58 14.08,2.4 13.84,2.4H10.16C9.92,2.4 9.74,2.58 9.7,2.8L9.34,5.38C8.72,5.62 8.16,5.94 7.64,6.34L5.24,5.32C5.02,5.24 4.76,5.32 4.64,5.52L2.72,8.88C2.6,9.08 2.66,9.34 2.84,9.48L4.86,11.06C4.82,11.36 4.8,11.68 4.8,12C4.8,12.32 4.82,12.64 4.86,12.94L2.84,14.52C2.66,14.66 2.6,14.92 2.72,15.12L4.64,18.48C4.76,18.68 5.02,18.76 5.24,18.68L7.64,17.66C8.16,18.06 8.72,18.38 9.34,18.62L9.7,21.2C9.74,21.42 9.92,21.6 10.16,21.6H13.84C14.08,21.6 14.26,21.42 14.3,21.2L14.66,18.62C15.28,18.38 15.84,18.06 16.36,17.66L18.76,18.68C18.98,18.76 19.24,18.68 19.36,18.48L21.28,15.12C21.4,14.92 21.34,14.66 21.16,14.52L19.14,12.94Z"/>
</vector> </vector>
@@ -0,0 +1,16 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="24"
android:viewportHeight="24">
<path
android:fillColor="#FF000000"
android:strokeWidth="1.5"
android:strokeColor="#FF000000"
android:pathData="M12,12m-2,0a2,2 0,1 1,4 0a2,2 0,1 1,-4 0"/>
<path
android:fillColor="#FF000000"
android:strokeWidth="1.5"
android:strokeColor="#FF000000"
android:pathData="M19.14,12.94C19.18,12.64 19.2,12.32 19.2,12C19.2,11.68 19.18,11.36 19.14,11.06L21.16,9.48C21.34,9.34 21.4,9.08 21.28,8.88L19.36,5.52C19.24,5.32 18.98,5.24 18.76,5.32L16.36,6.34C15.84,5.94 15.28,5.62 14.66,5.38L14.3,2.8C14.26,2.58 14.08,2.4 13.84,2.4H10.16C9.92,2.4 9.74,2.58 9.7,2.8L9.34,5.38C8.72,5.62 8.16,5.94 7.64,6.34L5.24,5.32C5.02,5.24 4.76,5.32 4.64,5.52L2.72,8.88C2.6,9.08 2.66,9.34 2.84,9.48L4.86,11.06C4.82,11.36 4.8,11.68 4.8,12C4.8,12.32 4.82,12.64 4.86,12.94L2.84,14.52C2.66,14.66 2.6,14.92 2.72,15.12L4.64,18.48C4.76,18.68 5.02,18.76 5.24,18.68L7.64,17.66C8.16,18.06 8.72,18.38 9.34,18.62L9.7,21.2C9.74,21.42 9.92,21.6 10.16,21.6H13.84C14.08,21.6 14.26,21.42 14.3,21.2L14.66,18.62C15.28,18.38 15.84,18.06 16.36,17.66L18.76,18.68C18.98,18.76 19.24,18.68 19.36,18.48L21.28,15.12C21.4,14.92 21.34,14.66 21.16,14.52L19.14,12.94Z"/>
</vector>
View File
View File
View File
View File
View File
View File
View File
View File