Make a UITableView that is not 100% width - objective-c

I would like to make a grouped UITableView where the cells are not 100% width, this is because I want to show the background, and each cell will have rounded corners.
Sort of like this;
However, I'm not sure how to do this using Storyboard; or is it only something you can do in code?
Ideally, I'd like the whole area scrollable; but make the cells appear less than 100% width

One possibility: you could use a container view. That is, in the view controller where you want this table view to appear, add a Container View in interface builder and set the size however you like. Then add a UITableviewController to your storyboard. Embed the UITableviewController in the Container View by control dragging from the Container View to the UITableviewController and selecting embed.

i think you can use customized cells, set special backgrounds (with rounded corners etc.) and replacing views to have a padding to the borders. but not sure if it really works well. in the example you would have 3 different cells in one section.

Not sure if this is the best solution; the one I have so far is...
In storyboard
Create UITableView as normal as child of a UIView, set up
delegates, data source as required
Add a UITableViewCell to this
Create my own custom subclass of UITableViewCell;
- (void)setFrame:(CGRect)frame {
frame.origin.x += kInset;
frame.size.width -= 2 * kInset;
[super setFrame:frame];
}
-(void) drawRect:(CGRect)rect {
[self.layer setCornerRadius:kCornerRadius];
[self.layer setMasksToBounds:YES];
}
The constants are just any number for now, say 10
Next I ensure my UITableViewCell is pointing to this subclass.
Now my cells appear with a margin and the uitableview itself is 100% width.
I will have to keep playing around with it; maybe there is a better solution

Related

Resize Window and contained NSView based on subviews size

For a MacOS app, I have a Window, containing an NSView; into that view, I want to add a subview with a constant size and height.
When loading the subview programmatically by [myView addSubview:mySubview], I want the NSView *myView that is hosting the subview to change in size so it accomodates the subview, and the window to change in size accordingly; so that the edges of the NSView inside that Window keep the same distance to their surroundings in the Window as before. How do I achieve that most efficiently and which properties do I have to specify in IB to make that work? Do I have to adjust the size of myView and of the Window programmatically by hand or can I achieve this in a more beautiful way?
There are multiple ways to achieve this.
A simple one is to set autoresizingMask the value(s) you want.
The mask you can see in Interface Builder are represented by predefined numbers (NSAutoresizingMaskOptions) that you will combine with bit operation
view.autoresizingMask = NSViewMaxXMargin | NSViewMaxYMargin;
which is simmilar to Autoresizing like in this screenshot of IB
The checkmark on Layout Translates Mask Into Constraints has to be made, either in IB or programmatically so they are used as constraints.
view.translatesAutoresizingMaskIntoConstraints = YES;
The relative positioning to its enclosing superview is defined when the view is instanced with -initWithFrame: with the given frame or with the values set in IB when it creates an instance and inits the UI element via -initWithCoder: .
Be aware this does not stop the autolayout mechanism of IB to warn you that your desired coordinates, sizes and constraints are maybe clashing with constraints.
As suggested by #Willeke, I needed to understand and apply Autolayout. To make it work in IB, I set the autoresizingMask of my subview to stick to all for sides and automatically adjust width and height. Even though it can be done completely in IB, I think programmatically this would be
subview.autoresizingMask = NSViewWidthSizable | NSViewHeightSizeable;
As pointed out by #Ol Sen in his answer, Translates Mask Into Constraints also has to be activated.
To arrange the elements inside that subview that is added programmatically as described in the opening post, I rely on nested stackviews and resize them instead of resizing the parent.
The only problem left is to correctly adjust the frame of the subview to match the parent view before adding it. If this step is left out, the contraints the autoresizing mask of the subview is translated into when adding it will result in the correct resizing behaviour, but wrong margins. The essential code looks like this:
MySubViewController *subViewController = [[MySubViewController alloc] init];
subViewController.view.frame = superView.bounds; // Correct the margins
[superView addSubview:subViewController.view];

Using CATransform3D

I'm trying to make a rotation on a tableview to tilt the table (to give the effect of a 3d text crawl similar to the star wars opening crawl).
After looking around I found this question objective-с CALayer UIView real rotation
and the accepted answer seems to do what I want, however when I apply the code to my TableView it does nothing and the table appears as usual.
This is the code I am copying:
float distance = 50;
CATransform3D basicTrans = CATransform3DIdentity;
basicTrans.m34 = 1.0 / -distance;
_tableView.layer.transform = CATransform3DRotate(basicTrans, M_PI_4, 1.0f, 0.0f, 0.0f);
I'm placing this in my viewDidLoad method after creating my array of Strings (that populate the tableView)
I currently only have three other methods in the Controller:
didReceiveMemoryWarning (automatically addd when project created)
tableView: numberOfRowsInSelection (used for setting up the table view)
tableView: cellForRowAtIndexPath (used for setting up the table view and setting the cells text form the array)
My understanding is that the tableview has a CALayer, and that the CATransform3D manipulates this to give the representation of the view in a 3d space. If my understanding is correct then I don't get why the list is shown normally on screen? I appreciate the numbers my not give the effect I want yet but they should at lest effect the appearance of the tableView on screen.
Also I have imported QuartzCore etc and added it in linked frameworks
Solution is to use the code marked as OLD answer in the the - (UITableViewCell *)tableView: cellForRowAtIndexPath: method after the cell is checked for being null.
Since the approach suggested below has not worked, another thing I would try out is applying the transform to the UITableView's subviews. Actually, UITableView is a UIScrollView, so it is just a container for subviews that make up the real content of the table view. I would try something like this:
for (UIView* subview in tableView.subviews) {
subview.layer.transform = ...;
}
I have never inspected a table view subviews hierarchy, so I cannot say whether this will work or you should rather apply the transform to just one of the subviews, but I hope this can lead you in the right direction.
OLD ANSWER:
You could try setting your table view's layer sublayerTransform instead of `transform':
You typically use this property to add perspective and other viewing effects to embedded layers. You add perspective by setting the sublayer transform to the desired projection matrix. The default value of this property is the identity transform.
(source).
I am suggesting this based on the hypothesis that a UITableView has quite a complex structure in terms of subviews, so transforming just the view's layer might have no effect. I haven't tried it, though, so I cannot guarantee it will work.

Custom scrolling drawing layer over UITableView

I've been struggling with this issue for days, so I hope someone can help me out...
I have a grouped UITableView with several cells. I want to draw some custom graphics above the UITableView that would scroll with the content of the table. Specifically, I want to draw a line with dots, joining the UITableViewCells (across the sections) like this:
Of course if we have more cells than what the screen is capable of displaying, the upper layer with the custom drawing should move with the underlaying cells.
I've tried to subclass UITableView and override it's -drawRect method, but it didn't work. Even if I wouldn't call [super drawRect:rect], the table content displayed without problem.
I've tried to add a new subview to the UITableView, but it changes it's size dynamically when it gets the cells and sections from its datasource... I'm out of ideas...
Although the Web is full of custom UITableViewCell samples, I haven't managed to find anything similiar to my concept...
Can anyone help me how to achieve the above mentioned feature?
First your should subclass UITableView. Then create another UIView and add it as a subView of your custom UITableVIew.
Next override the contentOffset property of the UITableView.
-(void)setContentOffset:(CGPoint)contentOffset
{
[super setContentOffset:contentOffset];
// Custom code here. Update custom subview here.
}
This method will be called as the UITableView is scrolled. You can then adjust the offset of your subview and update its drawing.

UITableView in a UIScrollView - How to make the view scroll, but not the TableView in itself?

Imagine, there is a UIViewController with a UIScrollView in it. At the top of the view there is an UIImageView, some UILabels and other things. Furthermore, there is a UITableView which content is Dynamic Prototypes. I attach a picture to make it clear:
I haven't got a static amount of cells in the UITableView so it could be scrollable. My problem is the following: the UITableView scrolls in itself but I want to scroll the whole View. What is the best possibility to do that?
Possible solutions I've founded today
1) The first thing is: I create a UITableViewController and declare a header section in which I include all my labels, images etc. programmatically (I would love to use the interface builder for that...)
2) Another solution is to calculate the height of the view. I tried the best to do it like this way - but: without success. If this is the best way to do that: Can anybody give an example?
I would ditch the UIScrollView and just use a UITableView. You can add a UIView object as the tableHeaderView of the UITableView just by dragging it in in Interface Builder. Now since everything is part of the UITableView hierarchy, everything will scroll together as expected.
You could also try setting delaysContentTouches to NO on your scrollView. Depending on your setup, this may make the scroll view respond to the touch first instead of the table view.
From Apples UIScrollView Docs:
delaysContentTouches
A Boolean value that determines whether the scroll view delays the
handling of touch-down gestures.
#property(nonatomic) BOOL delaysContentTouches
Discussion
If the value of this property is YES, the scroll view delays handling
the touch-down gesture until it can determine if scrolling is the
intent. If the value is NO , the scroll view immediately calls
touchesShouldBegin:withEvent:inContentView:. The default
value is YES.
You'll have to (as you've mentioned) add the UIView containing the image and buttons to the actual UITableView. Embedding it in the scroll view will produce the undesired behavior that you're seeing.
I would recommend returning the UIView as the header view for the first section of your table view. You can do this by implementing the UITableViewDelegate method:
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section;
If you maintain an IBOutlet to the view containing your image/labels, you can return it here.
this is same demo i hope its helps you from iphone sorce code library
http://developer.apple.com/library/ios/#samplecode/iPhoneCoreDataRecipes/Introduction/Intro.html
thank you

UITableView w/ translucent section headers & different colored section backgrounds

I'm trying to set up a UITableView with elements layered like this:
Specifically, the table has multiple sections and each section has a different background color. To do this I would normally just modify each cell. The tough part is that I'd like the section headers to be translucent. When I do this, the background under the header is the table view's background color when there's no cell under the header. I could of course set the table view's background color, but then the color under each header would be the same.
How would I create a table view like that depicted in the diagram?
UPDATE: To make it absolutely clear, I know how to make a custom header view, and know how to make it translucent using the alpha property. The problem is with what is UNDER the view. I need what is underneath to be the section's background color, not the table view's background color.
There is no exact framework provided solution for this but we can make use backgroundView property. Set it to a scroll view. This scroll view will contain background views for section. Define yourself as observer for the table view's contentSize and contentOffset and alter the scroll view's values parallel to table view's. Get the frame rects for your background views using rectForSection: method and create subviews to the scroll view with appropriate background colors set. This should work to an extent.
The problem with this approach is that that the scroll view will remain static when the table view bounces on the edges. Then there is the case of getting the cell to blend well with this background.
Use a UIImageView in the header and use a (custom) image.
- (UIView *) tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section {
UIView * junkView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:#"headerImageBackground.png"]];
junkView.alpha = .3;
[junkView autorelease];
return junkView;
}