Acquisire testo da immagini con Python – Parte 4 – Esportiamo i dati in CSV

Nell’ultimo post di questa serie abbiamo scoperto come estrarre testo da specifiche parti di un’immagine. Ora, per proseguire nel progetto che ci siamo dati in origine (vedi qui) dobbiamo fare in modo che il dato letto sia correttamente salvato in un file CSV che poi importeremo in seguito. Quindi, ricapitolando: un csv che riporti nella prima colonna il la descrizione del campo come, nome, ruolo e skills e nella seconda colonna il valore di questi campi. Ad esempio nel caso seguente dovremmo partire dall’immagine:

Scheda calciatore

Per ottenere un csv che possa più o meno essere come il seguente:

Esportazione desiderata

Per falro anzitutto creo una funzione Python che mi data un’immagine e le dimensioni in cui è contenuta mi estragga il testo, così evito di dovre riscrivere tutte le volte il codice per estrarle, in più passo come parametro un booleano che, all’occorrenza, mi può anche far vedere l’immagine ritagliata prima di estrarre il testo.

# Function to extract data from a portion of screenshot
def extract_portion_for_csv(x,y,w,h,image,showimg):
    roi = image[y:y+h,x:x+w]
    gray_roi = cv2.cvtColor(roi, cv2.COLOR_BGR2GRAY)
    if showimg:
        plt.imshow(gray_roi, cmap='gray')
        plt.show()
    export = pytesseract.image_to_string(gray_roi)
    return export

Ora che abbiamo una funzione che estrae il testo da specifiche parti dell’immagine si tratta solo di estrarre ognuna di esse definendo punto per punto dove recuperare il dato. Questa è la parte più noiosa in cui, testo per testo dobbiamo recuperare le coordinate. Per meglio organizzare le cose definisco 2 aree: quella in alto che contiene i dettagli anagrafici del profilo ed una sotto che contiene la parte di skills. Questo frammento estrae la parte anagrafica:

def extract_playerdetails_generic(img, showimg, matrix):
    #Date
    txt = extract_portion_for_csv(1225, 135, 148, 27, img, showimg)
    new_row = ["Date", txt]
    matrix.append(new_row)
    #Name 
    txt = extract_portion_for_csv(110, 140, 1240, 100, img, showimg)
    new_row = ["Name", txt]
    matrix.append(new_row)
    #Role
    txt = extract_portion_for_csv(350, 326, 900, 70, img, showimg)
    new_row = ["Role", txt]
    matrix.append(new_row)
    #Birth
    txt = extract_portion_for_csv(350, 400, 900, 70, img, showimg)
    new_row = ["Birth", txt]
    matrix.append(new_row)

E questo frammento invece estrae la parte di skills:

def extract_playerdetails_skills(img,showimg,matrix):
    txt = ""
    ycursor, i =474, 1
    #Left Side Skills
    while i<12:
        #Skill Desc
        #txt += extract_portion_for_csv(150, ycursor, 250, 30, img, showimg) + ","
        txta = extract_portion_for_csv(150, ycursor, 250, 30, img, showimg)
        #Skill Value
        #txt += extract_portion_for_csv(650, ycursor, 50, 30, img, showimg) + "\n"
        txtb = extract_portion_for_csv(650, ycursor, 50, 30, img, showimg)
        new_row = [txta, txtb]
        matrix.append(new_row)
        i=i+1
        ycursor += 34
    #Right Side Skills
    xoffset = 600
    ycursor, i =474, 1
    while i<9:
        #Skill Desc
        #txt += extract_portion_for_csv(150+xoffset, ycursor, 250, 30, img, showimg) + ","
        txta = extract_portion_for_csv(150+xoffset, ycursor, 250, 30, img, showimg)
        #Skill Value
        #txt += extract_portion_for_csv(650+xoffset, ycursor, 50, 30, img, showimg) + "\n"
        txtb = extract_portion_for_csv(650+xoffset, ycursor, 50, 30, img, showimg)
        new_row = [txta, txtb]
        matrix.append(new_row)
        i=i+1
        ycursor += 34
    #Current form
    #txt += "Current form," + extract_portion_for_csv(475+xoffset, 34*8 + 474, 250, 30, img, showimg) + "\n"
    txt = extract_portion_for_csv(475+xoffset, 34*8 + 474, 250, 30, img, showimg)
    new_row = ["Current form", txt]
    matrix.append(new_row)
    #Morale
    #txt += "Morale," + extract_portion_for_csv(475+xoffset, 34*9 + 474, 250, 30, img, showimg) + "\n"
    txt = extract_portion_for_csv(475+xoffset, 34*9 + 474, 250, 30, img, showimg)
    new_row = ["Morale", txt]
    matrix.append(new_row)
    #Physical Condition
    #¶txt += "Physical Condition," + extract_portion_for_csv(250+xoffset, 34*10 + 474, 400, 30, img, showimg) + "\n"
    txt = extract_portion_for_csv(250+xoffset, 34*10 + 474, 400, 30, img, showimg)
    new_row = ["Physical Condition", txt]
    matrix.append(new_row)

Ad una prima analisi possono sembrare complessi ma in realtà non lo sono: sono semplicemente abbastanza ripetitivi. Per ognuno dei testi che dobbiamo estrarre facciamo in modo di specificare le coordinate e mettiamo tutti i testi all’interno di una matrice così da utilizzarla poi nella scrittura del file csv tramite questo frammento:

def write_to_csv (csv_folder, csv_filename, matrixtowrite):
    with open(os.path.join(csv_folder, csv_filename), "w", newline="") as csvfile:
        csv_writer = csv.writer(csvfile)
        # Write data to CSV file
        csv_writer.writerows(matrixtowrite)

Come si può notare riempiamo una variabile matrix, una matrice che poi utilizzero per scrivere il file stesso. Il file generato contiene l’estrazione completa, confrontandola con la desiderata notiamo delle differenze:

Desiderata a sinistra, risultato dell’estrazione a destra

Come si può notare il risultato non è male ma lontano dall’essere perfetto: ci sono molti caratteri speciali che sporcano la lettura come “_”, “*”, “=”. Probabilmente le parti meno riconoscibili sono i trattini “-” e i numeri che hanno un colore del font minore meno pronunciato come quello in Marking 3. Il sistema sembra fare fatica a lavorare dove c’è un contrasto basso. Se guardiamo infatti la figura possiamo notare che tutte le parti che non sono state riconosciute sembrano essere meno evidenti delle altre.

Immagine originale con le parti meno chiare evidenziate in rosso

E’ chiaro che un file così non può essere importato per essere acquisito. L’ideale è capire come migliorare la qualità dell’estrazione, specie per quei caratteri che hanno un basso contrasto. Proviamo a fare una domanda specifica a ChatGPT:

Come posso aumentare l’accuratezza quando il contrasto è basso?

La risposta purtroppo non preannuncia nulla di buono: sembra non sia così semplice . Nel prossimo post analizzeremo le proposte di ChatGPT e proveremo a capire se è possibile migliorare il risultato.

Acquisire testo da immagini con Python – Parte 3 – Lavoriamo un po’ più di fino

Nello scorso post abbiamo visto come estrarre i testi da una schermata. Purtroppo nel caso analizzato abbiamo molti dati dispersi in vari punti e questo ci ha fornito un estratto difficilmente elaborabile.

Schermata Giocatore

Ciò che gioca a nostro favore in realtà è che il formato del dato è quello per tutte le schermate, ciò che cambierà sarà certamente il nome del calciatore, le info anagrafiche ed i valori delle skills. Fortunatamente la struttura ed il posizionamento sono praticamente identici. In soldoni: sappiamo precisamente dove andare a reperire le informazioni, quindi se ci fosse un modo per restringere il campo potremmo estrarre i dati un po’ alla volta selezionando solo ciò che ci serve.

In rosso alcuni esempi di dati da estrarre

E’ chiaro che sarebbe ideale trovare un modo per estrarre solo le aeree in rosso. Ci sarà? Chiediamo a ChatGPT 🙂

Chiedo a ChatGPT

Notare che ho pure scritto wite invece di write, non volontariamente, è solo un typo, ma vediamo come ci risponde.

Codice Python

Bene, ChatGPT ci espone tutto il codice da utilizzare: viene definita una ROI (region of interest) dell’immagine, viene convertita in scala di grigio e poi infine si estrae il testo così come facevamo anche nel caso precedente. Ok proviamo con un esempio: proviamo ad estrarre il nome del calciatore:

# Function to extract data from screenshots and rename files
def extract_data_and_rename(screenshot_folder):
    for file in os.listdir(screenshot_folder):
        print(file)
        if file.endswith(".png"):
            img_path = os.path.join(screenshot_folder, file)
            img = cv2.imread(img_path)
            x, y, w, h = 110, 140, 1240, 100
            #Define ROI
            roi = img[y:y+h,x:x+w]
            gray_roi = cv2.cvtColor(roi, cv2.COLOR_BGR2GRAY)
            plt.imshow(gray_roi, cmap='gray')
            plt.show()
            # Implement OCR to extract data from the image
            extracted_data = pytesseract.image_to_string(gray_roi)
            # Extract relevant information from the data
            print(extracted_data)

Come si può notare ho riprodotto fedelmente quanto indicato da ChatGPT, operando qualche accorgimento:

  • Itero tutti files presenti nella cartella
  • per ognuno di essi fisso x,y,w,h in modo da centrare esattamente il quadro dove sta il nome
  • Estraggo il frammento d’immagine con una scala di grigio
  • utilizzo una libreria per farmi vedere il frammento e capire se è realmente corretto
  • infine faccio scrivere a schermo il testo

Il risultato è questo:

Risultato acqusizione

Questo è indubbiamente il risultato che mi serve: qui il testo è stato estratto correttamente e può ora essere utilizzato per qualcosa di più strutturato. Purtroppo la parte più ostica è quella di estrarre delle coordinate corrette in cui trovare il testo che ci serve. Andando per tentativi diventa quasi impossibile, quindi googlando ho scoperto che è possibile attraverso la libreria pyplot visualizzare l’immagine selezionata, di conseguenza andando per tentativi possiamo definire pezzo per pezzo le aeree in cui operare l’estrazione effettiva. A questo punto non ci resta che definire pezzo per pezzo dove prelevare i dati che ci servono, estrarli ed in qualche modo convogliarli in un file di ouput che possa essere utilizzabile per aggregare i dati dei vari giocatori.

Acquisire testo da immagini con Python – Parte 2 – Tesseract e il primo test di acquisizione

Nel precedente post al fine di provare ad acquisire e aggregare dati provenienti da schermate di un video gioco anni novanta abbiamo chiesto a ChatGPT di darci una mano nel compito essendo neofiti totali. La scorsa volta ci siamo fermati all’installazione di Python, ora passiamo a Tesseract.

Tesseract

Se proviamo a far girare il codice che ci ha fornito ChatGPT scopriamo che manca un prerequisito che è Tesseract. Ma cos’è esattamente?

Ecco la risposta sempre di ChatGPT

La risposta di ChatGPT

Bene, Tesseract è un OCR ed è utilizzato per estrarre testi dalle immagini: quello che mi serve. E’ Open-Source, supporta il riconoscimento in varie lingue ed è molto accurato se correttamente “allenato” (interessante). Può essere facilmente utilizzato attraverso API e nello sopecifico per sessere tuilizzato in Python necessita della libra “pytesseract”. Direi che è esattamente quello che mi serve. Per installare Tesseract basta un semplice comando con brew [1]

brew install tesseract

Inifine come suggerito da ChatGPT installo anche il wrapper per Python.

pip install pytesseract

A questo punto possiamo cominciare a lavorare sul codice Python per capire come adattarlo e ricondurlo a quelle che sono le mie necessità.

Primo ciclo di codice

Apriamo Visual Studio Code e creiamo un file vuoto Test.py e copiamo il codice suggerito nel post precedente quindi lanciamo l’esecuzione dal menu Run > Start Debugging. Questo è il risultato:

Primo lancio

L’esecuzione va in errore e la modalità debug di Visual Studio Code ci aiuta evidenziando dove sta il problema: certo devo fornire un path corretto dove prelevare gli screenshots. Al netto di questo errore comunque il setup sembra corretto possiamo quindi dedicarci alla parte più divertene: vale a dire scrivere il codice. Anzitutto faccio un po’ di pulizia: rimuovo la parte che fa la categorizzazione perchè al momento non so ancora come poterla implementare e lo stesso faccio con la funzione che scrive il csv. Infine fornisco il path dove ho già preparato alcuni screenshots da cui estrarre il testo che mi serve. Il main dopo questo restyling è molto minimale:

# Main function to execute the workflow
def main():
    # Path to the folder containing screenshots
    screenshot_folder = ""/Users/xxxx/ScreenCapture""

    # Extract data from screenshots and rename files
    extract_data_and_rename(screenshot_folder)

Infine mi dedico alla funzione principale extract_data_and_rename che chiaramente itera i files nella cartella e tramite pytesseract estrae il testo dell’immagine. Al momento però mi limito a fare un print del dato estratto:

# Function to extract data from screenshots and rename files
def extract_data_and_rename(screenshot_folder):
    for file in os.listdir(screenshot_folder):
        if file.endswith(".png"):
            img_path = os.path.join(screenshot_folder, file)
            img = cv2.imread(img_path)
            # Implement OCR to extract data from the image
            extracted_data = pytesseract.image_to_string(img)
            # Extract relevant information from the data
            print(extracted_data)

Ok ci siamo se lo lanciamo teoricamente dovrebbe iterare tutti i files png presenti nella cartella e scrivere il contenuto estratto da ognuno di essi a schermo. Per questa prima prova uso una sola immagine:

Immagine sorgente

e questo è ciò che il sistema è stato in grado di interpretare:

Testi estratta dallo screenshot

Beh, diciamo che come primo test è già qualcosa però è evidente che alcuni testi sono stati correttamente interpretati mentre altri vanno rivisti. C’è parecchio da lavorare!

[1] https://pyimagesearch.com/2021/08/16/installing-tesseract-pytesseract-and-python-ocr-packages-on-your-system/

Acquisire testo da immagini con Python – Parte 1 – Cominciamo dalle basi

Qualche giorno fa in questo post [1] parlavo dei temi relativi all’AI e le sue differenze con la pura automazione. Come esempio pratico vorrei provare ad acquisire in automatico i dati provenienti da alcune immagini e convogliare queste informazioni in un excel. Dovete sapere che io sono un grande amante dei giochi degli anni ottanta e novanta. E voi direte che centra questo? Uno dei giochi sul quale ho perso letteralmente le notti quando ero poco più che un teenager era Championship Manager (Scudetto nell’edizione italiana). E’ stato il primo gioco a fornire una simulazione di ottimo livello del manager calcistico. Sono passati gli anni, sarà l’età avanzata, sarà del sano romanticismo, ma ancora questo gioco riesce a toccare corde cui i giochi strafighi di oggi difficilmente riescono a sfiorare. Se non lo conoscete vi invito a fare un giro su questo sito [2] dove potete addirittura scaricare il gioco (nella versione 97/98) e con dosbox [3] un simulatore di DOS potete persino giocarci. Ebbene una delle cose che ho sempre desiderato fare è avere uno scarico dei dati di giocatori e partite per poterli incrociare avere delle statistiche da cui possibilmente evincere trends ed informazioni utili a schierare le formazioni migliori.

Una schermata di esempio è quella delle skills di un singolo calciatore in cui ci sono info anagrafiche e capacità tecniche

Scheda calciatore

Nella fattispecie mi piacerebbe quindi avere in un unico excel le skills per colonna e i giocatori per riga magari indicando anche la data in cui questi dati sono stati raccolti con l’idea di poter monitorare un giocatore anche in giorni diversi nel caso le sue skills migliorino o peggiorino. Detto questo non ho la minima idea di come procedere, quindi chiedo a ChatGPT se mi può dare una mano:

Definizione del requisito

Chiedo scusa per l’inglese maccheronico, ma penso si capisca abbastanza bene. Ed ecco la risposta:

Prima parte della risposta

Bene, diciamo che già la lista delle attività pone sul tavolo alcuni strumenti come Python, OpenCV… In più mi porta cnhe un esempio di codice Python da utilizzare:

import os
import cv2
import pytesseract
import csv
from datetime import datetime

# Function to categorize screenshots based on format
def categorize_screenshots(screenshot_folder):
    # Implement your logic to categorize screenshots
    pass

# Function to extract data from screenshots and rename files
def extract_data_and_rename(screenshot_folder):
    for file in os.listdir(screenshot_folder):
        if file.endswith(".png"):
            img_path = os.path.join(screenshot_folder, file)
            img = cv2.imread(img_path)
            # Implement OCR to extract data from the image
            extracted_data = pytesseract.image_to_string(img)
            # Extract relevant information from the data
            # Rename the file using extracted data and current date
            new_filename = f"{extracted_data}_{datetime.now().strftime('%Y-%m-%d')}.png"
            os.rename(img_path, os.path.join(screenshot_folder, new_filename))

# Function to fill CSV files with data from screenshots
def fill_csv_files(screenshot_folder, csv_folder):
    for file in os.listdir(screenshot_folder):
        if file.endswith(".png"):
            img_path = os.path.join(screenshot_folder, file)
            img = cv2.imread(img_path)
            extracted_data = pytesseract.image_to_string(img)
            # Write extracted data to CSV file
            csv_filename = file.replace(".png", ".csv")
            with open(os.path.join(csv_folder, csv_filename), "w", newline="") as csvfile:
                csv_writer = csv.writer(csvfile)
                # Write data to CSV file
                csv_writer.writerow(extracted_data.split("\n"))

# Main function to execute the workflow
def main():
    # Path to the folder containing screenshots
    screenshot_folder = "path/to/screenshots"
    # Path to the folder where CSV files will be stored
    csv_folder = "path/to/csv_files"

    # Categorize screenshots
    categorize_screenshots(screenshot_folder)

    # Extract data from screenshots and rename files
    extract_data_and_rename(screenshot_folder)

    # Fill CSV files with data from screenshots
    fill_csv_files(screenshot_folder, csv_folder)

if __name__ == "__main__":
    main()

Fantastico: non avevo idea da dove cominicare e ChatGPT mi ha dato delle indicazioni preziose per cominiciare ad approfondire i temi.

Python

Non conosco questo linguaggio se non per sentito dire: non ho mai scritto mezza riga di codice, ma mi sembra di poter dire, dall’esempio che riporta ChatGPT, non sia poi così complesso. Leggendo su Wikipedia [4] tra l’altro scopro che deve il nome ai Monthy Python, già questa la dice lunga. Installarlo non è complesso basta seguire gli step indicati nelle varie guide online (tipo questa [5]). Anzitutto verifico che non sia già presente con questo comando a terminale:

python --version

Nel mio caso il risultato è quello che vedete (io ho installato la versione 3)

Bash

Nel caso non lo abbiate installato potete seguire la guida utilizzando brew

brew install python

Ora che Python è finalmente installato possiamo aprire Visual Studio code e utilizzando il codice che ChatGPT ci ha fornito creiamo un file .py di test da eseguire.

Nel prossimo post vedremo le librerie da utilizzare in Python così come ce le ha suggerite ChatGPT.

[1] https://www.beren.it/2024/02/08/automazione-o-intelligenza-artificale/

[2] https://www.fmscout.com/a-cm9798-v2-project.html

[3] https://www.dosbox.com

[4] https://it.wikipedia.org/wiki/Python

[5] https://www.jcchouinard.com/install-python-on-macos/

Capitolo 9 – Giro di boa

Arriviamo alla gara con il Maccesfield in piena emergenza: Preece non ha ancora recuperato mentre Marshall, Walker e Harsly hanno speso tutto nella gara di mercoledì. Devo fare qualche azzardo. Alla fine opto per mettere due terzini come esterni di centrocampo: Akhmedov a sinistra e Blamey a destra. In attacco ci sono Ormondroyd e Forrester. La partita inizia subito male, dopo venti minuti perdiamo 1-0. Con l’assetto corrente non riusciamo a combinare granchè e ad inizio secondo tempo tolgo il solito apatico Akhmedov ed inserisco Marshall sulla destra spostando Blamey sulla sinistra. Riusciamo a guadagnare campo ma anche l’inserimento di Harsley non dà profitto. Finisce 1-0 ed al solito, loro ci hanno fatto gol con l’unico tiro in porta…. Il mercoledì dopo c’è il Rotherham per il second turno del Windscreen Shield. In attacco è un vero disastro 3 giocatori su 4 sono in infermeria. Perdiamo 3-0 e siamo fuori.

3 Infortunati su 4 in attacco

Il sabato giochiamo il secondo turno di FA Cup e vinciamo 4-1 contro lo Stalybridge. Doppietta di Ormondroyd e reti Preece (MoM) e di Crosby. E’ stata una passeggiata, il prossimo turno ci sarà l’Ipswich Town di prima divisione: sarà dura.

Finalmente un po’ di riposo e qualche giorno in più per recuperare nerbo. Giochiamo l’ultima di andata in casa contro il Bristol C sotto di noi di soli 4 punti. Dominiamo ma non centriamo mai la porta e finisce sostanzialmente 0-0. Senza Harsley e Mainwaring purtroppo se non ci pensa il vecchio Ormondroyd non si riesce mai ad infilare la porta…

Classifica a metà campionato

Capitolo 8 – L’infortunio

Dopo la scorpacciata di partite casalinghe mi preparo alla gara in trasferta sul campo del Barnet. Nel frattempo mi arriva un’offerta per Sertori, la situazione finanziaria è abbastanza disastrosa, ma non posso privarmi del migliore difensore in termini di contrasti e colpi di testa. Tengo duro, rifiuto. Vista la situazione economica rinnovo Marshall, Hope ed Ormondroyd che erano tra i giocatori in scadenza di contratto. Non posso permettermi di perderli. Restano ancora 5 giocatori in scadenza: Walker, Clarke, Housham, Wilcox e Shakespear. Clarke e Housham non saranno di sicuro rinnovati. Wilcox certamente se lo meriterebbe mi lascia solo un po’ perplesso l’età (ormai 34)…

La partita con il Barnet è un mezzo disastro, subiamo con continuità e creiamo pochissimo il risultato è l’unica cosa salvabile: 2-2. Non un gran viatico in vista della prossima trasferta sul campo del Peterborough. Con il Rientro in pianta stabile di D’Auria dietro le punte il duo d’attacco titolare diventa Harsley-Mainwaring. Vinciamo meritatamente 1-0 con un gol proprio di Harsley. Dopo due mesi in cui si è giocato sempre ogni tre giorni finalmente non c’è il turno infrasettimanale. Riceviamo il Darlington e Mainwaring sfodera il primo hattrick della sua giovane carriera: finisce 3-0 con tanto di primo MoM. Ancora una settimana e affrontiamo il Cardiff in trasferta e finisce come spesso è accaduto negli scorsi mesi: 2 tiri 2 goal per loro e noi a sprecare troppo. Il mercoledì successivo nella seconda gara del Windscreen Shield otteniamo un bel 2-2 sul campo del Grimsby che ci consente di chiudere al primo posto nel girone.

Tre giorni dopo giochiamo il primo turno di FA challenge in casa contro Altrincham, la partita è molto chiusa e non ci sono molte occasioni: finisce 0-0 dopo i ’90 minuti. Si dovrà replicare tra una settimana.

Il 14 Novembre riceviamo il Northampton poco sopra di noi in classifica, è una di quelle gare dove serve fare punti per mille ragioni differenti. Dopo tre minuti la tegola: Mainwaring si accascia è strappo (credo) al polpaccio. Il Nothampton domina e vince 4-2. Nel dopo partita la cattiva notizia: Andrew sarà fuori 4 mesi…

L’infortunio di Mainwaring

La prossima gara è la ripetizione della partita con l’Altrincham. Preece è appena tornato dall’infortunio e non ancora in condizione. Sulla sinistra do’ un turno di riposo a McAuley e schiero Akhmedov. Il primo tempo scorre senza molte emozioni. Al 60′ Marshall di testa ci porta in vantaggio. A quel punto l’Altrincham prova la reazione ed un paio di buoni interventi di Colgan blindano l’1-0 finale. Il sorteggio ci arride affronteremo il Stalybridge una squadra delle serie minori: il terzo turno è alla nostra portata.

Capitolo 7 – E’ nata una stella

Il 26 Settembre riceviamo il Lincoln quinto in classifica. Brutto cliente, ma dopo due vittorie in tre partite sarebbe importante mettere in fila due vittorie consecutive. La parita rimane in equilibrio sul filo dello 0-0 ma al 72′ andiamo sotto e non riusciamo più a pareggiare. Ormondroyd da mezza punta al posto dell’infortunato D’Auria è troppo lontano dalla porta. Mainwaring gioca una buona mezzora senza produrre granchè. Si gioca ogni tre giorni e quindi il sabato successivo andiamo a giocare sul campo dell York fanalino di coda. Finisce in goleada, segnano tutti gli attaccanti, Harsley firma persino doppietta e Preece è MoM. Anche Mainwaring rompe il ghiaccio segnando il primo gol tra i professionisti. Risaliamo alla 13ma posizione.

Il mercoledì successivo va in scena la prima gara del girone del Windscreen Shield e giochiamo contro il Preston, squadra di seconda divisione. Vista la minore importanza del torneo rispetto al  campionato opero qualche cambio: posiziono Hope al posto di Wilcox e Mainwaring dall’inizio a fare coppia con Harsley. Dominiamo la gara e soprattutto Mainwaring fa doppietta 2-0. E’ nata una stella? La gara successiva è sul campo del Mansfield. Dopo la pausa rimetto Ormondroyd titolare al centro dell’attacco con Harsley e tengo Walker a centrocampo optando per un classico 4-4-2. Dopo 2 minuti, Ormondroyd si infortunia e tocca dunque a Mainwaring prenderne il posto. Vinciamo 2-1 con rete decisiva proprio di Mainwaring, il migliore in campo è però Colgan. Terza vittoria di fila tra campionato e coppe e soprattutto 5 vittorie nelle ultime 7 gare e decima posizione in classifica ad un soffio dalla zona playoffs, che finalmente sia arrivata la svolta?

Teoricamente il calendario è buono: abbiamo 4 partite casalinghe di fila e con po’ di fortuna potremmo davvero ingranare un buon passo ed attestarci ad una buona posizione di classifica. La prima è contro il Rotherham penultimo e dunque vittima designata. Andiamo sotto quasi subito, Harsley pareggia al 70′ ma 5 minuti dopo Walker commette il più classico degli autogol ed invece di tre punti facili ci ritroviamo con un pugno di mosche: 1-2. Tre giorni dopo è la volta del Brighton settimo in classifica. Partita di grande equilibrio come quella con il Rotherham e ache qui andiamo sotto, recuperiamo con Ormondroyd ma non è sufficiente e subiamo il 2-1 nel finale. La terza gara è contro il Shrewsbury sesto in classifica. Finisce 1-1 con il portiere avversario che prende 9! Di positivo c’è che Mainwaring va ancora a segno. L’ultima della serie di gare casalinghe è contro il Swansea sopra di un paio di punti in classifica. Il clichè è pressochè lo stesso delle altre gare: finisce 0-1 dopo aver avuto anche buone occasioni, probabilmente 1-1 sarebbe stato un risultato più giusto ma il loro portiere Jones è MoM. Così dopo un un punto in quattro partite ci ritroviamo di nuovo al 13mo posto in classifica.

Capitolo 6 – La partita più assurda

Rotto il ghiaccio si spera finalmente di cominciare a macinare qualche bella vittoria e magari tenersi nella parte alta del tabellone con vista playoffs. La gara successiva è in trasferta contro il Rochdale squadra da primi posti e quindi un buon test. Dominiamo letteralmente la gara ma non centriamo ma la porta: 10 tiri fuori ed uno solo nello specchio. Finisce 0-0 tra mille rimpianti. Si poteva vincere ma l’attacco aveva proprio le polveri bagnate. E’ evidente che in attacco serve un impatto maggiore. Devo trovare un buon attaccante, uno che veda la porta con continuità. Il problema sono i soldi, che mancano.

Tabellino dell’incontro con il Rochdale

Il mercoledì successivo riceviamo l’Harlepool ed è ancora 0-0, mentre la partita successiva è un’altra sconfitta per 2-1 sul campo del Bournemouth dove perdipiù riperdiamo Preece questa volta per infortunio. La situazione è parecchio sconfortante in poco più di 20 giorni in cui si è giocato ogni 3 per un totale di 7 gare ne abbiamo perse 4 e vinta una sola. Va così in scena una gara pressochè grottesca contro l’Altrincham. E’ un tiro segno 18 tiri a 3 ma finisce 1-1 nell’unica occasione loro segnano mentre noi sprechiamo l’impossibile e solo l’eterno Ormondoryd ci evita una vera e propria beffa. Un tiro un gol dicevamo e purtroppo in porta c’è chi avevo individuato essere il futuro del ruolo in squadra: Colgan. Evidentemente non è stata una scelta stra-azzeccata. Cmq il messaggio è chiaro: mi serve qualcuno che la butti dentro. Comincio a cercare tra chi costa poco, anzi, praticamente nulla. Nel valutare possibili soluzioni mi imbatto in Andrew Mainwaring, dotato di ottima tecnica e buon tiro. E’ privo di squadra e quindi posso proporgli anche un contratto contenuto.

Andrew Mainwaring

Nel mentre andiamo a giocare sul campo del Notts County in 4 posizione e con velleità assai diverse dalle nostre. Dominiamo la gara e complice anche l’espulsione del portiere avversario non corriamo grossi pericoli. Un bel 2-0 che ci fa tirare una bella boccata d’aria. Ormondroyd è il Man of the Match. Galvanizzati da questa vittoria riceviamo il Leyton Orient e per la gara si aggrega anche Mainwaring appena firmato il contratto. E’ l’ennesima doccia fredda finisce 3-4 e dopo aver subito 3 gol nelle ultime 5 gare ne prendiamo ben 4 tutti in una volta, questa volta in porta c’era Evans ma… il problema del portiere rimane. A fine gara faccio esordire Mainwaring ma solo per uno scampolo di minuti senza peraltro lasciare traccia. La gara successiva è quella che posso definire una delle più assurde abbia mai giocato: la vinciamo finendo la gara in 9 e con gli avversari che sprecano du calci di rigore. Evans si fa cacciare al 4 minuto e dato che in panca non ho altri portieri schiero tra i pali Forrester. Ormondroyd ci porta avanti ed Harsley raddoppia, quando però al 74 rimaniamo in 9 comincio a disperare, fortunatamente Steiner calcia alle stelle anche il secondo rigore. Finisce 1-2 con un po’ di patemi mah… insomma in 9 con un attaccante in porta…

Capitolo 5 – Calcio Mercato

Conscio della situazione abbastanza deficitaria in un po’ tutti i reparti ma in particolar modo la difesa mi concentro nella ricerca di un esterno valido e di un portiere di livello. Purtroppo i soldi sono davvero pochi e devo raschiare il fondo del barile. Dal mercato libero riesco a prelevare (naturalmente a 0) un esterno Nathan Blamey che spero possa dare un valore ad un ruolo dove ho spesso dovuto far giocare Hope (un centrale) per i problemi di rendimento e di infortuni di Neil.

Nathan Blamey

Una settimana dopo è l’ora del portiere, la vera nota dolente di tutta la difesa. L’anno passate ho provato i portieri esistenti in mille salse, per poi finire la stagione con due portieri giovani in prestito. Anche qui, viste le ristrettezze economiche riesco solo a rasciare il barile e acquisto dal Chelsea quello che in tutta probabilità è il 4 portiere Nick Colgan. 59K£ sono comunque una bella cifra per le finanze pessime del club ma serve una svolta anche in quel ruolo. Staccato assegno e contratto folle (fino al 2006!!!) possiamo affrontare gli ultimi giorni prima dell’inizio della stagione.

Nick Colgan

Per il momento pur avendo ben 7 giocatori in scadenza di contratto a fine della prossima stagione non procedo alcuna estensione. Non ci sono, intoccabili, la rifondazione continua. In attacco Stamp ha il contratto scaduto. Il giocatore non ha mai convinto, ma decido per il momento di tenerlo in rosa. Devo cercarmi anche un attaccante, possibilmente buono e che costi poco.

La prima partita della stagione è contro il Cambridge United fuori casa, Preece deve scontare 4 giornate di squalifica della passata stagione e quindi mi tocca schierare Housham uno di quelli che si giocano il rinnovo a fine anno. Perdiamo in maniera abbastanza meritata. Il migliore è Harsley che segna così il primo goal stagionale mentre cominciamo la stagione con un rosso, ad Housham… Non sembra cambiato granchè dallo scorso anno. I nuovi arrivati? Colgan è a casa, con una forma non certo idilliaca dopo aver giocato una gara ufficiale solo dal 1992. Abbastanza buona invece la prestazione di Blamey. Nemmeno il tempo di leccarsi le prime ferite dell’anno che il Glanfor Park si deve vestire a festa per la gara di andata del primo turno di coppa di Lega. Davanti ad un pubblico delle grandi occasioni (9036 spettatori) perdiamo in maniera abbastanza netta: al 24′ già siamo sotto di 3 gol. Ormondroyd segna il goal della bandiera. Colgan prende 3 goal alla sua prima da titolare. Housham stecca anche la seconda…

Fortunatamente la seconda di campionato è in casa contro il Torquay ed è arrivata proprio l’ora di fare qualche punto. Dopo la serata di gala infrasettimanale si gioca in uno stadio praticamente vuoto (880 paganti). Continuo a schierare il 4-4-2 classico, in porta torna Evans. Sulla destra lascio Hope in assenza di alternative visto l’acciacato McAuley. Dopo 8 minuti però deve lasciare il campo e devo schierare Akhmedov. Partita abbastanza equilibrata: Harsley e D’Auria ci portano sul 2-0 ma 83′ Watson accorcia e gli ultimi minuti sono pura sofferenza. Ma la sfanghiamo 2-1 e Wilcox è il migliore in campo.

Capitolo 4 – Fine Stagione

Walker è stato squalificato per una giornata: devo rivedere l’assetto. Prima che chiudesse la finestra di mercato riesco a spuntare un giocatore con il contratto vicino a scadenza Roger Preece. Sembra avere buoni numeri e potrebbe essere un buon titolare immezzo al campo.

Roger Preece

Wilcox ha ripreso ad allenarsi ma la condizione è troppo bassa 75% quindi tengo l’assetto della gara precedente. L’avversario è la prima in classifica, mica poco…  Dopo 20 minuti siamo sotto di due goal e facciamo fatica ad uscire dalla nostra metà campo. Al 22′ Davison commette fallo di mano in area, l’arbitro commina un calcio di Rigore e espelle il giocatore. D’Auria però calcia malamente e se lo fa parare. Male… Dopo qualche minuto prendiamo pure il terzo goal e nel secondo tempo Roberts si fa espellere lasciandoci in 10 e senza portiere… 1-6 un vero disastro… La partita successiva giochiamo contro il Barnet, promuovo Hope titolare e in attacco tengo Forrester e Harsley davanti. Il primo tempo scorre con varie occasioni di Barnet che però non centra mai la porta. Nel secondo tempo sposto avanti il baricentro optando per un 4-4-2 classico. La partita cambia, siamo padroni del campo ed al 55′ Harsley ci porta in vantaggio. Da lì in poi, abbiamo numerose occasioni ma non riusciamo mai a raddoppiare. Al 70′ provo a dare una chance a Akhmedov mettendolo al posto di O’Shea a sinistra… Non brilla granchè. A partita finita al 90′ Forrester fa 2-0. il modulo a rombo contro questo avversario non funzionava meglio, molto meglio il 442.

La partita successiva riceviamo l’Hull terzo in classifica, Roberts è squalificato e rimetto Evans in campo dopo mesi. Wilcox è recuperato e di conseguenza lo rimetto al centro della difesa a far coppia con Sertoni. Lascio Ormondroyd in panchina ancora per la terza volta di fila. La sua forma non è un granchè. Come tutte le partite giocate con le squadre di vertice degli ultimi tempi è una debacle perdiamo 3-0 giocando gran parte della gara in 10 per l’espulsione di Neil. Hope come esterno di difesa gioca una discreta gara. Da tenere in considerazione per il futuro.

Da qui alla fine del campionato perdiamo, male tutte le gare con le squadre forti Exter 0-5 e Chester 1-6 (in casa). Di rilievo solo 8-1 finale sul campo dello Scarborough gia ampiamente retrocesso. Terminiamo il campionato al 15th con 59 punti posto e la seconda peggior difesa, segno che è chiaramente quello su cui più si deve lavorare, a 17 punti dalla zona playoff.