-1

I have tried the solutions indicated here on stackoverflow, the code below uses one of them, recommended and voted as the right way to do it, but it doesn't work for me, why? In fact the href results empty.

<?php

//URLS LIST
$nameA = 'http://www.example.com';
$nameB = 'http://www.example.com';
$nameC = 'http://www.example.com';

class bannClass {

    private $class_varA;
    private $class_varB;
    private $class_varC;

    public $username = '';
    public function __construct($nameA, $nameB, $nameC) {
      $this->class_varA = $nameA;
      $this->class_varB = $nameB;
      $this->class_varC = $nameC;
    }
    public function check_userOne() {
      $url = 'https://example.com/wp-content/uploads/sponsor/' . $this->username . '/sponsor1.jpg';
      return '<a href="' . $this->class_varA . '" target="_blank" rel="noopener noreferrer"><img src="' . $url . '" alt="Sponsor"/></a>';
    }
    public function check_userTwo() {
      $url = 'https://example.com/wp-content/uploads/sponsor/' . $this->username . '/sponsor2.jpg';
      return '<a href="' . $this->class_varB . '" target="_blank" rel="noopener noreferrer"><img src="' . $url . '" alt="Sponsor"/></a>';
    }
    public function check_userThree() {
      $url = 'https://example.com/wp-content/uploads/sponsor/' . $this->username . '/sponsor3.jpg';
      return '<a href="' . $this->class_varC . '" target="_blank" rel="noopener noreferrer"><img src="' . $url . '" alt="Sponsor"/></a>';
    }
}

Also how can i make those 3 variables at the top dynamic in php? instead of "name" something like $($this->username . 'A') , $($this->username . 'B') , etc.

EDIT: the above class is being instantiated in another php file like so:

<?php

require_once('myclass.php');
$bannClass = new bannClass();
$bannClass->username = $data['username'];

//etc.

and used like:

<?php echo $bannClass->check_userOne();?>
Nathan Bernard
  • 391
  • 2
  • 7
  • 22
  • how you are calling `bannClass` ? – Niklesh Raut Oct 12 '19 at 11:38
  • Where is the object instantiation code? – u_mulder Oct 12 '19 at 11:39
  • I don't think You can make those variables "dynamic". What You could possibly do is create array instead of seperate objects. And call it with `$this->class_var['A']`, `$this->class_var['B']` etc. – D.Weltrowski Oct 12 '19 at 11:40
  • @NikleshRaut why? does it have any importance? the thing happens here inside the class. the call of the class in another php file works fine, the images show up correctly through the $url variable. – Nathan Bernard Oct 12 '19 at 11:44
  • @D.Weltrowski php looks so limited, more i experiment with it more i hate it. the array solution doesn't even go close to the dynamic thing – Nathan Bernard Oct 12 '19 at 11:46
  • @u_mulder mmm what's that again? – Nathan Bernard Oct 12 '19 at 11:46
  • Okay I read more about it and it seems You can do dynamic in PHP. Tho I belive array is still a better solution. https://stackoverflow.com/questions/9257505/using-braces-with-dynamic-variable-names-in-php – D.Weltrowski Oct 12 '19 at 11:50
  • @nathan : every programing language has its own importance, it depends on your skill and requirements how you use this. BTW you can use curly brackets to make dynamic variable ie `$this->{$this->username.'A'}` – Niklesh Raut Oct 12 '19 at 11:51
  • A large part of the problem is this is using procedural thinking for an OOP solution. Your object is not solving anything; it’s just the equivalent of a goto statement. You need to pass a value to a single method, not three identical methods. – Tim Morton Oct 12 '19 at 12:08
  • 1
    You’re instantiating it without passing values to the constructor... how does the object know what the properties are supposed to be? – Tim Morton Oct 12 '19 at 12:15

2 Answers2

2

As it is written, you must inject 3 values when it is instantiated. If you have error reporting turned on in your development environment (and you really should), it would have complained when you instantiated it as $bannClass = new bannClass();

This is how this object should be instantiated:

$nameA = 'http://www.example.com';
$nameB = 'http://www.example.com';
$nameC = 'http://www.example.com';

$bannClass = new bannClass($nameA, $nameB, $nameC);

I would make a few suggestions:

  1. Don’t mix logic and presentation. A good rule of thumb to follow is no html outside of the view. Objects are generally for logic, not formatting html. Leave html for helper functions and the “view” portion of the script (which should be the very last thing that happens)
  2. Keep it DRY (don’t repeat yourself). If you have methods doing the same thing, it’s time to refactor. Pass in a variable or an array for the method to work with.

—-

Further ideas relating to your comment:

The collection of the urls would typically be the job of an object. (Look into the PDO object. Helpful reference )

In all my projects, I use an object (named Database) to wrap around php’s db access, similar to pdo. It includes the following 3 methods (code is omitted for brevity):

public function prepare(string $query) { ... }
public function execute(array $params) { ... }
public function nextRecord() {...}

In a procedural script, you would first do whatever initialization is needed, deal with any user input using the PRG pattern, and any other logic. Then you would output the html, using php only to loop and insert variables. In OOP terms, this roughly corresponds to the MVC pattern (which is well worth learning).

So, for the example, let’s say that we have a database of urls:

ID   URL       Image
1    foo.com   Image1.com
2    bar.com   Image2.com
3    baz.com   Image3.com

A procedural script could go as follows:

<?php
require(‘database.php’);

// optionally deal with user input

$url = new Database;  // example is assuming connection is handled in the object
$url->prepare(“select url, image from sometable”);
$url->execute();

// all logic is complete; now give the output 
?>
<!— html stuff —>
<ul>
<?php while($row=$url->nextRecord() ): ?>
    <li><a href=“<?= $row->url ?>" target="_blank" rel="noopener noreferrer"><img src="<?= $row->image ?>" alt="Sponsor"/></a></li>
    <?php endwhile; ?>
</ul>

Admittedly, I haven’t explained my object; space does not permit. But this should give you an overview of what’s possible and how to display 150 urls without repeating yourself.

Tim Morton
  • 2,614
  • 1
  • 15
  • 23
  • Thanks for the tips! So given i have like 150 urls, is there an example of a similar scenario i can look at? to restructure it the correct way? I was thinking to do that few logic directly inside the main php file at this point without even the use of a class, but retrieve the urls from a csv or something – Nathan Bernard Oct 12 '19 at 13:39
0

Just to add to excellent answer by Tim Morton: Let's suppose, that the three links are almost always the same, then you can do something like this:

class bannClass {

    private $class_varA = 'https://example.com';
    private $class_varB = 'https://example.com';
    private $class_varC = 'https://example.com';

    public $username = '';
    public function __construct($nameA = null, $nameB = null, $nameC = null) {
      if (!empty($nameA)) $this->class_varA = $nameA;
      if (!empty($nameB)) $this->class_varB = $nameB;
      if (!empty($nameC)) $this->class_varC = $nameC;
    }

    public function getVarA(){
      return $this->class_varA;
    }

    public function getVarB(){
      return $this->class_varB;
    }

    public function getVarC(){
      return $this->class_varC;
    }

}

What above does, that if the class is not called with any parameters = $foo = new bannClass(); it will default all three URLs to what was set as default. Obviously, you should arrange the variables in such manner, that first is possibly changed the most time:

$bar = new bannClass('https://stackoverflow.com');
echo $bar->getVarA(); // returns stackoverflow.com
echo $bar->getVarC(); // returns example.com

Because changing only third parameter looks kinda stupid:

$baz = new bannClass(null,null,'https://stackoverflow.com');
cho $baz->getVarA(); // returns example.com
echo $baz->getVarC(); // returns stackoverflow.com
Pavel Janicek
  • 14,128
  • 14
  • 53
  • 77