Skocz do zawartości

Program wspierający budowę menu dla systemów wbudowanych


Pomocna odpowiedź

No i mam zaciach, kombinuję jak ogarnąć w widoku aplikacji wiele podobnych widoków, póki co testuję lewy panel z drzewem powiązań między strukturami ale nie zadawala mnie to. Chciałbym aby ktoś mi podpowiedział lub pokazał przykład kiedy na jednym panelu jest kilkadziesiąt tych samych obiektów. Tak aby użytkownik nie potracił się w tym. Póki co jest tak że kliknięcie przycisku "prev" lub "next" rozszerza listę w poziomie a kiedy ona nie mieści się w okienku zaczyna być przewijalna. Problemem jest kiedy chciałbym dodać obiekt "child", lista powinna rozciągać się w dół, potem znów można dodawać next i prev. Być może opis nie oddaje złożoności problemu, chodzi o to że w pewnym momencie kolejne okienka przestają się mieścić na podstawowym widoku a ja nie mam pomysłu jak to uporządkować. 

Link do komentarza
Share on other sites

Dnia 13.02.2022 o 11:09, _LM_ napisał:

No i mam zaciach, kombinuję jak ogarnąć w widoku aplikacji wiele podobnych widoków, póki co testuję lewy panel z drzewem powiązań między strukturami ale nie zadawala mnie to. Chciałbym aby ktoś mi podpowiedział lub pokazał przykład kiedy na jednym panelu jest kilkadziesiąt tych samych obiektów. Tak aby użytkownik nie potracił się w tym. Póki co jest tak że kliknięcie przycisku "prev" lub "next" rozszerza listę w poziomie a kiedy ona nie mieści się w okienku zaczyna być przewijalna. Problemem jest kiedy chciałbym dodać obiekt "child", lista powinna rozciągać się w dół, potem znów można dodawać next i prev. Być może opis nie oddaje złożoności problemu, chodzi o to że w pewnym momencie kolejne okienka przestają się mieścić na podstawowym widoku a ja nie mam pomysłu jak to uporządkować. 

Cześć _LM_,

ogólnie problem jest złożony - masz rację, że jest to drzewo i należy się w nim poruszać w pionie i w poziomie. W prostym kodzie, który przedstawiłem w pierwotnej dyskusji miałem cztery "zdarzenia": Up, Down, Left, Right oraz Enter (zatwierdź wybór) obsługiwane przez przerwania od klawiszy. Co bardzo ułatwiło mi poruszanie się po takiej drzewiastej strukturze była FSM (Finite State Machine) i fajna biblioteka do jej obsługi. Próbowałem Ci uzmysłowić, że problem jest całkiem złożony i napisanie generatora nie będzie sprawą łatwą - trzeba wymyśleć sposób na zrobienie abstrakcji struktury drzewiastej i przedstawienie jej graficznie. Nie wiem w czym programujesz tą aplikację do generowania menu, czy jest to C czy może C++(albo C# czy Java) i czy masz dostępną jakąś bibliotekę elementów graficznych (tak jak jest to np. w "Windows Forms" w VisualStudio, lub w bibliotece Swing w Javie). Jeśli masz język obiektowy taki jak C++, C# lub Java to zastosowałbym dziedziczenie, do reprezentacji parametrów danej pozycji menu (takich jak parametry tekstu,  Listy rozwijane, RadioButtons itp.). Napisanie takiej aplikacji zajmie Ci sporo pracy, a wygenerowany kod może mieć taki rozmiar i słabą prędkość działania, że nie da się jej wykorzystać na większości płytek Arduino (przynajmniej tych z MCU AVR).

BTW: wklejam kilka linków, które mogą być pomocne:

https://www.softwaretestinghelp.com/trees-in-cpp/

https://levelup.gitconnected.com/a-template-tree-class-in-c-7be9b4834e09

https://www.geeksforgeeks.org/binary-tree-set-1-introduction/

https://www.geeksforgeeks.org/c-programs-gq/tree-programs-gq/

https://docs.microsoft.com/pl-pl/dotnet/api/system.windows.forms.treeview?view=windowsdesktop-6.0

https://www.c-sharpcorner.com/article/tree-data-structure/

https://www.c-sharpcorner.com/article/treeview-control-in-C-Sharp/

Pozdrawiam

Edytowano przez FlyingDutch
  • Lubię! 1
  • Pomogłeś! 1
Link do komentarza
Share on other sites

Dziękuję za odpowiedź, ja mam małe doświadczenie w programach okienkowych i stąd ten problem. Piszę to basic for java. Jeśli chodzi dostęp do komponentów graficznych, nie stanowi to problemu, są wszystkie standardowe i wiele dodatkowych. Zaś w kwestii napisania silnika generującego drzewa struktur oraz potrzebne pliki, to nie powinno stanowić aż takiego wyzwania gdyż to tylko operacje na tekście. Co do kodu silnika biblioteki, główną jej część mam napisaną, zapewne pojawi się wpis w tamtym temacie. Także ja zabieram się za studiowanie zamieszczonych linków, pozdrawiam 

  • Lubię! 2
Link do komentarza
Share on other sites

Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

(edytowany)

Niestety nie mogę edytować już postu wcześniejszego, poniżej hipotetyczny zestaw struktur, wygenerowany w czasie około dwóch minut 🙂

const menu_t Start_menu[];
const menu_t czas[];
const menu_t s1[];
const menu_t s2[];


const node_t nodeTab[] ={
{.ptrNode = Start_menu,.nodeID = 0},
{.ptrNode = czas,.nodeID = 1},
{.ptrNode = s1,.nodeID = 2},
{.ptrNode = s2,.nodeID = 3},
};


const menu_t Start_menu[] ={
{
.menuNav[_next] = &Start_menu[SILNIK1],
.menuNav[_prev] = &Start_menu[NULL],
.menuNav[_parent] =Start_menu,
.menuNav[_child] =czas,
.id = ZEGAR
},
{
.menuNav[_next] = &Start_menu[SILNIK2],
.menuNav[_prev] = &Start_menu[ZEGAR],
.menuNav[_parent] =Start_menu,
.menuNav[_child] =s1,
.id = SILNIK1
},
{
.menuNav[_next] = &Start_menu[NULL],
.menuNav[_prev] = &Start_menu[SILNIK1],
.menuNav[_parent] =Start_menu,
.menuNav[_child] =s2,
.id = SILNIK2
},
};

const menu_t czas[] ={
{
.menuNav[_next] = &czas[DATA],
.menuNav[_prev] = &czas[NULL],
.menuNav[_parent] =czas,
.menuNav[_child] =null,
.id = CZAS
},
{
.menuNav[_next] = &czas[BUDZIK],
.menuNav[_prev] = &czas[CZAS],
.menuNav[_parent] =czas,
.menuNav[_child] =null,
.id = DATA
},
{
.menuNav[_next] = &czas[STOPER],
.menuNav[_prev] = &czas[DATA],
.menuNav[_parent] =czas,
.menuNav[_child] =null,
.id = BUDZIK
},
{
.menuNav[_next] = &czas[NULL],
.menuNav[_prev] = &czas[BUDZIK],
.menuNav[_parent] =czas,
.menuNav[_child] =null,
.id = STOPER
},
};

const menu_t s1[] ={
{
.menuNav[_next] = &s1[MOC],
.menuNav[_prev] = &s1[NULL],
.menuNav[_parent] =s1,
.menuNav[_child] =null,
.id = PRAD
},
{
.menuNav[_next] = &s1[OBROTY],
.menuNav[_prev] = &s1[PRAD],
.menuNav[_parent] =s1,
.menuNav[_child] =null,
.id = MOC
},
{
.menuNav[_next] = &s1[TEMPERATURA],
.menuNav[_prev] = &s1[MOC],
.menuNav[_parent] =s1,
.menuNav[_child] =null,
.id = OBROTY
},
{
.menuNav[_next] = &s1[CZEST],
.menuNav[_prev] = &s1[OBROTY],
.menuNav[_parent] =s1,
.menuNav[_child] =null,
.id = TEMPERATURA
},
{
.menuNav[_next] = &s1[NULL],
.menuNav[_prev] = &s1[TEMPERATURA],
.menuNav[_parent] =s1,
.menuNav[_child] =null,
.id = CZEST
},
};

const menu_t s2[] ={
{
.menuNav[_next] = &s2[MOC],
.menuNav[_prev] = &s2[NULL],
.menuNav[_parent] =s2,
.menuNav[_child] =null,
.id = PRAD
},
{
.menuNav[_next] = &s2[OBROTY],
.menuNav[_prev] = &s2[PRAD],
.menuNav[_parent] =s2,
.menuNav[_child] =null,
.id = MOC
},
{
.menuNav[_next] = &s2[TEMPERATURA],
.menuNav[_prev] = &s2[MOC],
.menuNav[_parent] =s2,
.menuNav[_child] =null,
.id = OBROTY
},
{
.menuNav[_next] = &s2[CZEST],
.menuNav[_prev] = &s2[OBROTY],
.menuNav[_parent] =s2,
.menuNav[_child] =null,
.id = TEMPERATURA
},
{
.menuNav[_next] = &s2[NULL],
.menuNav[_prev] = &s2[TEMPERATURA],
.menuNav[_parent] =s2,
.menuNav[_child] =null,
.id = CZEST
},
};

Ogólnie, jestem zadowolony z postępów, jednak aplikacja, jak i kody źródłowe zawierają jeszcze sporo błędów oraz jeszcze więcej sekcji "TODO" 😉 Także do publikacji potrzeba jeszcze nieco mojego czasu i zaparcia.

Tak przy okazji ta książka to jest kopalnia złota. 

IMG_20220306_212147.thumb.jpg.5b9a27fbdd2f7588421983594b877a57.jpg

Eot

Edytowano przez _LM_
  • Lubię! 2
Link do komentarza
Share on other sites

Pytanie do kolegów bardziej znających programowanie na PC. Muszę w tym generatorze wykonać kilka plików wzorcowych, i teraz aby nie robić sobie bałaganu w kodzie, pomyślałem że każdą taką templatkę trzeba zapisać osobno aby później łatwiej ją wyedytowć w razie potrzeby. Nie jestem jednak pewien czy to dobry kierunek, ponieważ z tego powodu będzie wygenerowanych sporo plików txt... Właśnie, tu jest drugie pytanie, czy te wzorce powinny być zapisane jako txt, czy inny format? Jak to waszym zdaniem powinno wyglądać? 

Poniżej przykładowy wzorzec, jeszcze zapisany w kodzie programu, a później w txt. Mam nadzieję że zadałem jasne pytanie 😉

	Private struct_menu_t_template As String = "{"&CRLF & _
".menuNav[_next] = &"&"NEXTTYPE"&"["&"NEXTID"&"],"&CRLF & _
".menuNav[_prev] = &"&"PREVTYPE"&"["&"PREVID"&"],"&CRLF & _
".menuNav[_parent] = " &"PARENTTYPE"&","&CRLF & _
".menuNav[_child] = "&"CHILDTYPE"&","&CRLF & _
".id = "&"MYID"&CRLF&"},"
{
	.menuNav[_next] = &NEXTYPE[NEXTID],
	.menuNav[_prev] = &NEXTYPE[PREVID],	
	.menuNav[_parent] = &PARENTTYPE,
	.menuNav[_child] = &CHILDTYPE,
	.id = MYID
},

 Ogólnie w całości funkcji to wygląda tak: no, widać że spory bałagan tutaj panuje.

 B4J_xBqcnL8xUT.thumb.png.07acb18b0845bbe3f653024aee5a05e8.png

Link do komentarza
Share on other sites

Więc utworzyłem osobne pliki tekstowe, program odnajduje w nich wzorce i podmienia na wygenerowane wartości na zasadzie znajdź/zamień. Kod staje się czytelniejszy i łatwiejszy w utrzymaniu. 

Link do komentarza
Share on other sites

Przed chwilą, _LM_ napisał:

program odnajduje w nich wzorce i podmienia na wygenerowane wartości na zasadzie znajdź/zamień.

Też tak robię (sorki że wczoraj nie odpisałem ale miałem ciężki dzień). Zresztą ja sobie trochę to skomplikowałem, bo we wzorcu znajduje się sposób podmieniania (np. dla szablonów html mam 'escape html', 'escape js', 'verbatim').

Wygląda to mniej więcej tak:

<input type="text" value="<:h wartosc:>" onclick="clicked('<:j wartosc:>');">

No a moja biblioteka już dba o sposób podmieniania.

Link do komentarza
Share on other sites

4 minuty temu, ethanak napisał:

Też tak robię (sorki że wczoraj nie odpisałem ale miałem ciężki dzień).

To nawet dobrze bo miałem czas aby samemu to sobie w głowie poukładać 🙂 a w myśl zasady "masz głowę i ch... to kombinuj" - wykombinowałem. Bardziej mnie ciekawiło czy takie podejście jest prawidłowe, teraz jak patrzę na ten kod źródłowy utwierdziłem się w przekonaniu że tak. Dla porównania ze wcześniejszym obrazkiem - potworkiem, te linie wyglądają teraz tak.

B4J_p4dZYd1gx3.thumb.png.46f5ff0e7fac4c6764096645ab13a8c3.png

Czysto i schludnie, to co jest powtarzalne siedzi w plikach tekstowych widać to w prawej kolumnie.

Link do komentarza
Share on other sites

@spook dziękuję za odpowiedź, po przemyśleniach właśnie tak zrobiłem że stałe zostały przeniesione do plików zewnętrznych. W idealnej wersji tego oprogramowania dobrze by było dać użytkownikowi możliwość tworzenia własnego szablonu, na przykład w związku z tym że niektóre mikrokontrolery mają swoje funkcje dostępu do pamięci Flash gdzie planuję przechowywać struktury. Póki co będą opcje wyboru tych podstawowych układów, program co chwila przechodzi dosyć znaczące zmiany wraz z rozwojem biblioteki oraz tym że wciąż uczę się "okienek". 

Link do komentarza
Share on other sites

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Anonim
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.

×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.