Articles

kotachang / Word-Replacer-Chrome-Extension

Veniți alături de noi pe #hackpack-chrome-ext pe Slack pentru a primi ajutor, pentru a vă petrece timpul și pentru a vă prezenta proiectul!

Prezentare generală

Felicitări! Ați ales acest hackpack și sunteți pe drumul cel bun pentru a construi un produs super tare!

În acest hackpack, veți construi o extensie chrome care înlocuiește conținutul de pe paginile web conform unor reguli personalizabile. Pe scurt, sarcinile dvs. vor include:

  1. Înlocuiți toate instanțele textului „cal” pe toate paginile web.
  2. Înlocuiți tot textul de pe o pagină web în conformitate cu regulile de înlocuire specificate de utilizator.
  3. Înlocuiți toate imaginile de pe o pagină web în conformitate cu regulile de înlocuire specificate de utilizator.

După ce ați terminat aceste sarcini, veți fi construit o aplicație interesantă pe care o puteți utiliza în propriul browser!

Noțiuni introductive

1. Descărcați și dezarhivați codul de pornire.

Ar trebui să aveți în linii mari următoarele fișiere.

hackpack-chrome-ext-master/├── README.md├── manifest.json├── icons│ ├── TreeHacks-white-128.png│ ├── TreeHacks-white-16.png│ ├── TreeHacks-white-19.png│ ├── TreeHacks-white-32.png│ ├── TreeHacks-white-48.png│ ├── TreeHacks-white-64.png│ └── TreeHacks-white-96.png└── src ├── bg │ └── background.js ├── browser_action │ ├── browser_action.css │ ├── browser_action.html │ └── browser_action.js ├── inject │ └── inject.js └── options ├── options.css ├── options.html └── options.js

Alternativ, dacă sunteți un maestru Git, vă puteți sincroniza cu depozitul nostru Git prin HTTPS sau SSH. Notă: Dacă nu sunteți familiarizat cu Git, sau nu știți ce ar face următoarele linii, nu executați următoarele comenzi!

# From Terminal.app or equivalent...# Clone via HTTPS$ git clone https://github.com/TreeHacks/hackpack-chrome-ext.git# or SSH$ git clone [email protected]:TreeHacks/hackpack-chrome-ext.git

Noțiuni introductive

Descărcați Google Chrome

Pentru a construi o extensie Chrome, veți avea nevoie de Google Chrome! Dacă nu ați descărcat deja Chrome, descărcați cea mai recentă versiune aici. Pentru acest hackpack, veți avea nevoie de Chrome versiunea 40 sau mai nouă. Pentru a vă da seama ce versiune aveți, mergeți la chrome://version/ în Omnibar și uitați-vă la linia de sus. Ar trebui să vedeți ceva de genul

Google Chrome48.0.2564.109 (Official Build) (64-bit)

Nu vă faceți griji dacă nu este exact la fel. Atâta timp cât numărul major (înainte de virgulă) este mai mare de 40, sunteți gata!

Load the Starter Code

Chrome livrează de obicei extensiile ca fișiere .crx (similar cu fișierele .zip), ceea ce este grozav pentru distribuție, dar nu atât de grozav pentru dezvoltare. În schimb, îi vom spune lui Chrome să trateze folderul cu codul de pornire ca pe o extensie.

Trebuie să activăm Chrome Developer Settings pentru a construi extensia noastră Chrome.

Pentru a face acest lucru:

  1. Navigați la chrome://extensions în browserul dvs.
  2. Asigurați-vă că este bifată căsuța de selectare Developer mode din colțul din dreapta sus.
  3. Click pe Load unpacked extension… pentru a deschide o fereastră de dialog de selectare a fișierelor.
  4. Navigați până la directorul în care se află fișierele extensiei dvs. și selectați-l.

Ar trebui să vedeți acum un ecran care arată ca cel de mai jos:

Loading Starter Code

Rețineți că este bifată caseta de selectare Developer mode, iar extensia este activată.

În plus, fiți foarte atenți la linkul Reload (Reîncărcare).

În mod implicit, Chrome nu vă va reîncărca extensia în mod automat dacă vă actualizați codul. Astfel, dacă doriți să vă testați extensia, trebuie să reîncărcați extensia înainte de a o testa. În caz contrar, modificările dvs. nu vor fi prezente în extensia activă. Practic, de fiecare dată când faceți o modificare a codului dvs. pe care doriți să o testați live în Chrome, asigurați-vă că reîncărcați extensia folosind acel buton Reload.

Cunoștințe de bază

Pentru acest proiect, veți avea nevoie de anumite cunoștințe de Javascript și extensii Chrome. Codul de pornire ar trebui să aibă suficiente comentarii pentru a explica fiecare fișier, dar dacă doriți să obțineți o înțelegere mai profundă a acestor sisteme înainte de a începe hackpack-ul, am furnizat link-uri către câteva tutoriale mai jos. În special, dacă nu ați mai văzut niciodată Javascript, vă recomandăm să parcurgeți un tutorial Javascript.

Învățați despre Javascript

Ce este Javascript?

JavaScript este un limbaj de scripting pentru calculatoare. Este adesea rulat în aplicații de browser web pentru a crea conținut dinamic, cum ar fi un mesaj pop-up sau un ceas viu. Nu este înrudit cu limbajul de programare Java.

Iată câteva dintre tutorialele noastre preferate de Javascript!

Dacă sunteți un expert în mai multe limbaje de programare înainte, sau dacă știați Javascript și aveți nevoie de o reîmprospătare a sintaxei, consultați Învățați X în Y minute. Acest tutorial durează aproximativ 10 minute.

Dacă nu ați mai văzut (sau nu ați mai auzit de) Javascript până acum, sau dacă doriți un tutorial aprofundat, implicat, care să vă ducă prin Javascript de la zero, vă recomandăm Codecademy. Acest tutorial durează aproximativ 10 ore.

Dacă doriți un tutorial cuprinzător despre tot ceea ce înseamnă Javascript, verificați W3 Schools. Acest tutorial durează aproximativ 10 ore.

Desigur, sunteți liber să vă găsiți propriile tutoriale sau să învățați prin practică.

Noțiuni de bază despre extensiile Chrome

Ce sunt extensiile Chrome?

Extensiile sunt mici programe software care pot modifica și îmbunătăți funcționalitatea browserului Chrome. Le scrieți cu ajutorul tehnologiilor web, cum ar fi HTML, JavaScript și CSS.

Dacă doriți să aflați mai multe despre extensiile Chrome, citiți introducerea Google privind extensiile și prezentarea generală la nivel înalt a Google.

Punctul de control 1: Cal to Butt

După ce am lămurit toate acestea, haideți să începem!

Sarcina A: Citiți codul de pornire

Înainte de a începe să scrieți orice cod, citiți codul de pornire și comentariile pe care vi le-am furnizat. În special, citiți tot src/inject/inject.js, pentru că veți face cele mai multe modificări în acest fișier. Dacă aveți întrebări, aceasta ar fi o ocazie excelentă pentru a cere ajutor pe canalul nostru Slack!

Task B: Update modifyText to replace every instance of ‘cal’ with ‘butt’

Pentru prima sarcină, veți actualiza funcția modifyText din src/inject/inject.js pentru a înlocui fiecare instanță a subșirului ‘cal’ cu șirul ‘butt’ într-un cuvânt dat și va returna șirul modificat. Pentru prima parte, variabila settings va fi nulă.

De exemplu, modifyText('calhacks organizer', null) ar trebui să returneze butthacks organizer.

/* File src/inject/inject.js */function modifyText(text, settings) {// YOUR CODE HEREreturn text;}

Testați-vă metoda vizitând pagina Wiki UC Berkeley sau site-ul CalHacks. Mie personal îmi place pagina Wiki Calculus.

(Sugestie: Consultați documentația despre JavaScript String replace)

Cazuri limită: Ce se întâmplă cu șirul 'iCalendar'? Încercați să actualizați modifyText astfel încât să respecte cazul original al subșirului cal. Adică, 'cal' -> 'butt', dar și 'Cal' -> 'Butt' și 'CAL' -> 'BUTT'. Ce alte scheme comune de casare va lua în considerare funcția dumneavoastră?

Punctul de control 2: Traduceri personalizate

Nu suntem primii care ne gândim la asta. Dacă citiți XKCD, este posibil ca unele dintre acestea să vă pară familiare. Dacă nu ați citit XKCD, ei bine, este timpul să faceți o pauză de codificare și să citiți niște webcomics de modă veche. Iată câteva dintre preferatele noastre.

Batman

s/keyboard/leopard

XKCD Substitutions

Horse

Substitutions 2

Aceste benzi desenate prezintă niște înlocuiri de text grozave, care sunt reproduse aici în format plainxt.

batman -> a man dressed like a batkeyboard -> leopardwitnesses -> these dudes i knowallegedly -> kinda probablynew study -> tumblr postrebuild -> avengespace -> spaaacegoogle glass -> virtual boysmartphone -> pokedexelectric -> atomicsenator -> elf-lordcar -> catelection -> eating contestcongressional leaders -> river spiritshomeland security -> homestar runnercould not be reached for comment -> is guilty and everyone knows itforce -> horsedebate -> dance-offself driving -> uncontrollably swervingpoll -> psychic readingcandidate -> airbenderdrone -> dogvows to -> probably won'tat large -> very largesuccessfully -> suddenlyexpands -> physically expandsfirst-degree -> friggin' awfulsecond-degree -> friggin' awfulthird-degree -> friggin' awfulan unknown number -> like hundredsfront runner -> blade runnerglobal -> sphericalyears -> minutesminutes -> yearsno indication -> lots of signsurgedrestraint by -> drunkenly egged onhorsepower -> tons of horsemeat

Și, bineînțeles, propria noastră

cal -> butt

Vom folosi această „sintaxă săgeată” pentru a reprezenta o regulă de înlocuire a textului pentru restul acestui proiect. În special, vom lăsa

pattern -> replacement

reprezintă transformarea din șirul "pattern" în șirul "replacement". De exemplu, "years -> minutes" înseamnă că înlocuim fiecare instanță a subșirului "years" cu șirul "minutes", iar "minutes -> years" înseamnă că înlocuim fiecare instanță a subșirului "minutes" cu șirul "years".

Sarcina C: Analizați o listă de șiruri de caractere într-o hartă de reguli de înlocuire.

Pentru această sarcină, veți scrie funcția parseSettings din src/inject/inject.js pentru a converti o matrice de intrare de șiruri reprezentând reguli de înlocuire și pentru a produce o hartă de la modele la înlocuitorii lor.

Semnătura funcției este

function parseSettings(lines) { // YOUR CODE HEREreturn null;}

De exemplu,

parseSettings()

ar trebui să returneze

{ "batman": "a man dressed like a bat", "keyboard": "leopard", "force": "horse"}

Vă garantăm că fiecare intrare din matricea de linii conține cel puțin o dată subșirul '->'.

Cazuri limită: Cum procesează funcția dvs. linia "a -> b -> c". O transformă în "a": "b -> c", în "a -> b": "c", sau în altceva? Ce se întâmplă dacă nu există un model (adică linia arată ca "->word" fără text înainte de săgeată)? Ce se întâmplă dacă nu există o înlocuire (de exemplu, linia arată ca "word->" fără text după săgeată)? Ce se întâmplă cu linia cu doar 2 caractere -> (adică nu există text înainte sau după săgeată)? Cum gestionează funcția dvs. spațiile albe? Procesează linia " a -> b " ca "a":"b" sau ca " a ": " b "? Ce se întâmplă dacă există două linii diferite, fiecare cu același model. De exemplu, poate că o linie a tabloului este "force->horse" și o altă intrare este "force->fore"?

Sarcina D: Utilizarea unei hărți de reguli de înlocuire pentru a efectua mai multe înlocuiri de text

După ce am terminat funcția parseSettings, acum trebuie să ne întoarcem la funcția modifyText pentru a utiliza noile noastre reguli de înlocuire! Codul de pornire va prelua valoarea de retur a funcției parseSettings și o va trece în funcția modifyText ca variabilă settings.

Pentru această sarcină, va trebui să actualizați modifyText în src/inject/inject.js, astfel încât toate regulile de înlocuire din hartă să fie puse în aplicare.

De exemplu, dacă harta conține o asociere între "force" și "horse" (adică settings = "horse"), atunci orice instanță a subșirului "force" trebuie înlocuită cu șirul "horse" în text, și așa mai departe pentru restul perechilor pattern: replacement din hartă. Ca întotdeauna, ar trebui să înlocuiți în continuare "cal" cu "butt"

Cazuri de margine: În ce ordine sunt evaluate înlocuirile? Să presupunem că settings = {'train':'bus', 'use':'eat'}. Ce se întâmplă cu șirul "trainer"? Se aplică mai întâi train, ceea ce duce la buser și apoi la beatr? Sau se aplică mai întâi use (fără niciun efect), urmat de train pentru un șir final de buser? La fel ca la punctul de control 1, cum se procedează în cazul textului original? Există o modalitate generală de a respecta cazul originalului?

Utilizarea acțiunii de browser.

Pentru a testa această funcție, v-am pus la dispoziție o acțiune de browser pentru extensie. În colțul din dreapta sus al ferestrei Chrome, va exista o mică pictogramă TreeHacks).

Browser Action Icon

Click pe pictogramă pentru a dezvălui o interfață utilizator în care puteți introduce reguli de înlocuire. Regulile de înlocuire pe care le introduceți vor fi trecute în funcțiile dvs. și aplicate paginii. O captură de ecran este prezentată mai jos:

Browser Action

Textul pe care îl introduceți în această casetă este persistent – nu va dispărea atunci când închideți fereastra pop-up. Dacă vă interesează, codul pentru a face acest lucru este în src/browser_action/. Apăsarea butonului de salvare salvează textul în memoria locală a Chrome, iar apăsarea butonului de ștergere șterge memoria locală.

Punctul de control 3: Înlocuirea imaginilor

Pentru cel de-al treilea și ultimul punct de control, veți extinde funcționalitatea extensiei pentru a permite utilizatorului să specifice înlocuiri de imagini, la fel ca și înlocuirile de text.

Din moment ce aceasta este partea finală a hackpack-ului, vă dăm puțin mai puține îndrumări și ceva mai multă libertate aici. Puteți folosi orice schemă de codificare doriți pentru a reprezenta regulile de traducere a imaginilor. Vă sugerăm să folosiți schema img->https://path.to/image.png pentru a indica faptul că toate imaginile trebuie să fie înlocuite cu imaginea de la https://path.to/image.png. În funcție de modul în care alegeți să vă reprezentați regulile de înlocuire a imaginilor, este posibil să aveți etape distincte față de cele de mai jos.

Tașa E: Găsiți toate imaginile de pe o anumită pagină web.

Dacă vrem să înlocuim toate imaginile de pe o pagină web, va trebui mai întâi să avem toate imaginile de pe acea pagină web. Scrieți o metodă (de ajutor) care să returneze o listă cu toate imaginile de pe o pagină.

Ați putea fi tentați să folosiți jQuery, dar fiți atenți – încorporarea jQuery într-o extensie Chrome nu este ușoară și există o modalitate de a rezolva acest lucru folosind vanilla JS. Dacă aveți nevoie de un indiciu, consultați documentația pentru querySelectorAll.

Task F: Update parseSettings to handle image replacement rules in addition to text replacement rules.

Trebuie să modificați implementarea lui parseSettings pentru a urmări regula (regulile) de înlocuire a imaginilor. Cum veți reprezenta o regulă de înlocuire a imaginii?

Tara G: Actualizați sursa fiecărei imagini de pe pagină.

După ce aveți imaginile și URL-ul de înlocuire, scrieți cod pentru a actualiza imaginea originală astfel încât să afișeze URL-ul țintă. Dacă aveți nevoie de un indiciu, uitați-vă la atributul src de pe imagini.

Task H: We’re All in This Together

Cu aceste metode ajutătoare în mână, implementați funcția replaceAllImages din src/inject/inject.js. Această funcție este apelată imediat după ce înlocuirile de text sunt evaluate. Dacă totul merge bine, ar trebui să puteți introduce o regulă de înlocuire a imaginii în acțiunea browserului și să vedeți că toate imaginile sunt înlocuite!

Felicitări!

Ați reușit! Foarte bine făcut. Ați construit o extensie chrome interesantă care înlocuiește conținutul de pe site-urile web și, în plus, puteți să o păstrați!

Luați-vă un moment pentru a vă relaxa, respirați adânc și priviți înapoi la proiectul pe care l-ați construit. Este foarte impresionant!

Dacă ajungeți în acest punct, veniți pe canalul Slack #hackpack-chrome-ext pentru a sărbători! O meritați.

Extensii

La un nivel înalt, ați construit un sistem care se bazează pe trecerea de mesaje între un dialog popup (acțiunea browserului Chrome) și un script care rulează pe fiecare pagină web. Am folosit acest lucru pentru a transmite informații despre înlocuirea textului și a imaginilor către scriptul de injecție, dar nu există niciun motiv pentru care trebuie să ne oprim aici!

Puteți extinde acest cadru pentru a construi proiecte foarte interesante. Cerul este limita, dar am dat câteva sugestii aici.

  • Corespundeți mai mult decât doar text simplu – potriviți expresii regulate! Extindeți funcționalitatea lui modifyText pentru a trata modelele din settings ca reprezentând expresii regulate, nu doar text simplu.
  • Suportați potrivirea pe selectori de documente din DOM. Potriviți pe nume de etichete (cum ar fi img, dar și a și iframe), sau nume .class, sau poate chiar #ids. Puteți construi suport pentru întregul set de selectori?
  • Nu înlocuiți toate imaginile – înlocuiți doar câteva (să zicem 1%). Ați putea schimba linkurile youtube (tag-uri a cu un href care conține "youtube") în videoclipuri Rick Astley?

Îndepărtându-vă de domeniul înlocuirilor,

  • Permiteți utilizatorului să semnaleze informații către scriptul de fundal. Poate să le ceară numele și să evidențieze cu roșu orice text care conține numele lor.
  • Lăsați utilizatorul să specifice o serie de servere care să acționeze ca proxy-uri. Ați construit un Tor de bază!
  • Permiteți unui utilizator să introducă datele sale de sănătate și sugerați-i (printr-un popup prietenos sau o redirecționare) să facă exerciții fizice în fiecare perioadă de timp pe care o petrece navigând pe un site (tuse reddit tuse).

Acesta este doar începutul. Lăsați-vă imaginația să zburde. Abia așteptăm să vedem ce construiți!”

Diverse

Feedback

Dacă aveți comentarii, pozitive sau negative, contactați-l pe Sam Redmond (@organizer-sam pe Slack) cu feedback! Ne-ar plăcea să auzim ce credeți că este grozav și ce credeți că putem îmbunătăți.

Credit

Creditul pentru idee merge la creatorii extensiei Cloud-to-Butt Chrome Extension, creditul pentru documentația excelentă (din care am furat cu nerușinare o mare parte) merge la contribuitorii Chromium, iar creditul pentru imagini merge la XKCD.

Licență

MIT

.