title: UICollectionViewCell with UITextView poor scrolling performance (cells don't dequeue)
body: <p>I have a <code>UICollectionView</code> for which cell heights can vary, while the width is full-width (I'm not using a <code>UITableView</code> because I'll need a different layout for iPad in the near future).</p>
  
  <p>Straight to the point first: the weird thing is that dequeueing doesn't really ... dequeue. Cells never really get reused: if there are 40 items, 40 cells are getting initialised, and only then are they reused. I added a <code>print("initialising cell")</code> call in the cell's <code>init</code> method, and it prints as many times as there are cells.</p>
  
  <p>I'm currently using auto-sizing cells, but I've also used the "keep a cell dummy property around to calculate the size" approach, and the outcome was the same. I even pre-calculated all the heights, before showing any data, basically not spending <em>any</em> time in <code>preferredLayoutAttributesFitting</code> or <code>sizeForItemAt</code>.</p>
  
  <ul>
  <li>With self-sizing:
  
  <ul>
  <li>I have set the <code>estimatedSize</code> on the flow layout to <code>CGSize(width: view.width, height: 1)</code> - if I use a "real" average height, the <code>contentOffset</code> jumps around when scrolling;</li>
  <li>I'm overriding <code>preferredLayoutAttributesFitting</code>, and here I'm calling <code>let newAttributes = super.preferredLayoutAttributesFitting(layoutAttributes)</code>, then, before returning them, I'm setting <code>newAttributes.width = layoutAttributes.width</code>, since that's the <code>width</code> I actually need;</li>
  <li>I have also tried not calling <code>super</code>, but <code>layoutIfNeeded</code> and <code>systemLayoutSizeFitting</code>, but the results were the same, even slightly worse
  
  <ul>
  <li>I also tried this, but by returning the cached sizes if they were already calculated, but the results were the same;</li>
  <li>I also tried this, but by calling <code>super</code> as well, but the results were the same;</li>
  </ul></li>
  </ul></li>
  <li>Without self-sizing:
  
  <ul>
  <li>Calculate the heights in <code>sizeForItemAt</code> with my cell dummy;</li>
  <li>Pre-calculate all the heights before displaying any data, and returning those in <code>sizeForItemAt</code>.</li>
  </ul></li>
  <li>Replacing the text view with a label:
  
  <ul>
  <li>if I don't use <code>preferredMaxLayoutWidth</code>, it has the same problem;  </li>
  <li>if I do set it (no matter if in <code>init</code> or <code>layoutSubviews</code>), the problem is there at first, but goes away when reusing starts.</li>
  </ul></li>
  </ul>
  
  <p>The text for the <code>UITextView</code> is 99% of the times under 5-6 rows, and I'm using it for the link detector.</p>
  
  <p>I checked Time Profiler thoroughly, and there <em>are</em> spikes, but not where I'd expect them. It appears that on each spike, the most time is spent in <code>cellForItemAt</code>. </p>
  
  <p>This is an average sample of the spikes:</p>
  
  <ul>
  <li><code>UIView(CALayerDelegate) layoutSublayersOfLayer</code> has a whopping 76% Weight;
  
  <ul>
  <li><code>layoutSubviews</code> has 37%;</li>
  <li><code>cellForItemAt</code> has 26%;
  
  <ul>
  <li>The <code>init</code> of the cell has 18.5%;
  
  <ul>
  <li>The <code>init</code> of my <code>UITextView</code> subclass has a whopping 9.2%, half of the whole cell's init;</li>
  </ul></li>
  <li>My update cell method has 7.4%;</li>
  </ul></li>
  <li><code>_updateConstraintsAsNecessaryAndApplyLayoutFromEngine</code> has 27.7%;</li>
  <li>There's a <code>UIView(internal) _didMoveFromWindowToWindow</code> at 10%;</li>
  </ul></li>
  <li>Some image assignment at 16%, but removing any image assigning code doesn't reduce the stutter whatsoever.</li>
  </ul>
  
  <p>All the relevant code can be found here:  <a href="https://gist.github.com/rolandleth/ab5453b39a2cfe5c83119cb79ac3dc09" rel="nofollow noreferrer">https://gist.github.com/rolandleth/ab5453b39a2cfe5c83119cb79ac3dc09</a></p>
  
  <p>If any other info is missing/is required, please let me know.</p>
  
  <p>Edit: The <code>CreateCell</code> (which has just an <code>imageView</code> and a <code>textView</code>) behaves exactly the same, so the number of subviews/constraints isn't a culprit here - I'm just eliminating any possibility I find.</p>