CSS zakonisht nuk dështojnë menjëherë. Ajo dështon një vit më vonë, kur sistemi është në përdorim real dhe ndryshimet duken të rrezikshme. Stilet fillojnë të ndjehen të rënda.Ju hapni DevTools, hidheni nëpër rregulla dhe përpiquni të kuptoni pse diçka funksionon ashtu siç funksionon.Refactoring ndihet mentalisht taksimi dhe kohëzgjatja kështu që ju shtoni një tjetër override vetëm për të bërë biletën të shkojë. CSS e keqe nuk është vetëm e shëmtuar, është e shtrenjtë.Kjo është arsyeja pse përditësimet e thjeshta të UI marrin tre ditë në vend të tre minutave. Kodi është duke bërë . shumë Shumë vendime të marra herët që janë shumë të vështira dhe shumë të shtrenjta për t’u shfuqizuar. Ky artikull është rreth asaj se çfarë e shkakton këtë dhe si ta shmangni atë.Jo nëpërmjet truket apo mjeteve, por nëpërmjet disa zakoneve që mbajnë CSS të thjeshtë, të lexueshëm dhe të lirë për të ndryshuar si një projekt rritet. Këto janë gjërat që do të doja të kisha mësuar më herët. Fillimi me CSS është gabimi i parë Unë e di se artikulli është në lidhje me CSS, por një nga gabimet më të zakonshme që shoh që bëjnë të rinjtë është të hidhen në një detyrë dhe të ndërtojnë gjithçka në të njëjtën kohë. Zakonisht ata fillojnë me pjesën më të komplikuar, ose pjesën më argëtuese. Unë e marr atë. CSS është joshëse sepse është e prekshme. Qasja më e mirë është të lini CSS anash, të ndaloni, të ngadalësoni dhe të filloni me shënimin. Nëse jeni duke ndërtuar një aplikacion të tërë, filloni me shell-in e faqes. Pikëpamjet, hierarkinë e titujve, seksionet kryesore. Punoni në këtë fillim. Lexoni faqen duke filluar deri në fund. A ka kuptim? Vetëm kaloni në stilet kur e bën. Nëse jeni duke punuar në një veçori më të vogël, e njëjta ide vlen. Vendosni markupin së pari dhe shihni se si përputhet me pjesën tjetër të aplikacionit. Duke filluar me shënimin, ju detyroheni të mendoni për qëllimin, jo për pamjen. Jo atë që ata Me një qasje HTML-First, ju definoni strukturën, kuptimin dhe kufizimet që e mbajnë sistemin të thjeshtë dhe të parashikueshëm. janë Shikoni si CSS should adapt to that, not the other way around. Kur nxitoheni në styling, ju keni tendencë të formoni shënimin rreth shenjave vizuale. Përmbajtje shtesë. Tags të gabuara. Zakonisht ju përfundoni me gjëra që mirë, por janë semantikisht të gabuara, ose të pamundura për të shkallëzuar. Shikoni Duke kryer shënimin së pari, ju bllokoni në një themel të fortë. Aksesibiliteti, përmbledhja e dokumentit, rrjedha e tastierës dhe hierarhia e përmbajtjes zgjidhen kryesisht paraprakisht. Gjithashtu ju ngadalëson në një mënyrë të mirë. Ju kapni rastet e krahut herët. Ju shihni se ku gjërat nuk i përkasin. Ju mund të shtyjë prapa në disa vendime të projektimit. Me pak fjalë: HTML-First bën çdo gjë tjetër të ketë kuptim. Kur CSS bën më shumë se sa mendoni Një tjetër gabim i zakonshëm që shoh në rishikimet e kodit është që juniorët bëjnë Shpesh, pa e kuptuar, le t’ju tregojmë disa shembuj të thjeshtë. shumë Tregoni që dëshironi të përqendroheni në një kolonë përmbajtjeje horizontalisht: .entry-content { max-inline-size: 48rem; margin: 0 auto; /* ❌ Avoid this! */ } Ju vendosni një gjerësi maksimale dhe centralizoni elementin duke përdorur margjinat automatike. Megjithatë, ajo që mund të mos e kuptoni është se ju po vendosni edhe margjinat e sipërme dhe të poshtme në zero. Nëse kjo është e qëllimshme, mirë. Shumica e kohës shkurtesë është përdorur vetëm për shkak se ajo është më e shkurtër. .entry-content { max-inline-size: 48rem; margin-inline: auto; /* ✅ Do this */ } Të njëjtin rezultat. asnjë efekt anësor. më shumë qëllim. Një tjetër shembull i zakonshëm: .button--secondary { background: var(--color--dark-gray); } Kjo vendos ngjyrën e sfondit duke përdorur Por gjithashtu rivendos një grumbull të pronave të tjera të lidhura me sfondin. --color--dark-gray Shumë, në fakt: Imazh i pashembullt, asnjë Pjesëmarrje 0 % 0 % Madhësia e automjetit Fjalë kyçe përsëritje origjina e origjinës padding-box Fjalë kyçe border-box Fjalë kyçe scroll Shumica e kohës, kjo nuk është ajo që ju dëshironi.Kjo mund të çojë lehtësisht në efekte anësore shqetësuese që ju do të duhet të merren me më vonë. Ajo që ju mund të dëshironi në vend të kësaj është kjo. .button--secondary { background-color: var(--color--dark-gray); } E njëjta ide si më parë.Por kirurgjikale.Ndryshoni vetëm atë që në të vërtetë doni të ndryshoni.Përsëri, më shumë qëllim. I njëjti parim vlen për pronat e tjera të shkurtra, të tilla si: të të të Bëni kujdes kur i përdorni ato si shkurtesa ose shmangni përdorimin e shkurtesa krejtësisht. border transform transition font Një shembull më i zakonshëm i të bërit shumë është të jesh shumë specifik shumë herët. a { text-decoration: none; background-image:linear-gradient(to right, currentColor, currentColor); background-position:0%100%; background-repeat: no-repeat; background-size:100%2px; transition: background-size 0.3s; &:hover, &:focus-visible { background-position:100%100%; } } Ky fragment shton një nënshkrim të animuar në lidhje. Problemi është se jo të gjithë Tag është një lidhje teksti. Imazhet mund të jenë lidhje. Avatarët e profilit mund të jenë lidhje. Butonat shpesh janë shënuar si ankore. <a> Papritmas, ky stil global "i zgjuar" është duke shtuar linja të çuditshme 2px nën logon tuaj ose duke thyer gradientët e sfondit në butonat tuaja kryesore. Tani, ju do të shpenzoni pjesën tjetër të projektit duke luftuar kaskaden, duke shkruar stilet "undo" për çdo lidhje jo-tekstore që punoni. visual debt Ju mund ta zgjidhni këtë në disa mënyra.Një opsion është që të synoni lidhjet e tekstit brenda përmbajtjes. .entry-content:is(h1, h2, h3, h4, h5, h6, p, li) > a { /* styles here */ } Por edhe kjo ende mund të jetë shumë e ngushtë ose shumë e gjerë, në varësi të markup. Qasja ime e preferuar është një klasë shërbimi. .has-animated-underline { /* styles here */ } Duke lëvizur këtë në një klasë, ju bëni sjelljen Është e qartë, e qëllimshme dhe, më e rëndësishmja, nuk kërkon që ju të rregulloni gjëra që nuk janë thyer në fillim. opt-in rather than opt-out Kur Mobile është një Afterthought Megjithatë, unë ende shoh se dizajnerët shpenzojnë shumicën e kohës së tyre duke punuar në desktop comps dhe duke paraqitur punën desktop-i parë, me celularët trajtuar si një version të thjeshtë "shtrirë" të desktop. Kjo ende ndihet mbrapa. E duam apo jo, ne përjetojmë internetin përmes një telefoni së pari. që mund të ndryshojë përsëri, por kjo është realiteti sot. Mënyra se si ne ndërtojmë për web duhet të pasqyrojë këtë. Në praktikë, kjo është mënyra se si unë e qasem stilin tani: Vendosni markupin (flasim për të 😉). Ndryshoni shfletuesin në rreth 400px dhe stiloni aplikacionin ose funksionin sikur të mos ekzistonte desktop. Pasi të funksionojë në celular, ndryshoni madhësinë e shfletuesit në desktop dhe bëni një kalim të dytë në stilet. Duke punuar në këtë mënyrë natyrisht ju merr 80% (numri i rastit që duket i drejtë) atje në aspektin e duke e bërë projektin tuaj të arritshëm dhe të gatshëm për ekranet e vogla. Kjo organikisht na çon në implementimin mobile-first. Kur fillova të bëja zhvillimin e uebit, pyetjet e mediave ishin pothuajse një gjë.Ne nuk shfletuam internetin në telefon. Pastaj iPhone doli, dhe pyetjet e mediave u bënë mjeti kryesor për vendosjen e përgjegjshme.Numri i pajisjeve të afta për web ishte i kufizuar, kështu që ju mund të largoheni me një grup të ngurtë të pikëpyetjeve: /* phones */ @media (max-width: 480px) {} /* large phones and small tablets */ @media (max-width: 767px) {} /* tablets */ @media (min-width: 768px) and (max-width: 1024px) {} /* desktop */ @media (min-width: 1025px) {} Vini re se kjo nuk është as mobile-first. qasje të min-width Sot, realiteti është ndryshe.Ka shumë pajisje dhe madhësi të ekranit për të projektuar për të përdorur pikat e ndërprerjes vetëm.Shpesh është më e mençur të mbështetet në mjete që përshtaten natyrshëm në të gjithë gamën. Për shembull: Layouts intrinsike me Grid ose Flexbox Vlerat e lëngshme duke përdorur clamp() për madhësitë e fontit, hapësirat dhe dimensionet Kontejnerët që duan Pyetjet e mediave janë ende të dobishme, por ato nuk duhet të jenë mjeti i parë për të arritur. Nëse një paraqitje funksionon vetëm për shkak të pikat e ndërprera, ajo ndoshta është shumë e ngurtë.Kur punon pa to, pyetjet e mediave bëhen rregullime të vogla, të qëllimshme në strukturën e përgjegjshme, jo themelin. Lufta kundër kaskadës në vend që ta përdorësh atë Kjo është një zonë tjetër ku shpesh shoh inxhinierë të rinj që luftojnë. Shumë korniza CSS dhe zgjidhje ekzistojnë për të zgjidhur një tipar kryesor: kaskada. Dhe unë e kuptoj pse. Nëse ju hidhen në CSS pa shumë përvojë, ajo mund të ndjehen kaotike. Ju shkruani një rregull dhe nuk bën asgjë. Ju e rregulloni atë dhe papritmas diçka tjetër thyen. Përveç kësaj, skedari i stilit të agjentit të përdoruesit po bën gjënë e vet në sfond. Kjo është frustruese sepse CSS nuk është si shumica e gjuhëve të tjera.Në JavaScript, ju mund të krijoni një modul dhe asgjë nuk rrjedh. Ju nuk mund të qaseni në CSS në të njëjtën mënyrë.Nëse provoni, do t'ju kafshojë me të vërtetë fort në fytyrë. Çdo ndryshim CSS jeton në dy fusha në të njëjtën kohë: gjëja që po stiloni dhe pjesa tjetër e sistemit në të cilën rrjedh. Duke u kthyer në shembullin e mëparshëm, ju nuk mund të shkruani vetëm këtë: a { text-decoration: none; background-image:linear-gradient(to right, currentColor, currentColor); background-position:0%100%; background-repeat: no-repeat; background-size:100%2px; transition: background-size 0.3s; &:hover, &:focus-visible { background-position:100%100%; } } Nëse e bëni këtë, kjo do të zbatojë pronat e lidhura me sfondin për çdo ankorë në faqe, edhe nëse ajo ankorë nuk është një lidhje teksti. Shumica e kohës, kjo nuk është ajo që ju dëshironi. Disa inxhinierë mësojnë këtë në mënyrën e vështirë dhe përgjigjen duke shmangur kaskadën krejtësisht, si prekja e një furre të nxehtë si një fëmijë dhe të mësojnë të mos e bëjnë atë kurrë më. Unë mendoj se kjo është një gabim, sepse ajo çon në shumë përsëritje. Këtu është një shembull nga një projekt i kohëve të fundit në të cilin kam punuar. @define-mixin focus-state { &:focus-visible { outline: var(--outline--color) var(--outline--style) var(--outline--width); outline-offset: var(--outline--offset); } } Pastaj ajo u përfshinë në shumë komponente: .button { @mixin focus-state; } a { @mixin focus-state; } .pagination-link { @mixin focus-state; } ...dhe kështu me radhë. Përqendrimi përmbledhjet duhet të duken konsistente në të gjithë një projekt, me shumë pak përjashtime. Në këtë konfigurim, çdo thirrje mixin gjeneron të njëjtën CSS përsëri dhe përsëri. Një qasje më elegante është të mbështetet në kaskadë dhe të përcaktojë këtë globalisht: :focus-visible { outline-color:var(--outline--color); outline-offset:var(--outline--offset); outline-style:var(--outline--style); outline-width:var(--outline--width); } Tani çdo element që merr një gjendje të dukshme të fokusit merr të njëjtin stil të parazgjedhur. Dhe në rastet e rralla ku diçka duhet të jetë e ndryshme, ju mund ta mbivendosni atë në mënyrë lokale: .pagination-link { --outline--offset: -2px; } Kjo është ajo. e thjeshtë, kompakte dhe e parashikueshme. E njëjta gjë vlen edhe për gjëra si të Marrjenëgojë Marrjenëgojë, , dhe stile të tjera që duhet të sillen në mënyrë të qëndrueshme në të gjithë aplikacionin. box-sizing ::selection text-wrap Një kontroll i shpejtë i gojës ndihmon këtu. E njëjta gjë vlen edhe për secilën pjesë, me përjashtime, ndoshta i përket stilit tuaj global. exactly very few Mos e injoroni kaskadën, përdoreni atë në avantazhin tuaj. 5.Specifikimi është aty ku gjërat vazhdojnë të bien poshtë Kjo është zakonisht arsyeja prapa "Kam shkruar CSS-në time, por nuk funksionon". Unë nuk do të shkoj thellë në atë se çfarë është specifikimi. Ajo që ka rëndësi këtu është se specifikiteti i lartë është një nga burimet kryesore të dhimbjes kur punon me bibliotekat e palëve të treta ose me kodin e dikujt tjetër. E bën vërtet mirë Merrni këtë shembull: .layout > :not(.alignleft):not(.alignright):not(.alignfull):not(.alignwide) { max-width: var(--content-width); margin-left: auto; margin-right: auto; } Këtu ne përqendrohemi fëmijët e menjëhershëm të horizontalisht dhe aplikoni një gjerësi max - të gjithë fëmijët përveç të të dhe . .layout alignleft alignright alignfull alignwide Ekzistojnë dy arsye kryesore pse ky kod ka erë. Së pari, ky është një model i listës së zezë.Ne po stilojmë gjithçka Një listë në rritje e gjërave. Problemi është se "gjithçka" gjithmonë ndryshon me kalimin e kohës. Ndërsa projekti rritet, ju pothuajse me siguri do të shtoni më shumë përjashtime. Një ditë ju do të harroni për të shtuar atë, dhe diçka do të thyhet. Përveç Së dyti, çdo selektor që shtoni rrit specifikitetin. Kjo do të thotë që mbizotërimi i saj kërkon një selektor edhe më të fortë, të Ose të përqafosh gjithçka në Me fjalë të tjera, ju rregulloni kompleksitetin me më shumë kompleksitet. 0.5.0 !important @layer :where() WordPress është një shembull i mirë i fillimit pa arkitekturën CSS dhe përfundimit me kaos. body .is-layout-constrained > :where(:not(.alignleft):not(.alignright):not(.alignfull)) { max-width: var(--wp--style--global--content-size); margin-left: auto !important; margin-right: auto !important; } Unë po marr sinjale të përziera këtu.Ne u përkulëm me model, e kuptoi se ishte një ide e keqe, u rikthye me Dhe më pas, të aplikuar Unë jam i sigurt se ka pasur një arsye për këtë, por njeriu... nuk është kaq frustrues. :not() :where() !important Sigurisht që mund të bëni të gjitha këto... Ose ju mund të jeni më të qëllimshëm dhe të blini veten pak paqe: /* 0.1.0 */ .layout > * { max-width: var(--content-width); margin-left: auto; margin-right: auto; } /* 0.2.0 */ .layout > .alignleft, .layout > .alignright { --content-width: var(--content-width--narrow); } /* 0.2.0 */ .layout > .alignwide { --content-width: var(--content-width--wide); } /* 0.2.0 */ .layout > .alignfull { --content-width: var(--content-width--full); } Kjo është më e lehtë për t'u lexuar dhe më e lehtë për të arsyetuar. Përjashtimet janë . 0.1.0 0.2.0 të parashikueshme dhe të qëllimshme. Këtu është një tjetër mënyrë e zakonshme se si specificity rritet pa ndonjë arsye të mirë: /* ❌ combine element with a class ❌ element nested inside the block ❌ modifier nested inside the block */ a.button { &.button__label {...} &.button--secondary {...} } Në këtë shembull: Nëse nuk ka asnjë arsye për të kombinuar një dhe .button, mos e bëni. Nëse nuk ka asnjë arsye për të futur .button__label nën .button, mos e bëni këtë. E njëjta gjë vlen edhe për klasat e modifikuara. Nëse jeni duke dërguar një komponent të ri, kjo është zakonisht ajo që ju dëshironi në vend: /* ✅ no element + class combination ✅ elements and modifiers stay flat */ .button {...} .button__icon {...} .button--primary {...} Këtu është rregulli i gishtit të madh që unë ndjek: Preferoni një selektor të vetëm të klasës sipas parazgjedhjes. Përdorni variacionet e shërbimit në vend të grumbullimit të zgjedhësve. rendi i burimit do t'ju ndihmojë këtu. Mbani specifikimin në 0.1.0 ose 0.1.1. Mos shkoni mbi 0.2.0 në tiparet që dërgoni. Shmangni selektorët #id dhe stilet e linjës në kodin e aplikacionit. Përdorni specifikitet më të lartë vetëm kur tejkaloni kodin e palës së tretë ose të trashëguar që nuk mund të refactor ende. Shënim në të dhe :where() @layer @scope Unë jam plotësisht i vetëdijshëm për këto mjete. Ju mund të zvogëloni specifikimin në zero me Stili i izolimit me , dhe përzgjedhësit e fushës me . :where() @layer @scope Ata janë të fuqishëm dhe kanë vendin e tyre, por ata nuk rregullojnë arkitekturën e keqe. Të njëjtat rregulla specifike vazhdojnë të zbatohen brenda secilës shtresë dhe brenda secilës fushë. Mbani specifikat e ulëta. vetja juaj e ardhshme do t’ju falënderojë.