其通过调用 Android 的原生 API 来实现通知功能,并确保通知在不同版本的 Android 系统上都能正常工作。
1.创建一个uniapp项目
以下是创建本地通知栏消息代码
// utils/notification.js
const CHANNEL_ID = "notices";
/**
* 获取当前活动的主 Activity。
* @returns {Object} 当前活动的主 Activity。
*/
function getMainActivity() {
return plus.android.runtimeMainActivity();
}
/**
* 获取系统服务。
* @param {string} serviceName - 服务名称,如 "NOTIFICATION_SERVICE"。
* @returns {Object} 系统服务对象。
*/
function getSystemService(serviceName) {
const main = getMainActivity();
const Context = plus.android.importClass("android.content.Context");
return main.getSystemService(Context[serviceName]);
}
/**
* 创建 PendingIntent。
* @param {Object} main - 主 Activity。
* @param {Object} intent - Intent 对象。
* @returns {Object} PendingIntent 对象。
*/
function createPendingIntent(main, intent) {
const PendingIntent = plus.android.importClass("android.app.PendingIntent");
return PendingIntent.getActivity(main, 0, intent, PendingIntent.FLAG_CANCEL_CURRENT);
}
/**
* 创建通知通道。
* @param {Object} nm - NotificationManager 对象。
* @param {string} channelId - 通知通道 ID。
* @param {string} channelName - 通知通道名称。
* @param {number} importance - 通知通道重要性。
*/
function createNotificationChannel(nm, channelId, channelName, importance) {
if (plus.os.version.split('.')[0] >= 8) {
const NotificationChannel = plus.android.importClass('android.app.NotificationChannel');
const channel = new NotificationChannel(channelId, channelName, importance);
if (typeof nm.createNotificationChannel === 'function') {
nm.createNotificationChannel(channel);
} else {
console.error('NotificationManager does not have createNotificationChannel method');
// 尝试使用反射调用方法
try {
const createNotificationChannelMethod = nm.getClass().getMethod('createNotificationChannel', [plus.android.importClass('android.app.NotificationChannel')]);
createNotificationChannelMethod.invoke(nm, [channel]);
} catch (e) {
console.error('Failed to call createNotificationChannel via reflection:', e);
}
}
} else {
console.error('Device OS version is less than 8.0');
}
}
/**
* 构建通知。
* @param {Object} main - 主 Activity。
* @param {string} channelId - 通知通道 ID。
* @param {Object} connect - 通知内容对象。
* @param {Object} pendingIntent - PendingIntent 对象。
* @returns {Object} 构建的通知对象。
*/
function buildNotification(main, channelId, connect, pendingIntent) {
const NotificationCompat = plus.android.importClass("androidx.core.app.NotificationCompat");
const mNotification = new NotificationCompat.Builder(main, channelId);
mNotification.setContentTitle(connect.title || 'notices通知')
.setContentText(connect.content || '')
.setAutoCancel(true)
.setShowWhen(true)
.setTicker(connect.ticker || '固定弹出通知')
.setSmallIcon(17301620)
.setPriority(NotificationCompat.PRIORITY_MAX) // 设置最高优先级
.setContentIntent(pendingIntent);
return mNotification.build();
}
/**
* 创建并显示通知。
* @param {string} content - 通知内容。
* @param {Object} data - 附加数据。
* @param {Object} connect - 通知内容对象。
* @returns {boolean} 如果成功创建通知返回 true,否则返回 false。
*/
function createNotification(content = '', data = {}, connect) {
if (plus.os.name !== 'Android') {
return false;
}
const main = getMainActivity();
const nm = getSystemService("NOTIFICATION_SERVICE");
const NotifyID = Math.floor(Math.random() * 10000) + 1;
const Intent = plus.android.importClass("android.content.Intent");
const intent = new Intent(main, main.getClass());
const payload = {
'msg': content,
'notify_id': NotifyID,
'data': data
};
intent.putExtra("receive", JSON.stringify(payload));
const pendingIntent = createPendingIntent(main, intent);
// 使用固定的渠道 ID 和名称
const channelName = "通知渠道";
const importance = plus.android.importClass("android.app.NotificationManager").IMPORTANCE_HIGH;
// 确保通知渠道只创建一次
const existingChannel = nm.getNotificationChannel(CHANNEL_ID);
if (!existingChannel) {
// console.log('创建通知渠道');
createNotificationChannel(nm, CHANNEL_ID, channelName, importance);
} else {
// console.log('通知渠道已存在');
}
const mNb = buildNotification(main, CHANNEL_ID, connect, pendingIntent);
if (plus.os.version.split('.')[0] >= 8) {
nm.notify(CHANNEL_ID, NotifyID, mNb);
} else {
nm.notify(NotifyID, mNb);
}
// vibrateDevice(300);
console.log('通知结束');
return true;
}
/**
* 使设备振动。
* @param {number} duration - 振动持续时间(毫秒)。
*/
function vibrateDevice(duration) {
const main = getMainActivity();
const Vibrator = plus.android.importClass("android.os.Vibrator");
const vibrator = getSystemService("VIBRATOR_SERVICE");
vibrator.vibrate(duration);
}
/**
* 处理接收到的通知。
*/
function handleNotification() {
if (plus.os.name !== 'Android') {
return false;
}
const main = getMainActivity();
const intent = main.getIntent();
const message = intent && intent.getExtra !== undefined ? intent.getExtra("receive") : null;
const parsedMessage = message ? JSON.parse(message) : '';
// console.log('32344')
if (parsedMessage) {
const params = parsedMessage.data;
uni.navigateTo({
url: '/pages/news/news',
success: () => {
uni.setStorageSync('vuex_news', false);
}
});
const nm = getSystemService("NOTIFICATION_SERVICE");
const notifyId = parsedMessage.notify_id;
if (plus.os.version.split('.')[0] >= 8) {
nm.cancel(CHANNEL_ID, notifyId);
} else {
nm.cancel(notifyId);
}
nm.cancelAll();
intent.putExtra("receive", '');
}
}
export {createNotification, getSystemService, handleNotification, createNotificationChannel, CHANNEL_ID};
其可以结合webstock实现简单的实时消息推送