Le 2 janv. 2011 à 01:33, Christopher Armstrong a écrit :

> On 02/01/2011, at 06:13 AM, Quentin Mathé wrote:
> 
>> May be I'm completely off, but I have the feeling you shouldn't be using 
>> ETIconLayout but just a simple ETColumnLayout. 
>> ETTemplateItemLayout main use is to make a presentation that alters item 
>> properties completely reusable.
>> 
>> Could you describe me precisely the view/presentation you'd like to obtain 
>> from the various perspectives listed below?
>> - Enclosing parent item (fixed size, scrollable etc.)
>> - Item resizing policy
>> - User interaction (click, label editing, drag and drop, rubber-band 
>> selection or not etc.)
>> - Drawn content (text, image, view etc.)
> 
> I suspect this is the case as well. I was trying to get something that I 
> could just create a sort of "template" and then get EtoileUI to clone and 
> reuse for each item.

You can do that with an ETController. You create a controller, declare a 
template with -[ETController setTemplate:forType:] and then set the controller 
on the viewSwitcher item.
-add: or -insert: action methods when invoked on ETController will now use the 
template to create new items. In your case, you have nothing to do, 
-reloadAndUpdateLayout will just create the items transparently and set the 
represented object taken from the 'allViews' array.

See the code suggestion at the end to get an idea.

You can have multiple templates per controller and have specific action methods 
to create the right items. Out of the box, ETController supports two template 
types kETTemplateObjectType and kETTemplateGroupType. Which means -add: creates 
a simple item (kETTemplateObjectType) while -addNewGroup: creates an item group 
(kETTemplateGroupType).

> I was basically trying to build the sort of "task bar" that is needed for 
> project manager so that users can minimise/unminimise windows. I have got it 
> XCBKit to the point where it creates and updates window pixmaps from each of 
> the relevant top-level X11 windows on the screen, and shrinks them down to a 
> size that fits into a 128x128 icon. These will be stored in some sort of 
> array that is updated as windows are minimised/unminimised.
> 
> In terms of the criteria that you list:
> - The parent item should be a narrow (say 96-128px) window on the left or 
> right hand side of the screen. It will be fixed to be the same height as the 
> screen, but the width might be adjustable. At this point, a resizable width 
> isn't important.

ok

> - I don't want the items to be user-resizable - I just want them to fill out 
> as much of the width of the column as possible. It seems to be sensible to 
> constrain the height so that it is no more than 20-50% longer than the width. 
> The pixmaps are copied from the window backing store on the X11 server and 
> also scaled on the server before I pull them using XGetImage() and passing 
> off to GNUstep as a NSBitmapImageRep. It would be great if I can get hints 
> from EtoileUI about what size the layout item's icon will be rendered at, 
> because I could just do the scaling to match that and eliminate 
> double-scaling artefacts.

For the flexible width, I just discovered I forgot to implement any 
autoresizing for item which are not view-backed :-/
By view-backed I mean… By default, ETLayoutItem instances don't have a view, 
they draw in the closest enclosing view which is usually the window content 
view. ETLayoutItem objects becomes view-backed when -setView: is invoked or 
-setLayout: with an ETWidgetLayout.

So I'm going to finish the autoresizing support, and add some mechanism to 
control how the items are sized when the parent is resized. 

-[ETBasicItemStyle rectForImage:ofItem:] should give you a hint about the size 
at which the image will be drawn. Here is an example:

ETLayoutItem *item = [[viewSwitcher items] firstObjectMatchingValue: [allViews 
firstObject] forKey: @"representedObject"];
NSSize imgDrawingSize = [[item coverStyle] rectForImage: [[item 
representedObject] image] ofItem: item];

> - The user just clicks on the items. There is no label or label editing. I 
> don't think they should be rearrangeable via drag and drop, but this 
> shouldn't matter if they are. No "selection" such as single or multi or 
> rubber band selection.
> - The content is just an icon, but it would be nice to have optional labels I 
> think as the window images are rather small and difficult to see on a low-res 
> display.

ok. Here is how you can achieve something close to what you request with a 
ETColumnLayout. There is cosmetic bug that causes the label to be shifted to 
the left when they should be centered time to time. Not sure why… but I'll fix 
it.

        ETLayoutItem *viewItem = [[ETLayoutItemFactory factory] item];

        [viewItem setSize: NSMakeSize(160, 100)];
        /* Delegate the image sizing to the ETBasicItemStyle which ensures its 
fits along with the label.
           ETBasicItemStyle draw the image with a size scaled proportionally as 
ETContentAspectScaleToFit does. */
        [viewItem setContentAspect: ETContentAspectComputed];

        /* This adjusts the ETBasicItemStyle instance set as -coverStyle in 
ETLayoutItem initialization */
        [[viewItem coverStyle] setLabelPosition: ETLabelPositionInsideBottom]; 
// by default it's ETLabelPositionNone
        [[viewItem coverStyle] setLabelMargin: 5];
        [[viewItem coverStyle] setEdgeInset: 6];
        /* Make the label a bit bigger than the default small system font size 
*/
        [[viewItem coverStyle] setLabelAttributes: D([NSFont labelFontOfSize: 
[NSFont systemFontSize]], NSFontAttributeName)];

        viewSwitcher = [[[ETLayoutItemFactory factory] 
itemGroupWithRepresentedObject: [self allViews]] retain];
        [viewSwitcher setSource: viewSwitcher];
        [viewSwitcher setHasVerticalScroller: YES];
        [viewSwitcher setSize: NSMakeSize(180, 700)];

        [viewSwitcher setController: AUTORELEASE([[ETController alloc] init])];
        /* allViews provides instantiated impermanent views that the controller 
will set as represented objects on 
           each item cloned from the template. If an objectClass was passed, 
each item represented object would be 
           instantied from it. */
        [[viewSwitcher controller] setTemplate: [ETItemTemplate 
templateWithItem: viewItem objectClass: Nil] 
                                       forType: kETTemplateObjectType];

        [viewSwitcher setLayout: [ETColumnLayout layout]];
        [[[ETLayoutItemFactory factory] windowGroup] addItem: viewSwitcher];
        [viewSwitcher reloadAndUpdateLayout];

Finally you can set PMWorkspaceManager as the viewSwitcher delegate and 
implements the delegate method  -(void) itemGroupSelectionDidChange: 
(NSNotification *)notif, in order to react to each selection change.
An alternative would be to subclass ETActionHandler and override 
-handleClickItem:AtPoint: or -handleDoubleClickItem:, then set this action 
handler on viewItem. If you don't want to handle double clicks, it's simpler to 
begin with the selection change notification.
I need to add some settings to control whether selection / first responder 
rects should be drawn or not, and make them a bit prettier. Currently a thick 
black outline rect is visible all the time on the selected item.

Cheers,
Quentin.


_______________________________________________
Etoile-discuss mailing list
[email protected]
https://mail.gna.org/listinfo/etoile-discuss

Répondre à