Jump to content

API: How to Set Image Description Language Value?


bytesource
 Share

Recommended Posts

Hi all,

I have been wondering how to set the value an an image's description for another language.

The following code did not work:

<?php
// $translations: array of id => translation key/value pairs
// $language: string determing the target language, such a 'de' or 'pt'
function insertTranslations($translations, $language) {

     $translations = mergeSections($translations);

     foreach($translations as $id => $translation) {

         // example ID:
         // 1335··1335··FieldtypeImage··images··03.jpg··1of1
         list($refPage, $page, $type, $name, $identifier) = splitID($id);

         if ("FieldtypeImage" === $type || "FieldtypeFile" === $type) {
             $p = wire('pages')->get($page);
             $p->setOutputFormatting(false);

             $field = $p->$name;
             $file  = $field[$identifier];

             $targetLanguage = wire('languages')->get($language); // get the language we want
             $file->set("description$targetLanguage", $translation);
             $p->save();
         }
     }
     // [...]
} 

Any suggestions are highly welcome!

Cheers,

Stefan

Link to comment
Share on other sites

It should work that way. Here's a comment from Pagefile.php. Did you check the other parts of the function to work properly?
 

// check if a language description is being set manually by description123 where 123 is language ID

Link to comment
Share on other sites

Thanks for pointing me to the implementation of the Pagefile::set() function.

I went through my function again, but couldn't find any errors. Of, course, this does not mean there aren't any. It is just that setting the language values for all other language fields, such as TextLanguage and TextareaLanguage using the setLanguageValue() function does work as expected.

To get a better understanding of what I am actually dealing with here, I would like to know how FieldtypeImage (or FieldtypeFile) is represented internally. I read that images bound to the type were represented as an array. But what kind of array items are these exactly? In other words, if I have an image field containing three images, what is the field type of each image?

Cheers,

Stefan

Link to comment
Share on other sites

I think it's kinda like this: Page -> Pageimages (/-files) -> Pageimage (/-file), just like $page->images->eq(0). You'll find the corresponding classes in the core folder. Also having a look at FieldtypeFile and FieldtypeImage wouldn't do harm.

  • Like 1
Link to comment
Share on other sites

Thanks for this overview!

Doing a little bit of testing, I found that the language value actually gets set, but for some reason it does not get saved.

Here is the the original code with some extra lines added for testing:

// $translations: array of id => translation key/value pairs
// $language: string determing the target language, such a 'de' or 'pt'
function insertTranslations($translations, $language) {

     $translations = mergeSections($translations);

     foreach($translations as $id => $translation) {

         // example ID:
         // 1335··1335··FieldtypeImage··images··03.jpg··1of1
         list($refPage, $page, $type, $name, $identifier) = splitID($id);

         if ("FieldtypeImage" === $type || "FieldtypeFile" === $type) {
             $p = wire('pages')->get($page);
            $p->setOutputFormatting(false);

             $field = $p->$name;
             $file  = $field[$identifier];

             // added for testing only
             $sourceLanguage = wire('user')->language;
             $translation    = "This is a translation";
             // ---------------

             $targetLanguage = wire('languages')->get($language);
             $file->set("description$targetLanguage", $translation);

             // for added testing only
             echo $file->get("description$targetLanguage") . "</br></br>";
             // => "This is a translation"
             echo $file->get("description") . "</br></br>";
             // => This outputs the original string set for the default language in the Admin
             // ---------------

             $p->save();
             }
            // [....]
        }
}

So, the language value gets set properly, but it does not appear in the admin. As I already called $p->save(), I am not sure what I might have missed.

Language values for fields of type FieldtypeTextLanguage and FieldtypeTextareaLanguage that are also set in this function by calling setLanguageValue() do appear in the admin.

Again, any ideas are highly welcome!

Cheers,

Stefan

Link to comment
Share on other sites

Maybe try this before you save the page. I'm not that fluid in pass by reference and this stuff, but maybe the changes are to a variable, that does not get picked up by the page.

$p->isChanged($name);

This is the line that made me curious. I would also rather use getFile() as it's nicer / more descriptive than the array notation.

$file  = $field[$identifier];

Also did you take a look at the database, to be sure it's the part before the saving, that does not work?

  • Like 1
Link to comment
Share on other sites

I am glad you mentioned pass by reference. As the file is part of an array I made a small test:

<?php

      $arr = array("Tom");
      $value = $arr[0];
      $value = "Jerry";
      echo $arr[0];  // => Tom

      $arr[0] = $value;
      echo $arr[0];  // => Jerry
?>
 
As it turns out, the original array element did not get changed at all. So I replaced the old file with the one that was changed and now the translation appears in the admin:
 
<?php
// $translations: array of id => translation key/value pairs
// $language: string determing the target language, such a 'de' or 'pt'
function insertTranslations($translations, $language) {

     $translations = mergeSections($translations);

     foreach($translations as $id => $translation) {

      // example ID:
      // 1335··1335··FieldtypeImage··images··03.jpg··1of1
      list($refPage, $page, $type, $name, $identifier) = splitID($id);

      if ("FieldtypeImage" === $type || "FieldtypeFile" === $type) {
      $p = wire('pages')->get($page);
            $p->setOutputFormatting(false);

      $field = $p->$name;
      $file  = $field->getFile($identifier); 

      $targetLanguage = wire('languages')->get($language); 
      $file->set("description$targetLanguage", $translation);

      // replace old value with new one
      $field[$identifier] = $file;

      $p->save();
      }
     // [...]
  }
}
 
 
Thanks a lot for your help! 
 
Cheers, 
 
Stefan
 
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...