Lisp HUG Maillist Archive

Problem Creating Small Version of Problem in LWL 4.2

I have a larger CAPI based APP running on LWL4.2.  I am having difficulty
creating a small example that exhibits the same behaviour. The smaller
examples I have made all work.

What happens is I have a capi:multi-column-list-panel and
capi:text-input-pane in a interface (call it multi-interface) that is
embedded as a pane in a larger interface (call it top-level-interface).
When I perform a selection from another list-panel in the
top-level-interface there is a some processing and the contents of the
multi-interface is updated depending on the choice.

In the error case I get a beep-pane from the system and the new selections
contents are not shown (or set) in the multi-interface.  On further
selections I still get the beep-pane, BUT, the values displayed in the
multi-interface are for the previous selection.  Its like the
multi-interface is caching the previous values and displaying those on the
next selection.  (The results are one selection out of phase).  I have tried
putting in a call capi:redisplay-interface to attempt to get the cached
values displayed, but it does not help.  When the multi-interface is
displayed outside of the top-level-interface, everything works fine.  It
also works fine when I call the functions to update the mutli-interface
inside the top-level-interface manually (from a listener).

I am at an impasse with what to do.

Would Xanalys be willing to log into the development computer and see the
behaviour for themsleves in an attempt to solve it?

BTW, all the code works on LWW 4.1. (my initial development system).

Wade




Re: Problem Creating Small Version of Problem in LWL 4.2

Unable to parse email body. Email id is 291

Re: Problem Creating Small Version of Problem in LWL 4.2

Thanks Dave,

The good news is that I fixed the problem.  See the end of mail.

----- Original Message ----- 
From: <davef@xanalys.com>
To: <humeniuw@cadvision.com>
Cc: <lisp-hug@xanalys.com>
Sent: Friday, April 19, 2002 7:28 AM
Subject: Re: Problem Creating Small Version of Problem in LWL 4.2


| 
| One possibility is that you are modifying an interface from another
| process. If so, ensure you use CAPI:EXECUTE-WITH-INTERFACE instead.
| 

Tried this but did not help.

| Another possibility is that you've hit a bug. We do have a known
| problem with the process associated with a CAPI:INTERFACE which is
| embedded in another CAPI:INTERFACE. 

Your fix could solve the problem, we will install it when it comes out.

THE FIX

I have fixed the problem.  It seems in the embedded interface case a
call to (setf (capi:text-input-pane-text pane) newstring) forces a
call to the change-callback on the text-input-pane (if any).  This
does not seem to happen when the text-input-pane is not embedded in an
embedded interface.  My change-callback was rejecting the change, the
result being that none of the rest of the interface is updated.

The code change is below.  I introduced a special var called
*special-forced-change* that should be set to t before a call to change
a varchar-pane.  The new change callback detects the forced
change (luckily the call to set the text-input-pane-text causes a
change-callback on the same stack).

;; Buggy Code

(defclass varchar-pane (capi:text-input-pane database-pane)
  ((previous-text :initform nil)
   (previous-caret-position :initform 0))
  (:default-initargs
   #+linux :font #+linux *linux-display-font*
   :change-callback 'varchar-pane-change-callback))

;; this method set-pane-text is called causing the call to varchar-pane-change-callback

(defmethod set-pane-text ((vp varchar-pane) (text string))
  (with-slots (previous-text previous-caret-position) vp
    (setf (capi:text-input-pane-text vp) text
          previous-text text
          (capi:text-input-pane-caret-position vp) 0
          previous-caret-position 0))))

(defun varchar-pane-change-callback (text pane interface caret-position)
  (declare (ignore interface))
  (with-slots (previous-text previous-caret-position editing-enabled) pane
    (cond
     ((string= previous-text text)
      (setf previous-caret-position caret-position))
     (editing-enabled
      (setf previous-text text previous-caret-position caret-position)
      (pane-changed pane))
     (t
      (setf (capi:text-input-pane-text pane) previous-text
            (capi:text-input-pane-caret-position pane) previous-caret-position)
      (capi:beep-pane)))))

;; FIXED CODE

(defvar *special-forced-change* nil)  

(defclass varchar-pane (capi:text-input-pane database-pane)
  ((previous-text :initform nil)
   (previous-caret-position :initform 0))
  (:default-initargs
   #+linux :font #+linux *linux-display-font*
   :change-callback 'varchar-pane-change-callback))

(defmethod set-pane-text ((vp varchar-pane) (text string))
  (let ((*special-forced-change* t))
    (with-slots (previous-text previous-caret-position) vp
      (setf (capi:text-input-pane-text vp) text
            previous-text text
            (capi:text-input-pane-caret-position vp) 0
            previous-caret-position 0))))

(defun varchar-pane-change-callback (text pane interface caret-position)
  (declare (ignore interface))
  (with-slots (previous-text previous-caret-position editing-enabled) pane
    (cond
     ((string= previous-text text)
      (setf previous-caret-position caret-position))
     ((or *special-forced-change* editing-enabled)
      (setf previous-text text previous-caret-position caret-position)
      (pane-changed pane))
     (t
      (setf (capi:text-input-pane-text pane) previous-text
            (capi:text-input-pane-caret-position pane) previous-caret-position)
      (capi:beep-pane)))))





Updated at: 2020-12-10 09:02 UTC