Il Bar dell'Ingegneria

I colori che contano

« Older   Newer »
 
  Share  
.
  1.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    In questo topic mi propongo di scrivere un semplice codice per la conta delle celle colorate in excel.
    Può essere utile in molti casi, qualcuno lo illustrerò.
    Attached Image
    ContaColori

     
    Top
    .
  2.     +1   -1
     
    .
    Avatar

    Member

    Group
    Member
    Posts
    250
    Reputation
    +31

    Status
    Offline
    Afazio due domande: il codice in che linguaggio sarà; e nel caso fosse un un'algoritmo che scansiona righe e colonne metodicamente, c'è un numero massimo di righe e di colonne? Oppure c'è un "barbatrucco" in Excel che mi dà la massima colonna e la massima riga editata?
    Perché se ho tempo potrei tentare uno sviluppo parallelo al tuo, ma in powershell script...
     
    Top
    .
  3.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    CITAZIONE (TDoes @ 7/10/2022, 14:43) 
    Afazio due domande: il codice in che linguaggio sarà; e nel caso fosse un un'algoritmo che scansiona righe e colonne metodicamente, c'è un numero massimo di righe e di colonne? Oppure c'è un "barbatrucco" in Excel che mi dà la massima colonna e la massima riga editata?
    Perché se ho tempo potrei tentare uno sviluppo parallelo al tuo, ma in powershell script...

    L'ambiente di lavoro è un foglio Excel, pertanto il codice è in VBA per Excel.
    Il codice scansione righe e colonne di un range prefissato e conta le celle aventi stesso colore di quelle stabilite in una palette di colori.
    VBA mette a disposizione due funzioni con le quali è possibile conoscere le dimensioni del range, ossia numero di righe e di colonne che lo compongono.

    Il numero delle righe e delel colonne scansionabili viene fissato dall'ambiente stesso. Quindi il numero massimo di righe e di colonne gestite da excel stesso.
     
    Top
    .
  4.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    La procedura che descrivo nasce da un mio reale problema. Dopo aver progettato i muri di sostegno con gabbioni metallici riempiti di pietrame, dovevo procedere al computo del volume di pietrame. Per questo serviva disegnare oltre che le sezioni dei muri alle varie altezze, anche il profilo longitudinale. E trattandosi di strada in pendenza, per forza di cose si dovevano prevedere dei salti di quota delle fondazioni.
    Avevo iniziato a computare i volumi ma dopo qualche centinaia di metri cubi mi sono confuso tra i sassi. Dovevo quindi escogitare un modo che mi permettesse di computare tutti i profili dei muri in progetto.
    Ho pensato quindi di costruire una griglia di celle quadrate in excel, ad ogni cella attribuire le dimensioni (LxH) mentre per la profondità avrei utilizzato un colore.
    In sostanza una cosa cosi:
    Attached Image
    PosizioneProble

     
    Top
    .
  5.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Il prossimo passo è stato quello di catturare l'immagine del profilo del muro, incollarlo sul foglio excel e scalarlo alle stesse dimensioni excel, in modo da poter facilmente colorare la griglia.
    Per uno dei profilo ho ottenuto quanto segue.
    Notare che è stato possibile simulare anche il salto di mezza unita in altezza agendo sulla dimensioni H della palette.
    Adesso era sufficiente riuscire a scrivere il codice della conta e far trascrivere i numeri delle cellette accanto al colore nella palette.
    Una banale moltiplicazione tra il numero e le dimensioni mi avrebbe dato il volume di pietrame necessario.
    Illustrerò il codice stasera o domani.

    Edited by afazio - 7/10/2022, 17:08
    Attached Image
    Posizione2

     
    Top
    .
  6.     +1   +1   -1
     
    .
    Avatar

    Member

    Group
    Member
    Posts
    250
    Reputation
    +31

    Status
    Offline
    Allora ho preso spunto da quello che ha pubblicato Afazio e ho provato a fare il mio programmino script PowerShell per Excel.
    Potrebbe addirittura funzionare sul foglio di Afazio stesso (se si leva il VBScript...), ma finchè Afazio non mette il suo file excel, non posso dirlo con esattezza, quindi metterò i miei files per le vostre prove...
    Io non sono molto preciso, ma penso che basti leggere il codice per capire cosa fa e come... a me funziona tutto, ma non dubito che si possa migliorare è solo per dimostrazione...
    Per farlo girare serve un sistema Windows con Excel installato sopra... come fare a lanciare lo script è descritto all'inizio del codice.
    Poi allegherò anche un file excel, con due definizioni di Range simili a quelle che penso abbia usato Afazio, che sono necessarie per il mio script.
    CODICE
    #############################################################
    ## CONTEGGIO CELLE COLORATE DI UN FOGLIO EXCEL
    #############################################################
    ## Da un'idea di Afazio, ma declinata a modo mio
    #############################################################
    ## 08.ott.2022 - Versione A.00 -  by Tdoes
    #############################################################
    ## v. https://bar-ingegneria.forumfree.it/?t=79336104
    #############################################################

    # PER FAR GIRARE LO SCRIPT BISOGNA:
    # 1. Aprire il programma "Windows PowerShell ISE"
    # 2. nel prompt inferiore posizionarsi nella cartella che contiene lo script, usando il comando:
    #                
    #                cd "nome_percorso_della_cartella_che_contiene_lo_script"
    #                
    # 3. una volta che il prompt è divenuto: PS nome_percorso_della_cartella_che_contiene_lo_script>
    # 4. lanciare il comando:
    #
    #                powershell.exe .\ContaCelleColorate.ps1
    #
    # 5. Nota bene: bisogna avere le autorizzazioni per l'esecuzione di script powershell ps1.
    #       Set-ExecutionPolicy Unrestricted
    # 6. Consultare https://www.robadainformatici.it/abilitare-esecuzione-script-powershell/ per delucidazioni sul comando precedente
    #    Attenzione: il comando "Unrestricted" potrebbe rendere il tuo PC vulnerabile
    #############################################################
    #A.00: prima versione
    #
    #
    ##############################################################à
    $debug = $true; # modalità di debug 'manuale'
    # puliamo la console
    Start-Sleep -Milliseconds 150; # ms
    cls
    #
    if($debug) {"STEP 001 : avvio script"}
    # avvisiamo l'utente
    if($debug) {"STEP 002 : preparo e visualizzo il MessageBox (non sempre è in primo piano!)"}
    Add-Type -AssemblyName PresentationCore,PresentationFramework
    Start-Sleep -Milliseconds 150; # ms
    $Result = [System.Windows.MessageBox]::Show("Vuoi selezionare il file Excel che contiene le celle colorate da contare?","ContaCelleColorate",[System.Windows.MessageBoxButton]::YesNoCancel,'Question')
    if($debug) {"STEP 003 : hai risposto " + $Result + " al MessageBox"}
    if($Result -ne "Yes") {
       if($debug) {"STEP 004A: lo script è terminato."}
       Return #termino lo script
       }
    if($debug) {"STEP 004B: lo script prosegue..."}
    # Vediamo di aprire il dialogo per selezionare il file excel dalla cartella documenti:
    Add-Type -AssemblyName System.Windows.Forms
    $FileBrowser = New-Object System.Windows.Forms.OpenFileDialog -Property @{
       InitialDirectory = [Environment]::GetFolderPath('MyDocuments')
       Filter = 'Excel Worksheets 2007(*.xlsx)|*.xlsx|Excel Worksheets 2003(*.xls)|*.xls'
       }
    $DialogExitStatus = $FileBrowser.ShowDialog()
    if($DialogExitStatus  -ne "Cancel") {
       if($debug) {"STEP 005 : Hai scelto di aprire: " + $FileBrowser.FileName}
       }
    # Apro Excel
    $XL = New-Object -comobject Excel.Application;
    $XL.Visible = $true;
    # Get Windows handle of the application
    $excelWinHwnd = $XL.Hwnd
    # Get Process Id of the application
    $process = Get-Process Excel | Where-Object {$_.MainWindowHandle -eq $excelWinHwnd}
    $excelProcessId = $process.Id
    # put excel window in foreground
    $WSShell = New-Object -ComObject WScript.Shell;
    $WSShell.AppActivate("Excel") | Out-Null;
    Start-Sleep -Milliseconds 150; # ms
    # Apro il file excel scelto
    $WB = $XL.Workbooks.Open($FileBrowser.FileName)
    # seleziono il foglio di lavoro (spreando per semplicità che sia l'ultimo creato)
    if($debug) {"STEP 006 : Seleziono l'ultimo foglio di lavoro creato"}
    $WS1 = $XL.Worksheets.Item($XL.Worksheets.count)
    $WS1.Activate();
    # Cerco il range Area
    $RangeArea = $WS1.Range("Area")
    # Cerco il range IndiceColori
    $RangeIndiceColori = $WS1.Range("IndiceColori")
    # vediamo di contare le celle
    [System.Int64] $iCountTotColorate=0;
    [System.Int16] $iCountAcc=0;
    #Azzero la colonna successiva al RangeIndiceColori
    foreach($cell in $RangeIndiceColori){
       $WS1.cells.item($cell.Row,($cell.Column+1)) = 0;
       }
    if($debug) {"STEP 007 : Azzero i conteggi nella colonna successiva all'indice colori"}
    # conto tutte le celle che NON hanno fondo trasparente, ma uguale all'indice colori se valorizzato
    foreach($cellA in $RangeArea) {
       if($cellA.Interior.ColorIndex -ne -4142){
           $iCountTotColorate++
           foreach($cellB in $RangeIndiceColori){
               if($cellA.Interior.ColorIndex -eq $cellB.Interior.ColorIndex){
                   $iCountAcc = ($WS1.cells.item($cellB.Row,($cellB.Column+1)).Value2);
                   $WS1.cells.item($cellB.Row,($cellB.Column+1)) = ($iCountAcc + 1);
                   }
               }
           }
       }
    #$WS1.Cells.item(7,'B').Interior.Color #16777215 che numero é?
    #$WS1.Cells.item(7,'B').Interior.ColorIndex #-4142
    if($debug) {"STEP 008 : Conteggio effettuato"}
    # scrivo il risultato in AX19 (dove AX = 50)
    $WS1.cells.item(19,51) = "Conteggio automatico di tutte le celle colorate";
    $WS1.cells.item(19,50).HorizontalAlignment = -4108; # $xlHAlignCenter
    $WS1.cells.item(19,50).VerticalAlignment = -4108; # $xlHAlignCenter
    $WS1.cells.item(19,50).NumberFormat = "#.##0,00 €\/\T\o\n"; # Euro/Ton
    $WS1.cells.item(19,50) = $iCountTotColorate;
    # faccio la somma della colonna in AX18 (dove AX = 50)
    $WS1.cells.item(18,50).Formula = "=sum(AX6:AX17)";
    $WS1.cells.item(18,51) = "Somma delle celle colorate";
    if($debug) {"STEP 009 : Scrivo i risultati del conteggio"}
    # salvo in un nuovo file:
    # tolgo l'estensione
    [System.string]$NewFileName = $FileBrowser.FileName;
    [System.string]$NewFileDirN = $FileBrowser.FileName;
    $NewFileDirN = (Get-Item $FileBrowser.FileName).DirectoryName
    $NewFileName = (Get-Item $FileBrowser.FileName).Basename;
    # aggiungo una data
    [System.string]$CurrentDateTimeStr = Get-Date -Format "yyyy-MM-dd_HHmmss";
    # salvo il file
    [System.string]$FilePathXLSX = $NewFileDirN + "\" +$NewFileName + "_" + $CurrentDateTimeStr + ".xlsx";
    #$FilePathXLSX
    $WB.SaveAs($FilePathXLSX)
    if($debug) {"STEP 010 : Ho salvato in un nuovo file: " + $FilePathXLSX }
    # per chiudere bene excel:
    #$WB.Close();
    #$XL.Quit();
    #$null = [System.Runtime.Interopservices.Marshal]::ReleaseComObject($XL)
    if($debug) {"STEP 011 : Fine."}

    L'unica cosa che non capisco è come mai il MessageBox che ho inserito nel codice a volte non va in primo piano... per cui può sembrare che lo script non stia facendo nulla... ma cercate una finestrella in secondo piano e premete SI...
    File Allegato
    ContaCelleColorate.ps1
    (Number of downloads: 13)

     
    Top
    .
  7.     +1   +1   -1
     
    .
    Avatar

    Member

    Group
    Member
    Posts
    250
    Reputation
    +31

    Status
    Offline
    Questo è il foglio excel che va in tandem col mio codice.
    Voi potete modificare i colori nel range Area e nel range IndiceColori. In teoria si possono modificare anche le dimensioni dei range stessi, il codice dovrebbe continuare a funzionare.
    Lo script richiede di selezionare il file excel che allego quì, oppure un qualunque excel che abbia i due ranges sopracitati (almeno in teoria!), l'unica cosa che non funzionerà sono i totali: perché vengono scritti in celle non dinamiche ...
    File Allegato
    FoglioColori.xlsx
    (Number of downloads: 15)

     
    Top
    .
  8.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    CITAZIONE (TDoes @ 8/10/2022, 00:23) 
    Allora ho preso spunto da quello che ha pubblicato Afazio e ho provato a fare il mio programmino script PowerShell per Excel......

    Accipicchia. Ma tu qui fai sul serio.
    A breve pubblico il mio foglio.
     
    Top
    .
  9.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Prima di passare al codice vediamo i nomi attribuiti alle aree del foglio excel.
    Sono tre:
    - Area -> l'insieme delle celle dove simuliamo il profilo del muro. Le dimensioni delle cellette sono quelle indicate nella palette dei colori. Lo standard è quello di stabilire che ogni celletta abbia base L pari ad 1.00 m (poco importa se poi le dimensioni delle gabbie sono diverse, sono sempre riconducibili a multipli di 1.00 m) ed altezza H pari a 1.00 m (ma possiamo anche inserire moduli di altezza diversa, scrivendolo sempre nella palette). ed infine la profondità indicata con B è proprio quella attribuita al colore.
    Sta a noi poi organizzare il tutto in maniera che sia coerente col progetto.
    ----
    - IndiceColore -> è la colonna dove preventivamente stabiliamo i colori che vogliamo utilizzare. Basterà poi copiare la celletta col colore che ci interessa e incollarla nelle celle dell'area da colorare. In questo modo siamo certi della corrispondenza tra i colori. Vi ricordo che la gamma completa dei colori prevede una varieta di 256*256*256=16777216 colori.
    ----
    Dati- > sono l'insieme tra la palette dei colori e la colonna accanto dove scrivere la conta. Qui avrei potuto inserire anche le rimanenti colonne con le dimensioni e col volume per far fare la moltiplicazione direttamente al codice.
    ---
    Ha ben compreso TDoes semplicemente leggendo l'immagine che avevo postato.
    C'è da dire che l'idea si può sfuttare per parechie altre applicazioni e che le dimensioni non sono vincolanti. per esempio se volessimo simulare meglio le mezze altezze o i quarti di altezza, basterebbe infittire la griglia, ed attribuire le dimensioni volute. Nel caso in esame l'infittimento della griglia per simulare i salti di mezzo metro, avrebbe comportato per me un maggiore onere di pittura, vanificando l'agevolazione che avevo pensato.

    ---
    In conclusione: io ho lanciato l'idea , chiunque può farla sua e adattare il tutto ad altre possibili applicazioni.
    Debbo però confessare che l'idea originaria leggermente diversa (era basata non sui colori ma sui numeri, ossia ogni celletta rappresentava un'area di 1.00 m², ed entro la celletta si scriveva il valore della profondità), è del mio simpatico collega Giacomo.
    Attached Image
    NamedRanges

     
    Top
    .
  10.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Ecco il codice, pochissime righe.
    Se facciamo il confronto tra le righe del codice di Tdoes e queste, diciamo che "non ce n'è per nessuno" anche se il codice di Tdoes contiene almeno un 60% di righe di commenti (graditissime).
    CODICE
    Sub ContaColori()

    Dim C_0 As Range
    Dim C_1 As Range
    Dim i As Integer
    Dim j As Integer

    j = 1
    For Each C_0 In Range("indicecolori")
       i = 0
       For Each C_1 In Range("Area")
           If C_1.Interior.ColorIndex = C_0.Interior.ColorIndex Then
               i = i + 1
           End If
       Next
       Range("Dati").Cells(j, 2) = i
       j = j + 1
    Next

    End Sub
     
    Top
    .
  11.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Ed ecco il file excel col codice all'interno.
    Può essere utilizzato e modificato liberamente.
    File Allegato
    ConteggioColori.xlsm
    (Number of downloads: 16)

     
    Top
    .
  12.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Commento al codice.
    - Nel codice non vengono lette le dimensioni dell'area da scansionare, ma invece si è fatto ricorso al costrutto For Each -> per ogni cella contenuta in.....
    Questo comporta il fatto che i range nel foglio, sia quello da colorare e sia l'indice dei colori, potrebebro anche essere dei range "disgiunti" ossia formati da diverse aree del foglio e non per forza di forma rettangolare.
     
    Top
    .
  13.     +1   -1
     
    .
    Avatar

    Member

    Group
    Member
    Posts
    250
    Reputation
    +31

    Status
    Offline
    Diciamo che in pratica il mio codice e quello di afazio sono quasi identici, perché il "core" del mio, come quello di afazio, si basa su due foreach nested uno nell'altro. Io ho aggiunto un filtro che salta le celle con fondo trasparente.
    Tutto il resto del mio codice non è strettamente necessario, però l'ho messo per farvi intuire le potenzialità del powershell.
     
    Top
    .
  14.     +1   +1   -1
     
    .
    Avatar

    Member

    Group
    Member
    Posts
    250
    Reputation
    +31

    Status
    Offline
    Un po' come avevo previsto il mio script funziona anche sul file di Afazio...
    Lo scoglio principale è che bisogna bypassare il filtro dell'OpenDialog che non mostra i file *.xlsm, sapete come fare vero? Basta digitare *.* (o meglio *.xlsm) seguito da INVIO nel campo 'Nome file:' ovvero nel campo dove dovrebbe apparire il nome del file da aprire...

    Una considerazione generale: perché usare un PowerShell script, dove si può usare un VBScript integrato nel file Excel? Non ha molto senso infatti.

    Però se pensate di dover interagire con altri files esterni ad Excel, ad esempio nel mio caso sono dati contenuti in uno o più DB SQL, vi assicuro che diventa più pratico, perché infinitamente più flessibile che utilizzare i tools di importazione dati di Excel.
    Immaginate poi di dover inviare il file così elaborato via mail, altra cosa facilmente fattibile con PowerShell...
    Poi più in generale con PowerShell potete fare tutto ciò che fate col vostro PC.
    Infine un PowerShell script può essere invocato all'interno di uno scheduled task (un'attività pianificata) di Windows...
    Combinate tutto quello che vi ho detto e chiaramente potete capire che una macro o uno script in Excel al confronto sono molto limitati!

    Edited by TDoes - 8/10/2022, 17:42
    Attached Image
    risultato del mio script

     
    Top
    .
  15.     +1   -1
     
    .
    Avatar

    Advanced Member

    Group
    Administrator
    Posts
    8,163
    Reputation
    +294

    Status
    Offline
    Butto giù altra idea che mi è balenata in testa mentre smanettavo col mio file recuperato sulle isobare e cedimenti.
    Penso basti questa immagine per esplicarla.
    Suddividiamo il foglio excel in tante piccole cellette quadrate o rettangolari di dimensioni fissate (per esempio 25 cm x 25 cm o meglio 25*50 cm). Fissate le dimensioni e fissato un sistema di riferimento xz con origine in alto a sinistra e verso positivo delle x verso destra e delle z verso il basso, il baricentro di ogni celletta è ben definito dalle coordinate x,z che faremo corrispondere a due contatori i,j di riga e colonna.
    Stabilite le forme di carico agenti sulla superficie limite, con le formule di Boussinesq integrate, siamo in grado di determinare l'incremento tensionale in qualsiasi celletta del range prestabilito.
    Adesso fissiamo una palette di variazione dei colori, dal colore iniziale (R1G1B1) al colore (R2G2B2) finale.
    Cosi siamo in grado di attribuire ad ogni incremento tensionale un colore diverso e colorare di conseguenza la corrispondente celletta.
    ---
    Riuscendo nel proposito simuleremo alla grande ed in maniera casereccia i blasonati programmi che determinano e disegnano i bulbi delle presisoni.

    Edited by afazio - 9/10/2022, 11:52
    Attached Image
    Idea

     
    Top
    .
33 replies since 7/10/2022, 12:39   1908 views
  Share  
.