Saya telah membuat CALayer
dengan menambahkan CATextLayer
dan teks menjadi buram. Dalam dokumen, mereka berbicara tentang "sub-pixel antialiasing", tapi itu tidak berarti banyak bagi saya. Adakah yang punya potongan kode yang membuat CATextLayer
dengan sedikit teks yang jelas?
Berikut teks dari dokumentasi Apple:
Catatan: CATextLayer menonaktifkan antialiasing sub-piksel saat merender teks. Teks hanya dapat digambar menggunakan antialiasing sub-piksel jika digabungkan menjadi latar belakang buram yang ada pada saat yang sama dengan rasterisasi. Tidak ada cara untuk menggambar teks subpiksel-antialiased dengan sendirinya, baik menjadi gambar atau lapisan, secara terpisah sebelum memiliki piksel latar belakang untuk menenun piksel teks. Mengatur properti opacity dari layer menjadi YES tidak mengubah mode rendering.
Kalimat kedua menyiratkan bahwa seseorang bisa mendapatkan teks yang terlihat bagus jika composites
membuatnya menjadi existing opaque background at the same time that it's rasterized.
Itu bagus, tapi bagaimana cara menggabungkannya dan bagaimana Anda memberinya latar belakang buram dan bagaimana Anda merasternya?
Kode yang mereka gunakan dalam contoh Menu Kios adalah sebagai berikut: (Ini OS X, bukan iOS, tapi saya anggap itu berfungsi!)
NSInteger i;
for (i=0;i<[names count];i++) {
CATextLayer *menuItemLayer=[CATextLayer layer];
menuItemLayer.string=[self.names objectAtIndex:i];
menuItemLayer.font=@"Lucida-Grande";
menuItemLayer.fontSize=fontSize;
menuItemLayer.foregroundColor=whiteColor;
[menuItemLayer addConstraint:[CAConstraint
constraintWithAttribute:kCAConstraintMaxY
relativeTo:@"superlayer"
attribute:kCAConstraintMaxY
offset:-(i*height+spacing+initialOffset)]];
[menuItemLayer addConstraint:[CAConstraint
constraintWithAttribute:kCAConstraintMidX
relativeTo:@"superlayer"
attribute:kCAConstraintMidX]];
[self.menuLayer addSublayer:menuItemLayer];
} // end of for loop
Terima kasih!
EDIT: Menambahkan kode yang sebenarnya saya gunakan yang menghasilkan teks buram. Ini dari pertanyaan terkait yang saya posting tentang menambahkan UILabel
daripada CATextLayer
tetapi mendapatkan kotak hitam. http://stackoverflow.com/questions/3818676/adding-a-uilabels-layer-to-a-calayer-and-it-just-shows-black-box
CATextLayer* upperOperator = [[CATextLayer alloc] init];
CGColorSpaceRef space = CGColorSpaceCreateDeviceRGB();
CGFloat components1[4] = {1.0, 1.0, 1.0, 1.0};
CGColorRef almostWhite = CGColorCreate(space,components1);
CGFloat components2[4] = {0.0, 0.0, 0.0, 1.0};
CGColorRef almostBlack = CGColorCreate(space,components2);
CGColorSpaceRelease(space);
upperOperator.string = [NSString stringWithFormat:@"13"];
upperOperator.bounds = CGRectMake(0, 0, 100, 50);
upperOperator.foregroundColor = almostBlack;
upperOperator.backgroundColor = almostWhite;
upperOperator.position = CGPointMake(50.0, 25.0);
upperOperator.font = @"Helvetica-Bold";
upperOperator.fontSize = 48.0f;
upperOperator.borderColor = [UIColor redColor].CGColor;
upperOperator.borderWidth = 1;
upperOperator.alignmentMode = kCAAlignmentCenter;
[card addSublayer:upperOperator];
[upperOperator release];
CGColorRelease(almostWhite);
CGColorRelease(almostBlack);
EDIT 2: Lihat jawaban saya di bawah untuk bagaimana ini diselesaikan. sbg.
sumber
Jawaban:
Jawaban singkat - Anda perlu mengatur penskalaan konten:
Beberapa waktu yang lalu saya belajar bahwa ketika Anda memiliki kode gambar khusus, Anda harus memeriksa tampilan retina dan mengatur skala grafik Anda sesuai dengan itu.
UIKit
menangani sebagian besar ini, termasuk penskalaan font.Tidak demikian halnya dengan
CATextLayer.
Keburaman saya berasal dari memiliki
.zPosition
yang bukan nol, yaitu, saya menerapkan transformasi ke lapisan induk saya. Dengan menyetel ini ke nol, keburaman hilang, dan digantikan oleh pikselasi serius.Setelah mencari tinggi dan rendah, saya menemukan bahwa Anda dapat mengatur
.contentsScale
untukCATextLayer
dan Anda dapat mengaturnya untuk[[UIScreen mainScreen] scale]
agar sesuai dengan resolusi layar. (Saya berasumsi ini berfungsi untuk non-retina, tetapi saya belum memeriksanya - terlalu lelah)Setelah memasukkan ini untuk saya
CATextLayer
, teks menjadi jernih. Catatan - ini tidak perlu untuk lapisan induk.Dan keburamannya? Itu muncul kembali saat Anda memutar dalam 3D, tetapi Anda tidak menyadarinya karena teks dimulai dengan jelas dan saat bergerak, Anda tidak dapat mengetahuinya.
Masalah terpecahkan!
sumber
textLayer.contentScale = [[UIScreen mainScreen] scale];
BTW, saya suka jawaban yang panjang juga :)_textLayer.contentsScale = [[UIScreen mainScreen] scale];
Anda kehilangan "s";)Cepat
Atur layer teks untuk menggunakan skala yang sama dengan layar.
Sebelum:
Setelah:
sumber
Pertama, saya ingin menunjukkan bahwa Anda telah menandai pertanyaan Anda dengan iOS, tetapi manajer kendala hanya tersedia di OSX, jadi saya tidak yakin bagaimana Anda membuat ini berfungsi kecuali Anda dapat menautkannya di simulator entah bagaimana. Di perangkat, fungsi ini tidak tersedia.
Selanjutnya, saya hanya akan menunjukkan bahwa saya sering membuat CATextLayers dan tidak pernah memiliki masalah kabur yang Anda maksud, jadi saya tahu itu bisa dilakukan. Singkatnya, pemburaman ini terjadi karena Anda tidak memposisikan lapisan Anda pada keseluruhan piksel. Ingatlah bahwa ketika Anda mengatur posisi sebuah layer, Anda menggunakan nilai float untuk x dan y. Jika nilai-nilai tersebut memiliki angka setelah desimal, lapisan tidak akan ditempatkan pada keseluruhan piksel dan oleh karena itu akan memberikan efek kabur ini - tingkat yang bergantung pada nilai sebenarnya. Untuk mengujinya, cukup buat CATextLayer dan tambahkan secara eksplisit ke pohon lapisan untuk memastikan bahwa parameter posisi Anda pada seluruh piksel. Sebagai contoh:
Jika teks Anda masih buram, berarti ada hal lain yang salah. Teks buram pada lapisan teks Anda adalah artefak dari kode yang salah ditulis dan bukan kemampuan lapisan yang diinginkan. Saat menambahkan lapisan Anda ke lapisan induk, Anda cukup memaksakan nilai x dan y ke seluruh piksel terdekat dan itu akan menyelesaikan masalah kabur Anda.
sumber
Sebelum menyetel shouldRasterize, Anda harus:
Jika Anda tidak melakukan # 1, maka sub lapisan versi retina akan terlihat buram, bahkan untuk CALayers normal.
sumber
Anda harus melakukan 2 hal, yang pertama disebutkan di atas:
Perluas CATextLayer dan setel properti opaque dan contentScale untuk mendukung tampilan retina dengan benar, lalu render dengan anti aliasing diaktifkan untuk teks.
sumber
Jika Anda datang mencari masalah serupa di sini untuk CATextLayer di OSX, setelah banyak melakukan benturan di dinding, saya mendapatkan teks yang jelas dan tajam dengan melakukan:
(Saya juga mengatur tampilan background layer contentScale menjadi sama).
sumber
Ini lebih cepat dan lebih mudah: Anda hanya perlu mengatur contentScale
sumber