MrBlueSky wrote: > Hi, I've got a ScrolledCanvas object (sc) and have identified an item > on the canvas to which I wish to scroll. I've been reading around and > experimenting but with not much success. > > So far I've managed to get the item's bbox using sc.bbox(item) > And got the proportion of the canvas that's visible using sc.xview() > and sc.yview() > And established the whole canvas bbox using sc.bbox(ALL) > > I've even gone on to use some rudimentary maths to work out whether I > need to scroll, then used: > sc.xview_moveto(itemX) > > But this is all rather messy and I've not yet got it working. > There must be an easier way?! > > Thanks! > > John
Done it! I realised that searching for the way to do this using Tk would give me the clue. For the benefit of any other poor soul who wants to do this, here's my code: def scrollToItem(self, item): """Work out whether the specified item is on display. If it's not, scroll to it.""" # Bounding box for the item xItemMin, yItemMin, xItemMax, yItemMax = self.bbox(item) # Find out what proportion (0.0 to 1.0) of the canvas is # currently on view xViewMinP, xViewMaxP = self.xview() yViewMinP, yViewMaxP = self.yview() # Find out the full extent of the canvas scrollRegionStr = self.component("canvas").cget("scrollregion") scrollRegionElementsStr=scrollRegionStr.split(' ',4) xCanvasMin = float(scrollRegionElementsStr[0]) yCanvasMin = float(scrollRegionElementsStr[1]) xCanvasMax = float(scrollRegionElementsStr[2]) yCanvasMax = float(scrollRegionElementsStr[3]) xRange = float(xCanvasMax - xCanvasMin) yRange = float(yCanvasMax - yCanvasMin) # Work out the canvas coordinates of the bit of the canvas that's # currently on view xViewMin = float(xViewMinP)*xRange xViewMax = float(xViewMaxP)*xRange yViewMin = float(yViewMinP)*yRange yViewMax = float(yViewMaxP)*yRange if xItemMin < xViewMin: newXViewP = float(xItemMin - xCanvasMin)/xRange self.xview_moveto(newXViewP) elif xItemMax > xViewMax: newXViewP = float(xItemMax - xCanvasMin - (xViewMax-xViewMin))/xRange self.xview_moveto(newXViewP) if yItemMin < yViewMin: newYViewP = float(yItemMin - yCanvasMin)/yRange self.yview_moveto(newYViewP) elif yItemMax > yViewMax: newYViewP = float(yItemMax - yCanvasMin - (yViewMax-yViewMin))/yRange self.xview_moveto(newYViewP) (I'd still very much appreciate any critique of this!) John -- http://mail.python.org/mailman/listinfo/python-list