[meld] matchers.helpers: Schedule our result check to the main scheduler



commit 5f2c23f58ebcd6fbe6d6e598a780dd83b70eb574
Author: Kai Willadsen <kai willadsen gmail com>
Date:   Sun Jul 16 09:48:48 2017 +1000

    matchers.helpers: Schedule our result check to the main scheduler
    
    Previously we scheduled the result check to the GLib mainloop in an idle
    handler. This had the downsides that we would spin constantly waiting
    for results, and while waiting for results we weren't showing as busy.
    
    In 68bf29, we changed the result checker to run on a 10 msec timeout,
    which solved the busy looping, but delayed results slightly and still
    didn't show our normal busy indicator.
    
    This commit switches both these things up so that we now run our results
    check in the main application scheduler (which runs as a GLib idle
    handler) and therefore we get correct a busy indicator. Doing this
    brings back the busy-loop CPU usage issue, so here we also switch up
    the result retrieval so that we actually block for 1ms when trying to
    retrieve a result, instead of not waiting at all. This is quite
    unpleasant, but it's effective.

 meld/filediff.py         |    2 +-
 meld/matchers/helpers.py |   12 +++++++++---
 2 files changed, 10 insertions(+), 4 deletions(-)
---
diff --git a/meld/filediff.py b/meld/filediff.py
index 00769ac..81999d2 100644
--- a/meld/filediff.py
+++ b/meld/filediff.py
@@ -180,7 +180,7 @@ class FileDiff(melddoc.MeldDoc, gnomeglade.Component):
         self.force_highlight = False
         self.syncpoints = []
         self.in_nested_textview_gutter_expose = False
-        self._cached_match = CachedSequenceMatcher()
+        self._cached_match = CachedSequenceMatcher(self.scheduler)
 
         for buf in self.textbuffer:
             buf.undo_sequence = self.undosequence
diff --git a/meld/matchers/helpers.py b/meld/matchers/helpers.py
index 548b129..d6f43d9 100644
--- a/meld/matchers/helpers.py
+++ b/meld/matchers/helpers.py
@@ -43,7 +43,13 @@ class CachedSequenceMatcher(object):
     eviction is overly simplistic, but is okay for our usage pattern.
     """
 
-    def __init__(self):
+    def __init__(self, scheduler):
+        """Create a new caching sequence matcher
+
+        :param scheduler: a `meld.task.SchedulerBase` used to schedule
+            sequence comparison result checks
+        """
+        self.scheduler = scheduler
         self.cache = {}
         self.tasks = multiprocessing.JoinableQueue()
         # Limiting the result queue here has the effect of giving us
@@ -67,14 +73,14 @@ class CachedSequenceMatcher(object):
 
     def enqueue_task(self, texts, cb):
         if not bool(self.queued_matches):
-            GLib.timeout_add(10, self.check_results)
+            self.scheduler.add_task(self.check_results)
         self.queued_matches[self.task_id] = (texts, cb)
         self.tasks.put((self.task_id, texts))
         self.task_id += 1
 
     def check_results(self):
         try:
-            task_id, opcodes = self.results.get_nowait()
+            task_id, opcodes = self.results.get(block=True, timeout=0.01)
             texts, cb = self.queued_matches.pop(task_id)
             self.cache[texts] = [opcodes, time.time()]
             GLib.idle_add(lambda: cb(opcodes))


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]