Android Java小部件-用于更新小部件中的ListView的策略

时间:2019-02-18 03:47:46

标签: java android android-widget

在在线示例之后,我创建了一个小部件,该小部件显示xml文件中的数据。 一切正常,至少看起来是这样:)但是

1)我将数据库连接,Internet连接和xml解析放入“ onDataSetChanged”中。因为数据是相同的,所以对于每个活动小部件重复连接是没有意义的。即使用户激活了多个小部件,我怎么也只能执行一次连接?

2)既然我做了/复制了,但是我仍然要理解:),除了重复连接的问题之外,还有其他错误吗?有什么可以做得更好的吗?

3)如果我想添加一个按钮来更新我该怎么称呼?

4)由于它每30分钟执行一次,因此我很难监视它的行为。我可以确定小部件会随着时间的推移继续正常工作吗?

感谢任何人能帮助我理解。

这里是主要文件

清单

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="pm48.news.testwidget">

<uses-permission android:name="android.permission.INTERNET" />

<application
    android:allowBackup="true"
    android:icon="@mipmap/ic_launcher"
    android:label="@string/app_name"
    android:roundIcon="@mipmap/ic_launcher_round"
    android:supportsRtl="true"
    android:theme="@style/AppTheme">

    <activity android:name=".MainActivity">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>

    <receiver android:name=".NewWidgetProvider">
        <intent-filter>
            <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
        </intent-filter>

        <meta-data
            android:name="android.appwidget.provider"
            android:resource="@xml/scroll_widget_info" />
    </receiver>

    <service
        android:name=".NewsWidgetService"
        android:permission="android.permission.BIND_REMOTEVIEWS"
        />

</application>
</manifest>

scroll_widget_info.xml

<?xml version="1.0" encoding="utf-8"?>
<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
    android:initialKeyguardLayout="@layout/scroll_widget"
    android:initialLayout="@layout/scroll_widget"
    android:minWidth="250dp"
    android:minHeight="110dp"
    android:previewImage="@drawable/example_appwidget_preview"
    android:resizeMode="vertical"
    android:updatePeriodMillis="1800000"
    android:widgetCategory="home_screen"></appwidget-provider>

NewsWidgetService

public class NewsWidgetService extends RemoteViewsService {
    @Override
    public RemoteViewsFactory onGetViewFactory(Intent intent) {
        return new NewsRemoteViewsFactory(this.getApplicationContext(), intent);
    }
}

class NewsRemoteViewsFactory implements RemoteViewsService.RemoteViewsFactory {

    private List<News> mNewsItems = new ArrayList<News>();
    private Context mContext;
    private int mAppWidgetId;

    public NewsRemoteViewsFactory(Context context, Intent intent) {
        mContext = context;
        mAppWidgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, AppWidgetManager.INVALID_APPWIDGET_ID);
    }

    public void onCreate() {
    }

    public void onDestroy() {
        mNewsItems.clear();
    }

    public int getCount() {
        return mNewsItems.size();
    }

    public RemoteViews getViewAt(int position) {

        RemoteViews rv = new RemoteViews(mContext.getPackageName(), R.layout.scroll_widget_item);

        rv.setTextViewText(R.id.widget_item, mNewsItems.get(position).getTitle());

        Bundle extras = new Bundle();
        extras.putInt(NewsWidgetProvider.EXTRA_ITEM, position);
        Intent fillInIntent = new Intent();
        fillInIntent.putExtras(extras);

        rv.setOnClickFillInIntent(R.id.widget_item, fillInIntent);

        return rv;
    }

    public RemoteViews getLoadingView() {
        return null;
    }

    public int getViewTypeCount() {
        return 1;
   }

    public long getItemId(int position) {
        return position;
    }

    public boolean hasStableIds() {
        return true;
    }


    public void onDataSetChanged() {

        NewsRoomDatabase db = NewsRoomDatabase.getDatabase(mContext.getApplicationContext());
        NewsDao mNewsDao = db.newsDao();

        try {
            URL url = new URL("http://examples.com/xml");
            URLConnection connection = url.openConnection();
            connection.setConnectTimeout(10000);
            connection.connect();
            InputStream in = connection.getInputStream();

            List<News> new_news = parseXML(in);
            mNewsDao.deleteAll();
            for (News n : new_news) {
                mNewsDao.insert(n);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        mNewsItems = mNewsDao.getAllNews();
    }


    List<News> parseXML(InputStream in) throws IOException, XmlPullParserException {
    // *** return List<News> *** 
    }
}

NewsWigetProvider

public class NewsWidgetProvider extends AppWidgetProvider {

    public static final String TOAST_ACTION = "com.example.android.stackwidget.TOAST_ACTION";
    public static final String EXTRA_ITEM = "com.example.android.stackwidget.EXTRA_ITEM";

    @Override
    public void onDeleted(Context context, int[] appWidgetIds) {
        super.onDeleted(context, appWidgetIds);
    }

    @Override
    public void onDisabled(Context context) {
        super.onDisabled(context);
    }

    @Override
    public void onEnabled(Context context) {
        super.onEnabled(context);
    }

    @Override
    public void onReceive(Context context, Intent intent) {

        AppWidgetManager mgr = AppWidgetManager.getInstance(context);

        if (intent.getAction().equals(TOAST_ACTION)) {
            int appWidgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, AppWidgetManager.INVALID_APPWIDGET_ID);
            int viewIndex = intent.getIntExtra(EXTRA_ITEM, 0);
            Toast.makeText(context, "Touched view " + viewIndex, Toast.LENGTH_SHORT).show();
        }

        super.onReceive(context, intent);
    }


    @Override
    public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
        for (int i = 0; i < appWidgetIds.length; ++i) 
            Intent intent = new Intent(context, NewsWidgetService.class);
            intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetIds[i]);

            intent.setData(Uri.parse(intent.toUri(Intent.URI_INTENT_SCHEME)));

            RemoteViews rv = new RemoteViews(context.getPackageName(), R.layout.scroll_widget);

            rv.setRemoteAdapter( R.id.stack_view, intent);

            rv.setEmptyView(R.id.stack_view, R.id.empty_view);

            Intent toastIntent = new Intent(context, NewsWidgetProvider.class);
            toastIntent.setAction(NewsWidgetProvider.TOAST_ACTION);
            toastIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetIds[i]);

            intent.setData(Uri.parse(intent.toUri(Intent.URI_INTENT_SCHEME)));

            PendingIntent toastPendingIntent = PendingIntent.getBroadcast(context, 0, toastIntent,
                    PendingIntent.FLAG_UPDATE_CURRENT);
            rv.setPendingIntentTemplate(R.id.stack_view, toastPendingIntent);


            // !!!!!! ?????
            appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetIds[i], R.id.stack_view);

            appWidgetManager.updateAppWidget(appWidgetIds[i], rv);
        }
        super.onUpdate(context, appWidgetManager, appWidgetIds);
    }
}

OT。 软件开发已有20年的历史(python,javascript,vb等),而我越来越接近Android。可能是每次必须了解如何做某事的最初挫败感,但我没有看到足够的抽象。除了编程之外,您还需要知道要使用哪个对象,它的方法和参数是什么,创建对象时想到的逻辑是什么...

0 个答案:

没有答案