I Use This!
Activity Not Available

News

Analyzed 3 months ago. based on code collected 4 months ago.
Posted about 8 years ago
VideoLAN and the VLC development team are happy to publish version 2.2.5.1 of VLC media player todayThis fifth stable release of the "WeatherWax" version of VLC fixes a few bugs reported on VLC 2.2.4, notably video rendering issues on AMD graphics ... [More] card as well as audio distortion on macOS and 64bit Windows for certain audio files. It also includes updated codecs libraries and improves overall security.Read more about it on our release page. [Less]
Posted about 8 years ago
VideoLAN and the VLC development team are happy to publish version 2.2.5.1 of VLC media player todayThis fifth stable release of the "WeatherWax" version of VLC fixes a few bugs reported on VLC 2.2.4, notably video rendering issues on AMD graphics ... [More] card as well as audio distortion on macOS and 64bit Windows for certain audio files. It also includes updated codecs libraries and improves overall security.Read more about it on our release page. [Less]
Posted about 8 years ago
Jinja2 is a powerful templating engine for Python. Inside LAVA, we use Jinja2 to generate configuration files for every boards that we support. The configuration is generated from a template that does inherit from a base template. For instance, for a beaglebone-black called bbb-01, the template inheritance tree is the …
Posted about 8 years ago
DiffUtil steps Threading Skip queued updates Code factorization As stated in the previous post, we do process all DiffUtil.DiffResult calculations in main thread to preserve adapter state consistency. But in VLC, we have to deal with ... [More] potentially HUGE datasets, so calculation could take some time. Background calculation is mandatory then, and we have to preserve dataset consistency. I lost a few days trying different techniques then finally chose to stack updates within a queue and use it for all dataset operations, because it provides consistency safetyness. I’ve been inspired by Jon F Hancock blog post to get this right. To achieve background calculation and preserve data consistency, we now have to use our update() method for all dataset updates or manage the pending queue state manually. Threading update(list) method is now splitted in two, in order to allow queueing and recursivity: update(list) which is now limited to queueing the new list and triggering internalUpdate(list) to do the actual job. Notice all queue accesses or modifications are done in the main thread (for the same reasons that for dataset changes). // Our queue with next dataset private final ArrayDeque<Item[]> mPendingUpdates = new ArrayDeque<>(); @MainThread void update(final ArrayList<Item> newList) { mPendingUpdates.add(newList); if (mPendingUpdates.size() == 1) internalUpdate(newList); //no pending update, let's go } //private method, called exclusively by update() private void internalUpdate(final ArrayList<Item> newList) { VLCApplication.runBackground(new Runnable() { @Override public void run() { final DiffUtil.DiffResult result = DiffUtil.calculateDiff(new MediaItemDiffCallback(mDataset, newList), false); //back to main thread for the update VLCApplication.runOnMainThread(new Runnable() { @Override public void run() { mDataset = newList; result.dispatchUpdatesTo(BaseBrowserAdapter.this); //We are done with this dataset mPendingUpdates.remove(); //Process the next queued dataset if any if (!mPendingUpdates.isEmpty()) internalUpdate(mPendingUpdates.peek()); } }); } }); } For simple actions, like item insertion/removal, we must check the mPendingUpdates state. Either we handle it, either we use update(list) in order to respect the queue process we just set. So, we have to copy the most recent dataset, add/remove the item then call update(list). Using mDataset as the current reference state can be a mistake, if mPendingUpdates is not empty, another dataset will be processed between mDataset and our new list with item added or removed. In this case, we have to peek the last list from mPendingUpdates. @MainThread void addItem(Item item) { ArrayList<Item> newList = new ArrayList<>(mPendingUpdates.isEmpty() ? mDataset : mPendingUpdates.peekLast()); newList.add(item); update(newList); } For item removal, I’d recommend to just avoid calling it with position only, prefer to pass the item reference. Because the position value is likely to be wrong if there is a pending update at this time. Skip queued updates In case you can receive a bunch of updates while DiffUtil is calculating the DiffUtil.DiffResult, you get a stack of new datasets to process. Let’s skip to the last one: as we made sure they are consistent we can do it. That’s just factorizing the updates. We have to clear the mPendingUpdates queue from all its elements but the last one. Here is our current queue processing: mPendingUpdates.remove(); if (!mPendingUpdates.isEmpty()) internalUpdate(mPendingUpdates.peek()); Which becomes: mPendingUpdates.remove(); if (!mPendingUpdates.isEmpty()) { if (mPendingUpdates.size() > 1) { // more than one update queued ArrayList<Item> lastList = mPendingUpdates.peekLast(); mPendingUpdates.clear(); mPendingUpdates.add(lastList); } internalUpdate(mPendingUpdates.peek()); } Code factorization Here is my base adapter class, dedicated to pending queue management. Children classes just need to call update(newList) for any update. (I chose to not specify List because I also use arrays) public abstract class BaseQueuedAdapter <T, VH extends RecyclerView.ViewHolder> extends RecyclerView.Adapter<VH> { protected T mDataset; private final ArrayDeque<T> mPendingUpdates = new ArrayDeque<>(); final Handler mHandler = new Handler(Looper.getMainLooper()); @MainThread public boolean hasPendingUpdates() { return !mPendingUpdates.isEmpty(); } @MainThread public T peekLast() { return mPendingUpdates.isEmpty() ? mDataset : mPendingUpdates.peekLast(); } @MainThread public void update(final T items) { mPendingUpdates.add(items); if (mPendingUpdates.size() == 1) internalUpdate(items); } private void internalUpdate(final T newList) { new thread(new Runnable() { @Override public void run() { final DiffUtil.DiffResult result = DiffUtil.calculateDiff(new ItemDiffCallback(mDataList, newList), false); mHandler.post(new Runnable() { @Override public void run() { mDataset = newList; result.dispatchUpdatesTo(BaseQueuedAdapter.this); processQueue(); } }); } }).start(); } @MainThread private void processQueue() { mPendingUpdates.remove(); if (!mPendingUpdates.isEmpty()) { if (mPendingUpdates.size() > 1) { T lastList = mPendingUpdates.peekLast(); mPendingUpdates.clear(); mPendingUpdates.add(lastList); } internalUpdate(mPendingUpdates.peek()); } } } My adapter class becomes: public class MyAdapter extends BaseQueuedAdapter<List<Item>, MyAdapter.ViewHolder> That’s it, we now have asynchronous and classy RecyclerView updates without extra boilerplate 😎 [Less]
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.
Posted about 8 years ago
Following the recent revelations from Wikileaks about the use of VLC by the CIA, you can download the official statement from the VideoLAN organization here.