Autor Zpráva
tester
Profil *
Pro účely javascriptu bych potřeboval přijít na to jaké platí priority pro pravidla.
Dozvěděl jsem se že platí toto:

id -> class -> attribute

jenže co když mám například toto:
div#id ul ...
div#id ul li ...
co má větší prioritu?

A dále
div.class
div.class div div.class
co má větší prioritu?

A dále
input.class[name="town"]
div.wrapper input.class[name="town"]
co má větší prioritu?

Mám to brát tak, že si pro každý výskyt id, třídy nebo atributu určím hodnotu, kterou budu přičítat k proměnné?
např. id = 3, class = 2, attr = 1

priorita div.wrapper input.class[name="town"] = 2+2+1 = 5?

A k tomu prvnímu příkladu mě zajímá jestli mám bodovat i to na kolik potomků pravidlo ukazuje:
div#id ul li ...
3 + 1 + 1 ?
div#id ul.list li ...
3 + 2 + 1 ?
div#id ul.list li.item ...
3 + 2 + 1 ?

Takto nebo jinak?
Bubák
Profil
CSS Specificity Calculator, třebas tady: specificity.keegan.st
Ještě pro jistotu, protože se mám dojem, že v tom máš chaos, tak třebas pro div#id ul.list li.item je výsledek 0123, dál už se s tím nic nedělá.
juriad
Profil
Specificity
Spočítáš kolikrát se vyskytuje kdekoli v selectoru:
a) id
b) třída, atributový selektor, pseudotřída
c) element, nebo pseudoelement

Pak vezmeš trojice (a, b, c) a porovnáš je lexikograficky.
Nemůžeš jednoduše přiřadit čisla, protože ani tisíc třid nepřebije jedno id.

div#id ul (1, 0, 2)
div#id ul li (1, 0, 3)
div.class (0, 1, 1)
div.class div div.class (0, 2, 3)
input.class[name="town"] (0, 2, 1)
div.wrapper input.class[name="town"] (0, 3, 2)
div#id ul li (1, 0, 3)
div#id ul.list li (1, 1, 3)
div#id ul.list li.item (1, 2, 3)
Keeehi
Profil
Je to tak jak píše juriad. Pokud si však zavedeš omezení že selektorů z žádné skupiny nebude nikdy více jak sto, můžeš jednoduše použít a * 10 000 + b * 100 + c.
tester
Profil *
juriad:
Díky moc. Ale co to znamená lexikograficky/slovníkově? Tak tomu nerozumím, ale použil bych to co navrhl Keeehi.
juriad
Profil
lexikograficky znamená, že se porovnává odpředu a v připadě shody se pokračuje dále:
(a, b, c) < (e, f, g) pokud: a < e || a == e && (b < f || b == f && c < f)

Pokud máš zaručeno, že existuje N takové že b < N && c < N, pak to lze převést na čísla, jak navrhuje Keeehi: a*N*N + b*N + c
Pokud máš omezení na délku selektoru K znaků, pak máš přirozené omezení N = K/2 pro každou kategorii.
tester
Profil *
A jak do toho všeho zapadá !important? Mám to udělat tak, že poslední !important přebije stejné pravidlo s jakkoliv vysokou prioritou (výpočet dle Keeehi)?
juriad
Profil
tester:
Přečti si okázanou stránku v [#3] juriad.
Bubák
Profil
tester:
Mám to udělat tak, že poslední !important přebije stejné pravidlo s jakkoliv vysokou prioritou (výpočet dle Keeehi)?
Není vhodné používat pravidla s vysokou prioritou, když je potřebuješ přebít, je to pak nepřehledné.
Nevím, co chceš udělat, ale "nikdy není tak zle, aby bylo important", zdroj www.zdrojak.cz/clanky/udrzovatelny-stylopis-poradek-hacky-important
tester
Profil *
Bubák to směruješ nesprávné osobě, dělám jen rozšíření pro prohlížeč které pracuje s webovými stránkami, které jsem já nepsal.


Ta informace na této stránce je chybná, že?

Specificity

[quote]Type selectors (e.g., h1) and pseudo-elements (e.g., :before).[/quote]

Podle MDN tam má správně být ::before


juriad:
Matematika mi nikdy nešla. Budu se držet toho jednoduchého vzorce od Keeehi. Pokud ty podmínky znamenaj omezený počet id, tříd aj. já myslím že ve většině selektorů jich není víc než 20 a stovku to jak věřím nepřekročí. Nebo si už někdy v životě narazil na stránky kde to překročilo stovku?
Bubák
Profil
tester:
Ta informace na této stránce je chybná, že?
Obojí je správně, :before i ::before
tester
Profil *
Dotaz na čárky. Kde všude se používají čárky kromě oddělování pravidel? V kulatých i hranatých závorkách? #a > :matches(.b, #c) , input.class[name="town", value="Praha"] ?
juriad_
Profil *
To co zminujes se tyka CSS4, v CSS3 tam byt nesmi.
Tvuj hlavni problem jsou retezce, protoze ty carky smi obsahovat. drafts.csswg.org/css-values-3/#string-value Pokud se snazis o zpracovani regularnimi vyrazy, tak nemas sanci to udelat spravne, na to potrebujes gramatiky. Dalsi problem jsou komentare.
tester
Profil *
Tak to se dá obejít, že tam dám podmínku že selector nesmí obsahovat "content:"
juriad_
Profil *
Moment. Ted zminujes deklaraci. Ja mluvim o atribute selectoru [data-x="a,b"].
tester
Profil *
Tak budu hledat uvnitř čárku uvozovek "," a zaměním ji za ^. Není to dokonalé, ale provizorně to snad stačí. Zpracovávám document.styleSheets[s].cssRules[r].selectorText ... a nevím ale myslím si že ty komentáře by tam snad už být uloženy nebyly ale nemám to ověřeno. Nemá totiž smysl je ukládat.
tester
Profil *
Pro zajímavost to vložím sem. Funkce je z jedné části hotová a má za cíl získat pozice čárek, které nejsou v uvozovkách ani neleží uvnitř závorek. Ve výsledku je pole, které se pak použije na rozparsování textu se selektory. V druhé části budu dělat vyhledávání konkrétních řetězců v selektoru.

String.prototype.findStrings = function (s = ',') {
  var prev = null, prevEscaped = null, typq = null, 
      typp = null, depRB = 0, depSB = 0;  
  var obj = { length: 0, 
    results: { array: [], A: null, B: null, C: null }
    };
  var action = null;
  if (s.constructor === Array)
    {
    action = 1;
    }
  else
    {
    if (typeof s === 'string' || s instanceof String)
      action = 0;
    }
  if ( action === null)
    return false;
  for (var i=0; i<this.length; i++)
    {
    // pokud není escapovaný:
    if (!prevEscaped)
      { // není escapovaný
      switch (this[i])
        {
        case '\\':
          prevEscaped = true;
          prev = '\\'; // předchozí escapovaný
        break;
        case '"':
          if (!typq)
            {
              typq = '"';
            }
          else if ( typq=='"' ) 
            { // konec uvozovek
              typq = null;
              continue;
            }
        break;
        case "'": 
          if (!typq)
            {
            typq = "'";
            }
          else if ( typq=="'" ) 
            { // konec uvozovek
            typq = null;
            continue;
            }
        break;
        }
      }
    else
      {  // je escapovaný (nedělat nic)
      prevEscaped = false;
      prev = null;
      continue;
      }

    if (!typq) // nejde o blok v uvozovkách
      {
      switch (this[i])
        {
        case '(':
          if (!typp)
              typp = '('; // určí které závorky mají prioritu
          depRB++;
        break;
        case "[": 
          if (!typp)
              typp = '[';
          depSB++;
        break;
        case ")": 
          depRB--;
          if (!depRB)
            {
            if ( typp == "(" )
              {
              typp = null; // konec bloku závorek
              continue;
              }
            }
        break;
        case "]": 
          depSB--;
          if (!depSB)
            {
            if ( typp == "[" )
              {
              typp = null; // konec bloku závorek
              continue;
              }
            }
        break;
        }
      }
    if (typp)    // čárky (s) uvnitř závorek jsou přeskočeny
      continue;
  
    // Následuje blok bez uvozovek a bez závorek

    if (!action) // Separate by string s
      {
      if ( this[i] == s ) 
        obj.results.array.push(i);
      }
    else 
      {
      }    

    } // end for
  
  return obj;
};



var test = '#a > :matches(.b, #c) , input.match(title="\\City \\"of ' + "'" + 'silly' + "'" +' people.", data=' + "'alpha=" + '"' + "string" + '"' + ",beta=2'" + ' value="New York"), article.class1 ul li'; 
var separators = test.findStrings();



V proměnné test jsou blbosti protože jsem tyhle pravidla nikdy nepoužíval, ale principově to snad stačí.
tester
Profil *
Jak se počítá toto?

:matches(section, article, aside) h1 {
    color: red;
}
nemělo by to být jako :2(1 | 1 | 1) 1 = (1)+1 = 2 čili (0,1,2)? prostě že section, article, aside vlastě odpovídá operátoru OR. Takže by se měly počítat jako jeden element?
juriad
Profil
www.w3.org/TR/selectors4/#specificity
Nelze tomu selektoru přímo přiřadit skóre, to skóre se počítá podle toho, jaký element byl nalezený:

:matches(section, article.x.y.z, aside#bla) h1
Pro section h1: (0, 0, 2)
Pro article.x.y.z h1: (0, 3, 2)
Pro aside#bla h1: (1, 0, 2)

Pro :not se jednoduše bere ten nejspecifičtější uvedený v seznamu.
tester
Profil *
Potřeboval bych to zjednodušit, je to moc složitý. Nejlepší by bylo kdybych ignoroval to co je závorkách pokud jim předchází -match, :matches, column

další věc co musím ignorovat je i před závorkou ], (ltr), (rtl), (*-, (active), (valid), (invalid), lang()

Vaše odpověď

Mohlo by se hodit


Prosím používejte diakritiku a interpunkci.

Ochrana proti spamu. Napište prosím číslo dvě-sta čtyřicet-sedm: