Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: [PHP]Przekazanie zmiennej z klasy do funkcji
Forum PHP.pl > Forum > Przedszkole
Malinaa
Jak przekazać zmienną z klasy do funkcji?

W folderze classes mam klasę z takim kodem

Kod
class routClass {
...
   public function __construct() {
      ...
      define('NAME_CONTROLLER', $name_controller); // Jak inaczej przekazac zmienna do funkcji?
   }
}


W folderze functions mam funkcje
Kod
function writeData($value) {
    global $arrayData; // Czy funkcja z global $arrayData jest ok?
    $key = NAME_CONTROLLER;  // Jak inaczej przekazac zmienna do funkcji?
    $data = '';
    
    if (isset($arrayData[$key][$value])) {
        $data = $arrayData[$key][$value];
    }
    else {
        $data = 'Sorry value not found!';
    }
    
    echo $data;
}

viking
A co ma wspólnego ta klasa z funkcją? Global i inne wynalazki to nie jest dobry pomysł.
gino
po pierwsze nazwiennictwo: funkcja w klasie to metoda. Aby przekazać parametr do konstruktora wywołaj instancję klasy z parametrem:
Kod
$controler = 'nazwa_kontrolera';
$data = new rouClass($controler);

na pewno trafi do konstruktora.

Funkcje oraz metody z natury rzeczy i z definicji zwracają wynik, nie ma w nich miejsca na żadne echo, print itd. Funkcja ma zwrócić wartoścć i tyle:
Kod
return $wynik;

O globalsach nie będę powtarzał za vikingiem, a już zwłaszcza wewnątrz funkcji.
Malinaa
Klasę wywołuje w pliku init.php

spl_autoload_register(function($className){
include(...$className.'.php');
});

/* Autoload Class */
$rout = new routClass();

gdzie ładuję kontroler w zależności od adresu strony

// Include controller
require_once($path . $this->controller . '.php');


Przykładowy kontroler
Kod
class indexController extends frameworkClass {
    public function __construct() {
        $this->helper("application");
    }    
    public function index() {
        $this->view("index");
    }
}


$this->helper("application") wczytuje funkcje aplikacji - tu znajduje się funkcja, którą chcę napisać wspólną dla wszystkich kontrolerów (klas)

Nie mogę napisać tej funkcji jako metody w klasie, ponieważ musiałbym to samo powtarzać w każdym jednym kontrolerze.
Takie rozwiązanie byłoby gorsze od wstawienie w funkcji $key = NAME_CONTROLLER;
Z kolei po wstawieniu funkcji w frameworkClass jako metody nie będzie widoczna dla view() które wczytuje template index.php (kod html i php <- w template wywołana jest ta funkcja).

Wiem, że global nie jest pożądane (to taka ostateczność), bo nie do końca wiem jak przekazać poprawnie tablicę do funkcji,
która to jest wczytywana na stronie startowej poprzez require() i nie jest widoczna w pliku z funkcją po wpisaniu print_r($tablica) = null
natomiast global $tablica i dane z tablicy są w funkcji?

Coś takiego
function writeData($value, $arrayData=array()) {
// echo or return data
}
nie działa? Dopiero z global $arrayData można tworzyć funkcje z użyciem parametrów tablicy.

Dałem echo $wynik (zamiast return) ponieważ nie trzeba za każdym razem przed wyświetleniem wyniku funkcji pisać echo writeData();
Czy naprawdę musi (powinno) być return $wynik i za każdym razem trzeba dopisywać echo writeData() kiedy w tym przypadku samo writeData() jest prostsze?
viking
Skoro ma być wspólna dla wszystkich a wszystkie zapewne dziedziczą po frameworkClass to dlaczego tam jej nie dodasz? Nie możesz użyć normalnie composera i prawidłowego nazewnictwa zgodnie z PSR? Nazwa kontrolera - echo static::class;
Malinaa
Tak, wszystkie dziedziczą po frameworkClass i tu chciałem napisać te metody, ale tutaj nie są widoczne w templatach dla view() nie wiem jak sprawić, aby były widoczne?

Kłopot, że używałem w skryptach zwykle tylko funkcji, czasem klas (nie znam tematu tak dobrze), a poczułem moc napisania autorskiego frameworka opartego na wzorcu MVC.
Chcę napisać ten framework na czystym PHP bez użycia Composera etc., standard PSR to tyle o ile poznałem przy okazji pisania w Symfony.
I tutaj moja prośba o pomoc.

frameworkClass napisałem tak:

Kod
class frameworkClass {
    
    // View Page Template
    public function view($viewName, $data = []) {
        if (file_exists("../application/views/" . $viewName . ".php")) {
            require_once("../application/views/$viewName.php");
        }
        else {
            echo "ERROR: Sorry application view $viewName.php file not found!";
        }
    }
}


kiedy wstawie do klasy funkcje (ładowaną w kontrolerze) to $result = lipa ;!

(public) function writeData($value) {
global $arrayDataPages;
$key = NAME_CONTROLLER;

return $result;
}


$arrayDataPages ładuje w pliku index.php katalogu public/ poprzez require(data.php);
NAME_CONTROLLER znajduje się w class routClass {} (klasa ładuje kontroler zależnie od adresu)

Obecnie tyle, że działa, ale jak całość poprawić, aby było w porządku Pro?
viking
Rzucić to w diabły i użyć Symfony albo Laravela wink.gif Naprawdę mamy PHP8 a tu nawet silnego typowania brakuje. Może to późna pora ale nie rozumiem co ta twoja funkcja ma robić? Chcesz wstrzykiwać dodatkowe dane do widoku?
gino
A tak już abstrachując od tego co radzi Viking a dobrze radzi, to co Ty zwracasz w tej funkcji writeData, skoro nie masz żadnej zmiennej $result w tej funkcji? Skąd ją wziąłeś? To, co napisałem to tylko przykład jak funkcja zwraca wartość, mogłem napisać return $abcd. Już nie będę pisał o obsłudze błędów bo pisanie echo 'error coś tam ' to zamierzchłe czasy phpcowe.
Malinaa
Cytat(viking @ 18.12.2020, 21:17:27 ) *
Rzucić to...


Pisałem, że chcę "czysty" PHP (żadnego gotowca Synfony itp.), obawiałem się, ale miałem nadzieję, że co napisałem będzie zrozumiałe.

W widoku mam funkcje np.

<div id="navigation" class="navbar-collapse collapse">
<?php buildMenu(); ?> ta funkcja buduje menu w Bootstrapie (śmiga active i wszystko po kolei jest pięknie Pro : )
</div>

funkcja writeData() ma (o ile się rozumiemy, tak jak piszesz) wstrzykiwać dane do widoku z tablicy (więcej szczegółów już podałem wcześniej)

ma działać podobnie jak np.

function linkCSS($cssPath){
$url = PATH . $cssPath;
echo '<link href="'. $url .'" rel="stylesheet">';
}

tu jest sprawa prosta z $cssPath = '...style.css'

ale przy writeData() dochodzą dwie wartości

global $arrayDataPages; // stala
$key = NAME_CONTROLLER; // zmienna

które trzeba zadeklarować w funkcji i tu jest cały kłopot.
Jak to zrobić porządnie?


Cytat(gino @ 18.12.2020, 21:54:10 ) *
A tak już abstrachując...


Sorki bez obrazy, ale wygląda na to, że nie potrafisz (nawet) przeczytać co chcę wykonać, a rzeczywiście tylko abstrakcje piszesz.
viking
Stykasz się z zasięgiem zmiennych wewnątrz funkcji. W view($viewName, $data = []) masz zmienną $data i tutaj tylko możesz przekazać zmienne które będą widoczne w pliku. Natomiast NAME_CONTROLLER mówiłem Ci już że w każdej klasie masz dostęp do static::class (zrób sobie echo tego). W żaden sposób nie jest to pro tylko pro tandeta wink.gif Własny FW można pisać jak ma się jakieś podstawy. Pisząc w ten sposób który nam prezentujesz nabierasz tylko mega złych nawyków. Nic tu nie jest poprawnie. Zacznij może od napisania chociaż klasy View w której mógłbyś normalnie inicjować zmienne. Composera powinieneś używać bo jest standardem. Nie wymyślaj swoich rozwiązań - naucz się korzystać z gotowych.
gino
Cytat
Kłopot, że używałem w skryptach zwykle tylko funkcji, czasem klas (nie znam tematu tak dobrze), a poczułem moc...


powodzenia życzę, szczerze.
Malinaa
Cytat(viking @ 19.12.2020, 11:52:17 ) *
Stykasz się z zasięgiem zmiennych wewnątrz funkcji. W view($viewName, $data = [])


Mogę przekazać dane poprzez $data[] i tak też robię z innymi danymi,
wówczas funkcja jako metoda zadziała w frameworkClass ale nie zmienia to sytuacji i tak dopiero po dodaniu global $arrayDataPages tablica jest ładowana do funkcji/metody
alternatywą dla global jest require(data.php) plik w którym jest ta tablica. Czy require() jest tu ok zamiast global?

Jeśli ok to pozostała zmienna, static::class to tandeta, więc nie o to chodzi.

W pliku routClass.php (wczytującym kontrolery w zależności od adresu strony) mam klasę i kod ze zmienną

Kod
class routClass {

public function __construct() {
            $name_controller = $this->nameController($url[0]);
}

}


Jak tę zmienną przekazać do pliku kontrolera np. indexController.php (z jednej klasy do drugiej znajdujących się w różnych plikach)?

Kod
class indexController extends frameworkClass {
    
    public function index() {
               //$html_menu = $this->buildMenu();

        $data = ['name_controller' => $name_controller, 'i inne dane dla widoku...'];

        $this->view("index", $data);
    }
}


Wówczas wynik np. z funkcji buildMenu() czyli całe Menu, które przeniosę do frameworkClass jako metodę też mógłbym wrzucić do tablicy $data i wyświetlić w widoku?!


If you try walking in my shoes... PHP Info, Please.

Kilka tygodni pracy i jest pierwsza strona na autorskim Frameworku: www.s7partner.dbm.org.pl

Z waszą pomocą, ale średnio wyszło i chciałbym popracować nad back endem php'em, może damy radę coś jeszcze usprawnić?

Tym razem przydałoby się więcej teorii o ile to możliwe bez słów typu rzuć to, powodzenia życzę, nie możliwe...


Mam pytania odnośnie kilku wypowiedzi:

1. "Nie możesz użyć normalnie composera i prawidłowego nazewnictwa zgodnie z PSR?"

Używam Composera do podstron typu Kontakt, gdzie potrzebuję PHPMailera itp., nie wiem jednak na co potrzebny jest w autorskim Frameworku (co mógłbym tu nim usprawnić)?
Standardy PSR są do opanowania, ale jak się do nich zabrać... szybko ? : )

2. "Rzucić to w diabły i użyć Symfony albo Laravela"

Wymienione frameworki są ok, ale to "krowy", samo skopiowanie plików, instalacja Symfony zajmuje stosunkowo bardzo dużo czasu, a strona otwiera się katastrofalnie na typowym serwerze.
Potrzebowałem szybkiego frameworka dla stron składających się z kilku/kilkunastu podstron i ten, który napisałem jest do tego celu dobry.
Ponadto uruchomienie strony na serwerze zajęło może 10 minut i gotowe.
Czy wymienione ciężkie frameworki są w takiej sytuacji pożądane?

3. "Pisząc w ten sposób który nam prezentujesz nabierasz tylko mega złych nawyków."
P.S. viking jak widać masz większe wyobrażenie o PHP, więc zostań mentorem, nie krzycz na mnie, że nie tak, a naucz paru rzeczy, abym nabrał dobrych nawyków.
gino
Cytat
Wymienione frameworki są ok, ale to "krowy", samo skopiowanie plików, instalacja Symfony zajmuje stosunkowo bardzo dużo czasu...


To zastosuj ultraszybkiego Lumen-a, młodszego brata Laravel-a, sama instalacja około 50KB:

Lumen
viking
Aktualnie mało kto pisze własny FW, korzysta się albo z gotowych komponentów (Symfony, Laminas) do budowy czegoś własnego, albo po prostu z całych FW. Jeśli ci zajmuje długo to zwyczajnie nie umiesz czegoś zrobić. Gotowy projekt na Laravel to przegranie plików (zazwyczaj z gita), dodanie produkcyjnego .env, uruchomienie composera/npm i wygenerowanie cache wszystkiego. 5 minut roboty. W zależności od środowiska całą pracę może też robić Dockerfile albo Jenkins. U ciebie nie ma nawet co poprawiać bo to się kupy nie trzyma. Nawet ciężko pomóc bo twój kod to losowe klasy bez większego zamysłu. Zacznij od podstaw typu PSR-0 do 2 i 4.
Malinaa
Cytat(gino @ 29.12.2020, 07:39:15 ) *
To zastosuj ultraszybkiego Lumen-a

Czy Lumen funkcjonuje na plikach tekstowych, bo z założenia miał to być framework bez bazy danych,
ponieważ takie rozwiązanie mnie interesowało dla tych w większości statycznych podstron.
Wymagane dane znajdują się w tablicy, menu tworzę z tablicy itd.
I jest ok, do momentu kiedy pomyślałem, że można by dodać opcje komentarzy w artykułach,
gdzie nie ma możliwości dodania postu przez gościa, a tylko przez użytkownika.
Tutaj musiałem rozszerzyć framework o bazę danych, rejestracja, logowanie...
Nie będę jednak wprowadzał takiego rozszerzenia na stronie,
ale ciekawi mnie, który framework szybko śmiga na typowym hostingu
i funkcjonuje na samych plikach tekstowych?
Dzięki za info.

Cytat(viking)
Aktualnie mało kto pisze własny FW...

Rozumiem, dlatego większy własny projekt tworzę w Symfony,
jednak gotowce nie dają podobnej satysfakcji i bardzo chciałem powalczyć z czystym PHP'em.
Mimo, że w postach pytałem tyko o fragmenty kodu widzę, że trzyma się to kupy.
Natomiast dla Symfony pewnie będę musiał zaopatrzyć się w mocny serwer (rosnące koszty, aby zarobić parę zł,
bo nie każdy ma genialne pomysły na super szybki biznes : ), chociaż po wygenerowaniu cacha jakoś to łazi.
Jak z tymi PSR, jest jakieś miejsce, gdzie można sprawnie opanować temat?

W postach pytałem o dwie rzeczy:
1. Jak przekazać zmienną z klasy (systemu) do funkcji widoku -> zrobiłem to za pomocą wspomnianej tablicy $data[] (nadal nie jest tak jak bym chciał)
2. Jak pozbyć się global $array z funkcji, bo to global okropnie mi się nie podoba ; ) , gdzie tablica $array znajduje się pliku data.php -> zrobiłem to za pomocą require() wczytałem plik z tablicą w funkcji, aby móc np. utworzyć z tej tablicy Menu
viking
Jeśli masz tylko parę stron statycznych to lepszym wyjściem może być generator stron statycznych które są teraz bardzo popularne. Pierwszy z brzegu https://gohugo.io/. Komentarze możesz osadzić disqus. Baza danych na plikach to zawsze był marny pomysł. Dużo lepiej użyć sqlite. O psr najlepiej poczytać u źródła. Włącz sobie w edytorze poprawianie kodu. Ps jak już to route nie rout.
Malinaa
"Statyczne" w cudzysłowie, wystarczy dodać w linku ?id=twoje-id aby zmienić działanie systemu na korzyść Partnera.

Nie ma bazy danych na plikach tekstowych, bo to nie jest dobry pomysł. Baza danych przy kilku/kilkunastu podstronach jest tu nie potrzebna.
Plik tekstowy służy tylko do wczytania page content, skrypt ten sam tylko content się zmienia i content jest statyczny.

PSR gdzie jest źródło, najlepiej w języku polskim, aby dobrze rozumieć, nie kombinować... czy, o ile dobrze zrozumiałem ; )

P.S. Cwana Bestia. Jakiego edytora używasz, że wystarczy włącz sobie i już wiem, że route, kiedy mi zawsze z angielskiego pasowało rout.
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.