C# wczytywanie obrazów za pomocą textbox-a

0

Witam,

mam problem z moim programem. Chciałbym, żeby po wpisaniu do textboxa ciągu liczb załadowały się odpowiednie obrazki. Na razie wykonałem możliwość wpisywania tylko cyfr i obsługę zdarzenia wczytywania obrazu. Działa to tylko wtedy gdy wpiszę jedną cyfrę, po wpisaniu kilku program wyszukuje pliku np textbox=123, wtedy program wyszukuje 123.jpg. Chciałbym, aby traktował te cyfry osobno. 1,2,3. Próbowałem stworzyć tablicę, jednak nie idzie mi tak jakbym tego chciał. Proszę o pomoc

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace WindowsFormsApplication9
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        private void textBox1_TextChanged(object sender, EventArgs e)
        {
            string dane = textBox1.Text;

            if (dane == "")
            {
                MessageBox.Show("Brak liczby");
            }
            else
            {
                bool jest_liczba = true;
                try
                {
                    double dane_ok = System.Convert.ToDouble(dane);
                }
                catch
                {
                    MessageBox.Show("Nieprawidłowe znaki");
                    jest_liczba = false;
                }
                if (jest_liczba == true)
                {

                }
            }
        }
        private void button1_Click(object sender, EventArgs e)
        {
            string temp = textBox1.Text; //tablica 
            for (int i = 0; i < temp.Length; i++)
            {
                textBox1.Text = char.ToString(temp[i]);
            }
            string _katalog = @"c:\obrazki\"; //wczytywanie obrazka
            string _typ = ".jpg";
            int _liczba;
            if (Int32.TryParse(textBox1.Text, out _liczba))
            {
                pictureBox1.Image = Image.FromFile(_katalog + _liczba + _typ);
            }
        }
    }   
}
0

Wykorzystałem substring. Wszystko działa jak trzeba jednak przy wpisaniu mniejszej ilości liczb wyskakuje błąd: Indeks i długość muszą odwoływać się do lokalizacji w ciągu.
Nazwa parametru: length. Oto kod:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace WindowsFormsApplication9
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        private void textBox1_TextChanged(object sender, EventArgs e)
        {
            string dane = textBox1.Text;

            if (dane == "")
            {
                MessageBox.Show("Brak liczby");
            }
            else
            {
                bool jest_liczba = true;
                try
                {
                    double dane_ok = System.Convert.ToDouble(dane);
                }
                catch
                {
                    MessageBox.Show("Nieprawidłowe znaki");
                    jest_liczba = false;
                }
                if (jest_liczba == true)
                {

                }
            }
        }
        private void button1_Click(object sender, EventArgs e)
        {
            string input = textBox1.Text;

            string sub = input.Substring(0, 1);
            Convert.ToInt32(sub);
            string _katalog = @"c:\obrazki\";
            string _typ = ".jpg";
            
            pictureBox1.Image = Image.FromFile(_katalog + sub + _typ);

            string sub1 = input.Substring(1, 1);
            Convert.ToInt32(sub);
            string _katalog1 = @"c:\obrazki\";
            string _typ1 = ".jpg";

            pictureBox2.Image = Image.FromFile(_katalog1 + sub1 + _typ1);

            string sub2 = input.Substring(2, 1);
            Convert.ToInt32(sub);
            string _katalog2 = @"c:\obrazki\";
            string _typ2 = ".jpg";

            pictureBox3.Image = Image.FromFile(_katalog2 + sub2 + _typ2);
}
}
}
0

Z uprzejmości zapytam, która linia. Od razu wnioskuje, że wykraczasz po za długość stringa.

1

Jak wpisze większą ilość liczb to wszystko jest ok. Wyświetla 3 obrazki (tyle ile jest pictureboxów) Jednak gdy jest ich mniej wyskakuje błąd:
user image

1

Skoro string input ma wartość "12", to jego długość wynosi 2, więc posiada elementy o indeksach: 0 i 1.
Ty chcesz się odwołać do elementu o indeksie 2, który nie istnieje.

W ogóle, co Ty tam zrobiłeś w textBox1_TextChanged, do czego ma służyć ten kod?

I w ogóle, to żaden Substring nie jest Ci potrzebny, wystarczy, żebyś szedł w pętli po elementach textBox1.Text i z każdego z nich robił oddzielną ścieżkę do pliku.

0

w textBox1_TextChanged jest wykonane zabezpieczenie, żeby user mógł wpisać tylko liczby. "Wystarczy, żebyś szedł w pętli po elementach textBox1.Text i z każdego z nich robił oddzielną ścieżkę do pliku" - mogłbym prosic trochę jaśniej ?

1

To po kolei.

Po pierwsze, zamiast:

bool jest_liczba = true;
try
{
    double dane_ok = System.Convert.ToDouble(dane);
}
catch
{
    MessageBox.Show("Nieprawidłowe znaki");
    jest_liczba = false;
}

Lepiej napisać coś takiego:

double liczba;
if (!double.TryParse(textBox1.Text, out liczba))
{
    MessageBox.Show("Nieprawidłowe znaki");
}

Po drugie, liczba całkowita to int, a nie double.

Po trzecie, ten sposób jest słaby. Lepiej byłoby obsłużyć zdarzenie KeyPress w ten sposób:

private void textBox1_KeyPress(object sender, KeyPressEventArgs e)
{
    if (!char.IsDigit(e.KeyChar))
    {
        e.Handled = true;
    }
}

I wracając do tematu:

private void button1_Click(object sender, EventArgs e)
{
    foreach (var c in this.textBox1.Text)
    {
        string sciezka = string.Format(@"c:\obrazki\{0}.jpg", c);
        MessageBox.Show(sciezka);
    }
}
0

Świetnie! Dziękuję, jednak nadal wczytuje mi tylko ostatni znak.

foreach (var c in this.textBox1.Text)
            {
                string sciezka = string.Format(@"c:\obrazki\{0}.jpg", c);
                pictureBox1.Image = Image.FromFile(sciezka);
            } 

Po modyfikacji:

 
foreach (var c in this.textBox1.Text)
            {
                string sciezka = string.Format(@"c:\obrazki\{0}.jpg", c);
                pictureBox1.Image = Image.FromFile(sciezka);
                pictureBox2.Image = Image.FromFile(sciezka);
                pictureBox3.Image = Image.FromFile(sciezka);
            }

Jak zmienić ścieżkę dostępu, żeby wczytywały się po kolei obrazy?

3
  1. Zadeklaruj sobie tablicę string[] sciezki;
  2. W tej pętli (ale lepiej zmień foreach na for) wyznacz jej elementy.
  3. A potem odpowiednim pictureboxom przypisz odpowiednie ścieżki.
    :)
0

... chyba się poddaje:

private void button1_Click(object sender, EventArgs e)
        {
            
            foreach (var c in this.textBox1.Text)
           {
                for(i=0;i<textBox1.Lenght;i++)
                {
                string sciezka = string.Format(@"c:\obrazki\{0}.jpg", c);
                string[] sciezki;
                sciezka[0] = pictureBox1.Image = Image.FromFile(sciezka);
                sciezka[1] = pictureBox2.Image = Image.FromFile(sciezka);
                sciezka[2] = pictureBox3.Image = Image.FromFile(sciezka);
            }
         } 

Jest jeszcze dla mnie jakiś ratunek?

1
  1. zadeklaruj tablicę przed pętlą
  2. popraw literówkę w warunki tej pętli (.Length)
  3. niech w pętli tylko raz będzie to Image.FromFile(sciezka);. Po coś masz tę tablicę, prawda? Masz także zmienną (iterator tej pętli) o nazwie i. Wykorzystaj ją.
  4. somekind napisał "zmień pętlę foreach na for", a nie "dodaj koleją pętlę for".
1
Abdicode napisał(a):

Jest jeszcze dla mnie jakiś ratunek?

Książka lub kurs podstaw C#, i uczyć się pisania prostych, konsolowych programów. Dopiero potem zająć się okienkami, itp.

0

Postarałem się zrobić tak jak podpowiadacie, jednak nie wychodzi tak jakbym tego chciał:

private void button1_Click(object sender, EventArgs e)
        {       
                string[] sciezki= new string[]; //deklaracja tablicy scieżki nie wiem jaka wartość wpisac, przy text.Box.Leght wyskakuje błąd
               
                for(i=0;i<textBox1.Length;i++)//pętla for zamiast foreach, skacze pokolei po znakach w textBox1
                {
                string sciezka = string.Format(@"c:\obrazki\{0}.jpg", i); //scieżka wczytania obrazka
                sciezki[i] = pictureBox1.Image = Image.FromFile(i);// ??
                }
       } 
1

Sugeruję tak:

tring[] sciezki= new string[textBox1.Text.Length]; 

Bo chcesz przecież mieć tyle różnych ścieżek, ile cyfr wpisano w Textboxie, prawda?

A znak w Textboxie, to nie jest i, lecz textBox1.Text[i]:

sciezki[i] = string.Format(@"c:\obrazki\{0}.jpg", textBox1.Text[i]);
0

Już pomału zaczynam to chwytać, jednak wyszedł nowy problem z długością stringa. Kod:

private void button1_Click(object sender, EventArgs e)
        {
                string[] sciezki = new string[textBox1.Text.Length]; 
                int i;
                for(i=0;i<textBox1.Length;i++)
                {
                sciezki[i] = string.Format(@"c:\obrazki\{0}.jpg", textBox1.Text[i]); 
                }
       }  

Błąd:
http://img833.imageshack.us/img833/7104/beztytuutvm.png

2

Bo TextBox nie ma właściwości Length. Musisz odwołać się do właściwości Text. textBox1.Text.Length

Jakbyś przeczytał uważnie treść błędu to byś wiedział od razu gdzie leży problem. Jeżeli nie rozumiesz po angielsku to lepiej zacznij, bo bez tego to jak ślepy bez laski.

0

Zrobiłem jak kazaliście, działa jak trzeba.

private void button1_Click(object sender, EventArgs e)
        {
            string[] sciezki = new string[textBox1.Text.Length];
            int i;
            for (i = 0; i < textBox1.Text.Length; i++)
            {
                sciezki[i] = string.Format(@"c:\obrazki\{0}.jpg", textBox1.Text[i]);
                MessageBox.Show(sciezki[i]);
            }
        } 

Teraz mam problem z wstawieniem odpowiedniej wartości do pictureBoxa. A raczej z przypisaniem go:

private void button1_Click(object sender, EventArgs e)
        {
            string[] sciezki = new string[textBox1.Text.Length];
            int i;
            for (i = 0; i < textBox1.Text.Length; i++)
            {
                sciezki[i] = string.Format(@"c:\obrazki\{0}.jpg", textBox1.Text[i]);
                pictureBox1.Image = Image.FromFile(sciezki[0]);
                pictureBox2.Image = Image.FromFile(sciezki[1]);
                pictureBox3.Image = Image.FromFile(sciezki[i]);
                
                
            }
        } 
2

Nie zrozum mnie źle, ale programujesz nieco jak jakiś "robot" - niby próbujesz coś-tam poskładać z kodu, który dotychczas napisałeś/otrzymałeś, ostatecznie wychodzi coś, co "wygląda" na działające, ale okazuje się być bezsensowne.

0

no racja, skończę tylko ten projekcik i biorę się za apki konsolowe jak radził somekid

2
Abdicode napisał(a):

Jest jeszcze dla mnie jakiś ratunek?
Obawiam się że nie.

private void button1_Click(object sender, EventArgs e)
  {
   PictureBox[] box=new PictureBox[3];
   box[0]=pictureBox1;
   box[1]=pictureBox2;
   box[2]=pictureBox3;
   for(i=0;i<textBox1.Text.Length;++i) box[i].Image=Image.FromFile(string.Format(@"c:\obrazki\{0}.jpg",textBox1.Text[i]));
  }

Pierwszy wiersz najlepiej przenieść do klasy.
Kolejne trzy wiersze do konstruktora formatki.

0

Poznając visual studio napotkałem na "FlowLayoutPanel", i po konsultacji zastosowałem to w moim programie:

void button1_Click(object sender, EventArgs e)
        {
            while (flowLayoutPanel1.Controls.Count > 0)
            {
                flowLayoutPanel1.Controls[0].Dispose();
            }
            for (int i = 0; i < textBox1.Text.Length; ++i)
            {
                PictureBox pb = new PictureBox();
                pb.Image = Image.FromFile(string.Format(@"c:\obrazki\{0}.jpg", textBox1.Text[i]));
                flowLayoutPanel1.Controls.Add(pb);
            } 

Działa jak powinno, jednak wyszedł nowy problem z wielkością obrazków. Aktualnie wyświetla je z wielkością 100x50 pixeli, niezależnie od zapisanego źródła.
Screen:
user image
Margin i Padding flowlayoutpanelu ustawione na zero.

1

A jak chcesz je wyświetlić? Żeby było je całe widać czy jak?

0

szukam opcji odpowiedzialnej za wielkość wyświetlanego obrazka. Chce je wyświetlać powiedzmy w wielkości 200x150pix

1

Musisz zedytować bitmapę. Czyli powiększyć obrazek albo zmienić tylko wymiary płótna.

0

Propertasy Flowlayoutpanel:
user image

2

Tu chodzi o PictureBox. Jego standardowe wymiary to 100x50, dlatego musisz je zmienić w kodzie na inne takie jakie chcesz. Dodatkowo możesz dopasować właściwość PictureBox'a SizeMode.

1 użytkowników online, w tym zalogowanych: 0, gości: 1